Secrets Manager 상태와 부수 효과
GitLab v19.5요약
Secrets Manager에는 동시에 모두 참일 수 있는 여러 종류의 상태가 있습니다. 변경 사항을 작성하거나 리뷰할 때 사용하는 체크리스트는 Secrets Manager 변경 가이드라인을 참고합니다. 이 표는 이 영역의 각 변경과 함께 일어나야 하는 작업을 나열합니다.
Secrets Manager에는 동시에 모두 참일 수 있는 여러 종류의 상태가 있습니다. 예를 들어 최상위 그룹의 체험판이 끝나는 시점에 Secrets Manager가 아직 프로비저닝 중일 수 있습니다. 대부분의 버그는 하나의 상태 확인이 아니라 코드가 처리하지 못한 두 상태의 조합에서 발생합니다.
변경 사항을 작성하거나 리뷰할 때 사용하는 체크리스트는 Secrets Manager 변경 가이드라인을 참고합니다.
결합할 수 있는 상태#
- Secrets Manager 수명 주기. 상태는
provisioning,active,deprovisioning입니다.activate이벤트는 레코드를active로 이동시킵니다. 프로비저닝 해제는 상태를 바꾸는 대신 Secrets Manager 행을 삭제하며, 프로비저닝 해제 작업이 대기 중인 동안effective_status는deprovisioning을 보고합니다. 시크릿 생성, 읽기, 업데이트, 삭제는 모두 Secrets Manager가active여야 합니다. Secrets Manager가active가 되기 전에는 기본 역할 정책이 아직 존재하지 않을 수 있으므로, 사용자 권한 확인(UserPermissions::EffectiveCapabilitiesService)이 모든 항목에 대해 false를 반환하고 아무것도 캐시하지 않습니다. - 시크릿 상태. 열로 저장되지 않고 타임스탬프로 계산됩니다. 값은
COMPLETED,CREATE_IN_PROGRESS,CREATE_STALE,UPDATE_IN_PROGRESS,UPDATE_STALE이며 오래됨 기준은 30초입니다. 상위 Secrets Manager가 아직active인 동안에도 시크릿이CREATE_STALE일 수 있습니다. - 유지 관리 작업. 고유 인덱스는
provision과deprovision작업을 모두 포함해 프로젝트 또는 그룹당 하나의 작업만 허용합니다. cron 워커는unprocessed,stale,retryable범위에서 작업을 가져옵니다. 프로비저닝 해제가 실행 중임을 알려 주는 지속적인 신호는 Secrets Manager 행이 아니라 이 작업입니다. - 등록. 수명 주기 상태와 별개로 Secrets Manager 사용 가능 여부를 제어합니다. 자세한 내용은 가용성 게이트를 참고합니다. 등록을 제거해도 아무것도 프로비저닝 해제되지 않습니다. 새 읽기와 쓰기만 차단합니다.
- 자격.
SecretsManagement::Entitlement의 체험판, 유료 또는 청구 상태입니다. 초기화, 쓰기, CI 읽기를 제어하며 Secrets Manager가active인 동안에도 만료될 수 있습니다. 상태와 규칙은 Secrets Manager 이행 및 자격을 참고합니다. - 프로비저닝.
InitializeService가 하나의 트랜잭션에서 Secrets Manager 행과 프로비저닝 작업을 만들고, 작업 워커가 OpenBao를 프로비저닝합니다. 프로비저닝 해제 작업이 대기 중인 동안에는 초기화가 차단됩니다. 기존 직접 프로비저닝 워커는 오래된 job을 비우는 용도로만 남아 있습니다. Owner, Maintainer, Developer 권한은provision_secrets_manager능력을 가집니다. 사용자에게 해당 능력이 있으면 체험판을 시작하거나 애드온을 활성화할 때 최상위 그룹의 Secrets Manager도 프로비저닝됩니다. - 배타적 리스. 생성, 읽기, 업데이트, 삭제(CRUD) 작업, 프로비저닝, 프로비저닝 해제는 프로젝트 또는 그룹당 하나의 리스 키를 공유하므로 서로를 차단합니다. 리스는 CRUD 작업에서 30초, 프로비저닝과 프로비저닝 해제에서 120초 동안 유지됩니다. 두 번째 호출자는 기다리지 않고 즉시 실패합니다.
상태 전환의 부수 효과#
이 표는 이 영역의 각 변경과 함께 일어나야 하는 작업을 나열합니다. 마지막 열은 이를 건너뛰면 무엇이 잘못되는지 보여 줍니다.
| 전환 | 필요한 부수 효과 | 건너뛸 때의 위험 |
|---|---|---|
| 시크릿 생성, 업데이트 또는 삭제 | CI 정책 갱신 | 파이프라인이 가지면 안 되는 액세스를 얻거나 유지함 |
| 시크릿 생성 | 값과 초기 메타데이터를 쓰고, 정책을 갱신한 다음, 메타데이터를 완료로 표시 | 갱신이 실패하면 시크릿은 OpenBao에 존재하지만 파이프라인이 읽을 수 없는 상태로 남으며, 이는 의도된 동작임 |
| 시크릿 업데이트 | check-and-set으로 메타데이터를 쓰고, 값을 쓰고, 정책을 갱신한 다음, 업데이트를 완료로 표시. 프로젝트와 그룹은 이 순서를 공유함. | 사용자가 쓰기 전에 갱신하면 OpenBao가 쓰기를 거부하는 경우에도 정책이 변경됨 |
| 프로젝트 또는 그룹 삭제 | 외래 키 연쇄 삭제가 Secrets Manager 행을 삭제하고, AFTER DELETE 트리거가 해당 행 자체의 조직, 루트 네임스페이스, 엔터티 ID로 프로비저닝 해제 작업을 삽입 |
살아 있는 상위 항목을 읽는 정리 코드는 상위 항목이 이미 없으므로 실패함 |
| 프로젝트 이전 | 이전 후 InitiateDeprovisionService가 Secrets Manager 행을 삭제하고 트리거가 작업을 삽입 |
이전 OpenBao 네임스페이스가 정리되지 않음 |
| 그룹 이전 | 하위 트리의 active Secrets Manager를 배치 단위로 일괄 삭제 |
대규모에서 레코드별 삭제를 하면 이전 요청이 타임아웃됨 |
| 프로비저닝 해제 워커 성공 | 하나의 트랜잭션에서 작업을 삭제한 다음 남은 Secrets Manager 행을 삭제 | 남은 프로비저닝 해제 작업이 Secrets Manager를 다시 초기화하는 것을 차단함 |
| 네임스페이스 해체 | containing child namespaces 및 route entry not found 오류를 허용 |
정리 cron이 실제로는 문제가 없는 상태를 영원히 재시도함 |
| 유지 관리 작업이 재시도 한도에 도달 | 작업을 그대로 둠. 고아 작업 정리 cron은 재시도 한도에 도달한 작업에 대해 30분 후 프로비저닝 해제를 실행함. | 없음. 멈춘 작업을 그것만으로 누수로 취급하지 않음. |
| 로테이션 정보를 쓴 뒤 시크릿 업데이트 실패 | 로테이션 정보 행을 그대로 둠. 로테이션 알림 cron이 고아 행을 제거함. | 없음. 고아 로테이션 행을 그것만으로 누수로 취급하지 않음. |
| 등록 변경 | 감사 이벤트 기록 | 변경에 감사 추적이 남지 않음 |
| 로테이션 정보 쓰기 | unique_by와 함께 upsert를 사용하며 일반 create나 save는 사용하지 않음 |
메타데이터 업데이트와 로테이션 쓰기 사이의 경쟁 상태가 중복 키 오류를 발생시킴 |
이행 조합#
자격은 체험판이나 청구 일정에 따라 GitLab 밖에서 변경되므로, 다른 상태가 아직 변경 중일 때 자주 변경됩니다.
| 조합 | 코드의 동작 | 확인할 사항 |
|---|---|---|
Secrets Manager가 active인 동안 자격 만료 |
느슨한 읽기 전용. UI 읽기와 시크릿 삭제는 계속 작동하고, CI 읽기는 grace 중에만 작동합니다. 쓰기, 권한 변경, 사용자가 시작한 프로비저닝 해제는 차단됩니다. 아무것도 프로비저닝 해제되지 않으며 시크릿은 유지됩니다. |
새 쓰기 경로도 여기서 차단해야 합니다. 프로젝트나 그룹을 삭제하면 데이터베이스 트리거를 통해 여전히 프로비저닝 해제됩니다. |
| 프로비저닝 중 자격 만료 | 프로비저닝 작업이 실패하고 세 번 재시도한 뒤 고아 작업 정리 cron이 프로비저닝 해제합니다. 행과 부분적인 OpenBao 상태가 제거됩니다. | 자격이 돌아온 뒤 사용자가 다시 초기화해야 합니다. |
| 프로비저닝 해제 작업이 대기 중일 때 자격 만료 | 그래도 프로비저닝 해제가 실행됩니다. 프로비저닝 해제 워커와 유지 관리 및 정리 cron은 자격을 확인하지 않습니다. | 이러한 정리 경로에는 자격 확인을 넣지 않습니다. 그렇지 않으면 정리가 멈출 수 있습니다. |
| 만료 후 자격 복구 | active Secrets Manager는 캐시가 만료된 뒤 다시 작동합니다. 다시 초기화할 필요가 없습니다. |
자격을 변경하는 뮤테이션은 캐시를 지워야 합니다. CustomersDot에서 직접 갱신한 경우 캐시가 만료되거나 사용자가 자격 새로 고침 뮤테이션을 실행하기 전까지는 아무것도 지워지지 않습니다. |
등록되었지만 trial_eligible 또는 ineligible |
trial_eligible은 최상위 그룹 읽기만 허용합니다. ineligible은 모든 것을 거부합니다. |
하위 그룹과 프로젝트 액세스는 최상위 그룹과 다릅니다. |
GitLab.com에서 옵트아웃했지만 paid |
자격은 paid로 유지되지만 가용성은 false입니다. 모든 것이 거부되고, CI job이 버려지며, secrets_stored가 내보내지지 않습니다. |
paid를 사용 가능으로 취급하지 않습니다. 가용성과 자격을 따로 확인합니다. |
| 프로젝트 또는 그룹 이전 | 두 루트의 자격과 관계없이 이동한 하위 트리의 모든 active Secrets Manager가 프로비저닝 해제됩니다. 새로 만드는 Secrets Manager는 대상 루트의 자격을 통과해야 합니다. |
시크릿 개수 행은 조정이 실행될 때까지 이전 루트 네임스페이스를 유지합니다. |
| 파이프라인 실행 중 자격 만료 | job을 가져갈 때마다 확인합니다. 실행 중인 job은 영향을 받지 않습니다. 이후 job은 캐시가 만료된 뒤 secrets_manager_access_denied로 실패합니다. |
job 가져오기는 조회 오류 시 열린 상태로 실패하고, 러너 페이로드 확인은 닫힌 상태로 실패합니다. |
| CustomersDot 중단 | 직접 읽기를 허용했다면 마지막으로 확인된 정상 응답이 최대 24시간 동안 재사용됩니다. 그렇지 않으면 자격은 ineligible입니다. |
중단 중에 만료되는 체험판은 해당 기간이 끝날 때까지 계속 작동합니다. |
차단되었거나 ineligible인 네임스페이스의 과금 이벤트 |
이벤트는 자격 상태를 메타데이터로 담아 여전히 내보내집니다. | 과금 이벤트가 자격에 의존하게 만들지 않습니다. |
| 엄격한 읽기 전용 데이터베이스 | 자격과 관계없이 아무것도 쓰이지 않습니다. | 느슨한 읽기 전용과 엄격한 읽기 전용은 각각 따로 처리해야 합니다. |
프로젝트와 그룹의 차이#
프로젝트와 그룹 Secrets Manager는 대부분 같은 방식으로 작동합니다. 아래 목록은 둘이 다른 부분을 다룹니다.
- 프로젝트 시크릿은
branch파라미터를, 그룹 시크릿은protected파라미터를 사용하며, 유효성 검사와 메타데이터 키가 다릅니다. - 프로젝트 Secrets Manager는 Owner, Maintainer, Developer 권한에 기본 시크릿 관리 권한을 부여하고, 그룹 Secrets Manager는 Owner 권한에만 부여합니다. Developer는
read와create를 받으므로 시크릿을 추가할 수는 있지만 이미 있는 시크릿을 변경할 수는 없습니다. 프로젝트와 그룹의 이 차이는 제품 결정입니다. - 삭제와 프로젝트 이전은 레코드별로 처리되고, 그룹 이전은 일괄 처리됩니다.
- 프로젝트와 그룹은 같은 시크릿 업데이트 순서를 공유하며, 둘 다 Common Expression Language(CEL) 역할만 프로비저닝합니다. 새로운 차이를 추가하는 변경에는 명시된 이유가 필요합니다.