- analysis/·source-index·state.json 을 final/document.md 제2부·제3부로 접었다. SSOT 는 하나다 - 파일럿 — commit-ambiguity-as-a-result 를 새 기준으로 재선별. 후보 14 → 글감 5 (PROMOTE 5 · MERGE_INTO 3 · KEEP_IN_SSOT 4 · 보류 2). 기록 5건을 다시 썼고 그림 1개를 techviz 로 만들었다 - 재선별이 잡은 것: 제1부 §6.2·§11.1 이 자기 §13.2 와 어긋나 있었다(레인을 안 돌렸다 vs 돌렸다) — 정정. 이미 답이 나와 있던 Question 을 HEAD 재실행 질문으로 다시 세웠다. Concept 이 인용한 코드가 SSOT 에 없어 뺐다 - candidateScope·sourceRepository 기록. 나머지 43개 주제는 재선별 대기(PENDING 905) Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
15 KiB
kind, slug, title, topic, project, status, sourceRevision, rootTreeNode, evidenceCapturedOn, body, assets, evidence, source
| kind | slug | title | topic | project | status | sourceRevision | rootTreeNode | evidenceCapturedOn | body | assets | evidence | source | |||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| CASE | analysis-finding-a06-f023 | 고위험 관리 작업 넷이 승인을 널로 넘기는 오버로드를 부른다 | multitenancy-isolation | clean-architecture-backend-template | 게시 전 | 21234e38cdb9a926cbc92bb97a2aee2e4a7d2916 | case:analysis-finding-a06-f023 | 2026-09-04 | case-analysis-finding-a06-f023.body.md |
|
|
|
고위험 관리 작업 넷이 승인을 널로 넘기는 오버로드를 부른다
MongoAdminGateway:66 이 승인 자리에 null 을 넣은 채 세 인자 오버로드를 부른다. :94~:102 는 고위험 연산에 승인이 없으면 거절한다. 그 편의 오버로드를 부르는 main 일곱 줄 가운데 넷이 고위험 연산을 넘긴다.
관계
- 권한이 센 절반이 설정 한 줄로 켜지면 안 된다 그 규칙이 다루는 것이 승인 어휘가 둘일 때의 문제다. 여기서는 편의 오버로드가 승인 없는 쪽을 기본으로 만든다.
- 같은 개념의 두 어휘가 공존하면 하나를 죽은 것으로 표시한다
execute가 둘인데 승인을 받는 쪽을 부르는 main 호출이 0 이다. - 두 형태를 나란히 내놓는 포트는 이미 안전하지 않은 쪽을 고른 것이다
그 규칙 2 가 폐기 표시도 이름 차이도 가시성 차이도 없으면 호출자가 짧은 쪽을 고른다고 적는다.
execute둘이 이름도 가시성도 같고, main 일곱 호출이 전부 짧은 쪽이다.
문제
이 평면의 실행 경로는 고위험 연산에 명령별 승인을 강제한다.
승인을 실제로 넘기는 호출이 있는지 확인했다.
결론
편의 오버로드가 :63~:67 에서 본 메서드를 부르면서 :66 의 승인 자리에 null 을 넣는다.
:94~:102 가 그 null 을 거절한다. 고위험 연산에 승인이 없으면 MongoOperationRejectedException 이 나가고, 메시지가 그런 연산은 명령에 묶인 승인 아래에서만 돈다고 적는다.
그 검사에 걸릴 수 있는 연산은 여덟이다. 그중 넷이 다섯 인자 오버로드로 넘어간다. MongoShardingAdminGateway:64 의 SHARD_COLLECTION, :75 의 REFINE_SHARD_KEY, :86~:87 의 RESHARD_COLLECTION, 그리고 MongoQueryableEncryptionCollectionManager:63~:64 의 MANAGE_ENCRYPTION_KEY 다.
넷 다 인자를 무엇으로 채워도 완료되지 않는다. 승인 자리가 null 로 고정돼 있어 :95 에서 걸린다.
MongoShardingAdminGateway:92 의 BALANCER_CONTROL 은 highRisk(false) 라 이 검사에 걸리지 않는다. MongoQueryableEncryptionCollectionManager:42 의 CREATE_COLLECTION 과 :70 의 COLL_MOD 도 그렇다.
승인 객체를 만드는 프로덕션 코드가 없다. MongoAdminApproval.of(...) 를 부르는 main 줄이 0 이고, 그 타입이 main 에 등장하는 다섯 자리는 전부 자기 선언이거나 게이트웨이 서명이다. 시험에는 그것을 만드는 줄이 넷 있다.
샤딩 게이트웨이가 받는 ReshardApproval 은 다른 타입이다. main 에 나오는 넷이 전부 자기 선언이거나 파라미터이고, 그것을 MongoAdminApproval 로 옮기는 자리가 없다.
MongoShardingAdminGateway:49~:63 이 그 앞에서 승인 준비 상태와 지원 인덱스를 검사하지만, 그것을 통과해도 :64 에서 막힌다.
검증 환경
OpenJDK : 21.0.12 확인 방식 : 샤딩 게이트웨이의 네 메서드 전문 인용과 그 호출 계수, 다섯 인자 오버로드 인용, 세 인자 오버로드의 승인 검사 인용, 연산 열거형의 위험 등급 인용과 계수, main 에 나오는 연산마다 위험 등급과 등장 줄 대조, 고위험을 넘기는 자리 전수 인용, 승인 객체를 만드는 main 계수와 그 이름의 main 등장 전수와 시험 대조, ReshardApproval 의 main 등장 전수 소스 수정 : x
재현 조건
- 샤딩 게이트웨이의 네 메서드를 전문으로 싣고 adminGateway.execute 호출을 센다.
- 다섯 인자 오버로드를 인용해 승인 자리에 무엇이 들어가는지 보인다.
- 실행 경로의 고위험 승인 검사를 인용한다.
- 그 오버로드를 지나는 연산 상수의 위험 등급을 열거형에서 인용하고 전체 상수와 고위험 개수를 함께 센다.
- main 에 나오는 연산 상수마다 위험 등급과 등장 줄을 대조한다.
- 고위험을 다섯 인자 오버로드로 넘기는 자리를 전부 인용한다.
- 승인 객체를 만드는 main 줄을 세고 그 타입이 main 에 등장하는 자리를 전부 나열한 뒤, 시험 쪽 계수를 대조로 낸다.
- ReshardApproval 이 main 에 나오는 자리를 전부 나열해 두 승인 타입을 잇는 코드가 있는지 본다.
본문
MongoAdminOperation:4 자바독이 이 열거형을 D4 평면이 수행할 수 있는 관리 연산이라고 부른다. 그 평면은 고위험 연산에 명령별 승인을 요구한다. 샤딩 게이트웨이가 네 작업을 그 위에 올린다.
샤딩 게이트웨이의 네 메서드
:::evidence key="analysis-finding-a06-f023" alt="저장소 루트에서 돌린 정적 검색 출력 215줄. 먼저 MongoShardingAdminGateway 3393번이 실린다. 3865번의 shardCollection 이 컬렉션과 샤드 키와 준비도 보고서와 지원 인덱스 필드를 받아 4953번에서 승인되지 않은 샤드 키를 거절하고 5463번에서 지원 인덱스가 샤드 키로 시작하지 않으면 거절한 뒤 64번에서 adminGateway.execute 에 SHARD_COLLECTION 을 넘긴다. 6876번의 refineShardKey 와 7988번의 reshardCollection 은 ReshardApproval 을 require 한 뒤 각각 75번과 8687번에서 REFINE_SHARD_KEY 와 RESHARD_COLLECTION 을 넘기고, 9193번의 controlBalancer 는 92번에서 BALANCER_CONTROL 을 넘긴다. 네 메서드가 부르는 execute 가 4 개다. 이어서 MongoAdminGateway 4068번이 실리는데 4756번 자바독이 다섯 인자의 뜻을 적고, 5762번 서명이 연산과 대상과 운영자와 사유와 본문을 받으며, 6367번이 MongoAdminCommand.routine 으로 명령을 만들어 66번에서 승인 자리에 null 을, 67번에서 본문을 넘긴다. 다음으로 69112번의 세 인자 오버로드가 실린다. 7081번 자바독은 단일 레코드 버전에서 셋이 바뀌었다며 의도가 명령 실행 전에 기록되고 아무것도 주장하지 않으며 무엇이 실제로 일어났는지 적는 종결 레코드가 뒤따르고 실패하는 감사 싱크가 명령을 멈추는데 감사할 수 없는 관리 작업은 나중에 누구도 재구성할 수 없기 때문이고 drop 이나 reshard 에는 그것이 이 평면을 두는 이유 전부라고 적으며, 79번이 승인은 고위험 연산에 필요하고 이 명령에 묶인다고 적는다. 83번 서명이 명령과 승인과 본문 셋을 받고, 87번이 권한을 요구하고 8893번이 만료된 명령을 거절하며, 94102번이 고위험 연산에 승인이 null 이면 데이터를 파괴하거나 컬렉션을 다시 쓰는 연산은 이 명령에 묶인 승인 아래에서 돌거나 아예 돌지 않는다는 메시지로 거절하고, 103번이 승인을 검사하며 104110번이 단일 사용을 강제하면서 그렇지 않으면 한 reshard 에 대한 승인 하나가 같은 모양의 이후 모든 reshard 를 허가하게 된다고 주석에 적는다. 이어서 MongoAdminOperation 310번 자바독이 이것이 D4 평면이 수행할 수 있는 관리 연산의 닫힌 열거형이고 모든 상수가 애플리케이션 런타임이 닿으면 안 되는 것이며 여기 모아 두는 것이 경계를 어떤 메서드가 있느냐에서 나오는 성질이 아니라 누군가 검토할 수 있는 목록으로 만든다고 적는다. 13번 CREATE_COLLECTION 과 16번 COLL_MOD 와 46번 BALANCER_CONTROL 이 false 이고 37번 SHARD_COLLECTION 과 40번 REFINE_SHARD_KEY 와 43번 RESHARD_COLLECTION 과 49번 MANAGE_ENCRYPTION_KEY 가 true 이며, 그 일곱 가운데 고위험이 4 개, 열거형 전체에서 고위험이 8 개, 상수 전체가 15 개다. 다음으로 승인을 실제로 넘기는 main 호출이 0 개이고, execute 를 부르는 main 자리 일곱이 나열되는데 MongoQueryableEncryptionCollectionManager 41번과 63번과 70번, MongoShardingAdminGateway 64번과 75번과 86번과 92번이며, 시험에서 세 인자 execute 를 부르는 줄은 10 개이고, MongoAdminApproval 을 만드는 main 줄은 0 개이며 그 이름이 main 에 나오는 자리는 MongoAdminApproval 자신의 19·21·31·33번과 MongoAdminGateway 83번의 서명 다섯이고, 시험에서 그것을 만드는 줄은 4 개다. 이어서 main 에 나오는 연산 상수마다 위험 등급과 등장 줄이 대조되는데 BALANCER_CONTROL 과 COLL_MOD 와 CREATE_COLLECTION 이 false 이고 MANAGE_ENCRYPTION_KEY 와 REFINE_SHARD_KEY 와 RESHARD_COLLECTION 과 SHARD_COLLECTION 이 true 이며 각각 한 줄씩이다. 고위험인데 다섯 인자 오버로드로 넘어가는 자리 넷이 실리는데 MongoShardingAdminGateway 64번과 75번과 8687번, 그리고 MongoQueryableEncryptionCollectionManager 6165번의 rotateDataKey 가 64번에서 MANAGE_ENCRYPTION_KEY 를 넘기는 자리이며, 대조로 같은 클래스 3443번의 createEncryptedCollection 이 4142번에서 넘기는 CREATE_COLLECTION 은 false 다. 마지막으로 ReshardApproval 이 main 에 나오는 줄이 4 개라고 나오고 그 넷이 MongoShardingAdminGateway 70번과 81번의 파라미터와 ReshardApproval 자신의 15번과 22번이다." caption="샤딩 게이트웨이의 네 메서드와 그 네 호출 · 승인 자리에 null 을 넣는 다섯 인자 오버로드 · 고위험에 승인을 요구하는 세 인자 오버로드 · 연산 열거형의 위험 등급과 계수 · 승인을 넘기는 main 호출 0 과 execute 일곱 자리 · 고위험을 넘기는 넷 · 두 승인 타입을 잇는 코드 부재 — 215줄 · exit 0" zoom="true"
:::
MongoShardingAdminGateway:38 의 shardCollection 이 컬렉션과 샤드 키와 준비도 보고서와 지원 인덱스 필드를 받는다. :49~:53 이 승인되지 않은 샤드 키를 거절하고, :54~:63 이 지원 인덱스가 샤드 키로 시작하지 않으면 거절한다.
:68 의 refineShardKey 와 :79 의 reshardCollection 은 ReshardApproval 을 require() 한다. :91 의 controlBalancer 는 앞선 검사가 없다.
넷 다 마지막 줄에서 adminGateway.execute(...) 를 부른다.
그 오버로드가 승인 자리에 넣는 것
MongoAdminGateway 에 execute 가 둘이다. :57~:62 의 다섯 인자 오버로드가 연산과 대상과 운영자와 사유와 본문을 받고, :83 의 세 인자 오버로드가 MongoAdminCommand 와 MongoAdminApproval 과 본문을 받는다.
다섯 인자 쪽이 :63~:67 에서 MongoAdminCommand.routine(...) 으로 일상 명령을 만들어 세 인자 쪽에 넘긴다. :66 이 승인 자리다. null 이다.
세 인자 오버로드가 그 null 을 거절한다
:87 이 권한을 요구하고 :88~:93 이 만료된 명령을 거절한다.
:94 가 연산이 고위험인지 본다. 고위험이면 :95 가 승인이 null 인지 보고, 그렇다면 :96~:102 가 거절한다. 메시지는 데이터를 파괴하거나 컬렉션을 다시 쓰는 연산은 이 명령에 묶인 승인 아래에서 돌거나 아예 돌지 않는다는 것이다.
:103 이 승인 자체를 검사하고 :106 이 단일 사용을 강제한다. :104~:105 주석은 그것이 없으면 한 reshard 에 대한 승인 하나가 같은 모양의 이후 모든 reshard 를 허가하게 된다고 적는다.
승인이 null 인 고위험 명령은 :95 에서 끝난다.
넷이 그 조합에 걸린다
MongoAdminOperation 상수는 열다섯이고 그중 여덟이 highRisk(true) 다.
main 에서 다섯 인자 오버로드로 넘어가는 연산은 일곱 줄에 나뉘어 있다. BALANCER_CONTROL 과 COLL_MOD 와 CREATE_COLLECTION 은 false 이고, SHARD_COLLECTION 과 REFINE_SHARD_KEY 와 RESHARD_COLLECTION 과 MANAGE_ENCRYPTION_KEY 는 true 다.
고위험 넷의 위치는 MongoShardingAdminGateway:64·:75·:86~:87 과 MongoQueryableEncryptionCollectionManager:63~:64 다. 마지막 것은 :62 의 rotateDataKey 로, 자바독이 자기 런북과 증거를 요구한다고 적는다.
넷 다 호출자가 무엇을 넘겨도 :95 를 지나지 못한다. 승인 자리가 그 오버로드 안에서 이미 정해져 있기 때문이다.
승인 객체를 만드는 main 코드가 없다
MongoAdminApproval.of(...) 나 new MongoAdminApproval 을 부르는 main 줄이 0 이다.
그 이름이 main 에 나오는 자리는 다섯인데, 넷이 MongoAdminApproval 자신의 선언과 팩터리이고 하나가 MongoAdminGateway:83 의 서명이다.
세 인자 execute 를 부르는 시험 줄은 MongoAdminAuditStateMachineTest 에 10 이고, 승인 객체를 만드는 시험 줄은 4 다. 프로덕션에는 그 짝이 없다.
MongoShardingAdminGateway 의 앞선 검사들은 그 뒤를 바꾸지 못한다. :49 의 준비도 검사와 :54 의 인덱스 검사와 :74·:85 의 ReshardApproval.require() 를 전부 통과해도 :64·:75·:86 에서 같은 자리에 막힌다.
ReshardApproval 과 MongoAdminApproval 은 다른 타입이다. ReshardApproval 이 main 에 나오는 줄은 넷인데 MongoShardingAdminGateway:70·:81 의 파라미터 둘과 ReshardApproval:15·:22 의 자기 선언 둘이다. MongoAdminApproval 을 만드는 자리는 그 안에 없다.
원문에 없는 것
원문은 샤딩 게이트웨이의 네 작업 중 셋이 어떤 입력으로도 완료될 수 없다고 적는다. 그 셋은 그대로 확인된다.
네 번째가 있다. MongoQueryableEncryptionCollectionManager:63~:64 의 rotateDataKey 도 같은 오버로드에 MANAGE_ENCRYPTION_KEY 를 넘기고, 그 상수도 highRisk(true) 다. 같은 클래스 :41~:42 의 CREATE_COLLECTION 은 false 라 걸리지 않는다.
다섯 인자 오버로드에 고위험 연산을 넘기는 main 자리를 저장소 전체에서 세면 넷이고, 그 넷이 두 클래스에 나뉘어 있다. 샤딩 리프만의 문제가 아니다.
확인하지 못한 것
그 넷을 불러 예외가 나는 것을 프로브로 보이지 않았다.
MongoShardingAdminGateway 와 MongoQueryableEncryptionCollectionManager 를 만드는 프로덕션 코드가 있는지 조립 경로를 세지 않았다.
포크가 승인을 어디서 만들어 넘기도록 설계된 것인지 설계 문서로 판단하지 않았다.
ReshardApproval 을 MongoAdminApproval 로 옮기는 코드가 왜 없는지, 두 타입의 관계를 설계 문서로 확인하지 않았다.