# Keycloak 수정 반영 재검토 리뷰 - 검토일: 2026-09-19 - 대상 프로젝트: `docs/keycloak` - 검토 기준: 7단계 TechLog 하네스 - 최종 판정: **아직 더 봐야댐** --- ## 1. 결론 직전 리뷰에서 지적한 **문서 내용과 SVG 문제는 이번 수정에서 모두 정상적으로 반영됐다.** 특히 다음 항목은 현재 기준으로 닫혔다. - Bearer JWT validation chain SVG 누락 - IdP Brokering boundary/flow SVG 누락 - `reference-pattern-selection.md`의 작성 지시형 문장 - Public / Confidential Client 정의 반복 및 shared-secret 중심 과도한 일반화 - IdP Federation Reference의 과도하게 긴 문장 - BFF state-store Question의 `여기까지` 같은 문서 진행 메타 표현 - Multi-instance Question의 지나치게 기계적인 선택지 리듬 - Public / Confidential Client의 일반 정의와 프로젝트 구현 사실의 범위 혼동 - Token Endpoint 섹션 제목의 과도한 일반화 - Authorization Endpoint의 referrer 설명에서 Referrer-Policy 조건 누락 자동 검사도 모두 통과했다. 다만 현재 수정 작업에 대응하는 **새 run ledger가 없다.** 이 프로젝트의 리뷰 기준은 결과물만 보는 것이 아니라, 문서를 다음 7단계 절차로 작성·수정했는지까지 확인하는 것이다. 1. S1 — 코드베이스 → SSOT 2. S2 — SSOT → 분해 계약 3. S3 — 글감 → 기록 4. S4 — 기록 → 그림 5. S5 — AI 티 제거 6. S6 — 일한 사람의 목소리 7. S7 — Studio 저장 이번 수정은 결과물 기준으로는 정상이나, **2026-09-19 수정 작업을 위 절차로 수행했다는 현재 시점의 실행 원장이 남지 않았다.** 따라서 최종 상태는 다음과 같다. > **문서 내용 수정: 문제 없음** > **7단계 절차 증빙: 미완료** 즉, 현재 `keycloak = 아직 더 봐야댐`이다. --- # 2. 이번 재검토 범위 이번 검토는 단순 기술 정확성 리뷰가 아니라 다음 순서를 기준으로 다시 확인했다. ## 2.1 S3 — 사실과 범위 - 일반 OAuth/OIDC 개념과 이 프로젝트 구현 사실이 섞이지 않았는지 - 확인한 것과 확인하지 못한 것을 분리했는지 - source repository가 없는 상황에서 live source 검증을 했다고 쓰지 않았는지 - Public / Confidential Client 정의가 shared secret 하나로 축소되지 않았는지 - Token Endpoint, Referrer-Policy 같은 세부 기술 설명이 과도하게 일반화되지 않았는지 ## 2.2 S4 — SVG - 그림이 필요한 Concept에 그림이 실제로 추가됐는지 - 그림이 표로 대체 가능한 내용이 아닌지 - 관계, 순서, 경계를 보여 주는 그림인지 - TechViz `context.json`, `prompt.md`, `spec.json`이 있는지 - 생성된 SVG에 provenance가 있는지 - Figure Text / Overlap / Provenance 검사를 통과하는지 ## 2.3 S5 — AI 티 제거 - 문서 작성 지시문처럼 읽히는 표현이 남아 있지 않은지 - 같은 정의를 반복하지 않는지 - 기계적인 문단 대칭과 리듬이 줄었는지 - 지나치게 긴 문장을 의미 단위로 나눴는지 - 스타일 점수를 맞추기 위해 OAuth 식별자까지 억지로 번역하지 않았는지 ## 2.4 S6 — 일한 사람의 목소리 - 실제 관찰, 코드 추적, 미검증 범위가 남아 있는지 - 근거 없는 1인칭 경험을 새로 만들지 않았는지 - S5 수정 과정에서 기존 판단 맥락을 평평하게 만들지 않았는지 ## 2.5 Command Pedagogy Keycloak 프로젝트에는 현재 shell/CLI block이 없다. 따라서 이 프로젝트에서는 command pedagogy를 억지로 적용하거나 명령어를 새로 추가하는 것이 아니라 **정상 SKIP / N/A**가 맞다. --- # 3. 직전 리뷰 항목 폐쇄 확인 ## F-S4-01 — Bearer JWT validation chain SVG ### 이전 문제 `concept-bearer-jwt-validation-chain.md`는 다음 변환 사슬을 텍스트로만 설명하고 있었다. ```text Bearer JWT → NimbusJwtDecoder → issuer/time validation → audience validation → validated Jwt → role converter → authenticated principal ``` 이 기록의 핵심은 변환 순서였기 때문에 Concept에서 SVG가 필요한 항목이었다. ### 현재 상태 **닫힘** 추가된 TechViz: ```text docs/keycloak/final/.techviz/bearer-jwt-validation-chain/ ├── context.json ├── prompt.md └── spec.json ``` 추가된 자산: ```text docs/keycloak/final/assets/bearer-jwt-validation-chain/ └── bearer-jwt-validation-chain.svg ``` Spec 확인 결과: - profile: `component-flow` - diagram-only: true - source gap: 없음 - assumption: 없음 노드 구성도 기록의 실제 검증 체인을 그대로 따른다. ```text Bearer JWT → NimbusJwtDecoder → Issuer · Time validators → AudienceValidator → Validated Jwt → Realm role converter → Authenticated principal ``` Concept 본문에도 SVG가 실제로 연결되어 있다. ### 판단 S4 누락 문제는 해결됐다. --- ## F-S4-02 — IdP Brokering boundary/flow SVG ### 이전 문제 `concept-idp-brokering.md`의 핵심은 외부 IdP가 다섯 번째 애플리케이션 인증 패턴이 아니라, ```text upstream IdP → Keycloak broker → Keycloak-issued code/token → AP1/AP2/AP3/AP4 application boundary ``` 라는 **두 OAuth 경계의 연결**을 보여 주는 것이었다. 기존에는 이를 text fence로만 설명했다. ### 현재 상태 **닫힘** 추가된 TechViz: ```text docs/keycloak/final/.techviz/idp-broker-upstream-downstream-boundary/ ├── context.json ├── prompt.md └── spec.json ``` Spec 확인 결과: - profile: `two-zone-pipeline` - diagram-only: true - source gap: 없음 - assumption: 없음 노드: ```text Google IdP → Keycloak broker → Keycloak authorization code → AP1 · AP2 · AP3 · AP4 ``` 이 구조는 문서의 핵심 주장인 다음 두 가지를 잘 분리한다. 1. upstream authentication은 외부 IdP와 Keycloak 사이에서 끝난다. 2. 애플리케이션이 상대하는 issuer와 downstream 인증 경계는 계속 Keycloak이다. ### 판단 S4 누락 문제는 해결됐다. --- # 4. SVG 전체 검증 현재 Keycloak 프로젝트의 TechViz / SVG는 각각 12개다. 검사 결과: ```text FIGURE TEXT: PASS - 그림 12장 - 문장 0건 FIGURE PROVENANCE: PASS - 정본과 짝지은 그림 12 FIGURE OVERLAP: PASS - 그림 12 - 본 그림 12 - 겹친 그림 0 ``` 따라서 새 SVG 두 장은 단순 파일 추가가 아니라 현재 하네스의 Figure gate도 통과했다. 기존 10개 SVG를 다시 그릴 이유도 확인되지 않았다. --- # 5. S5 — AI 티 제거 재검토 ## F-S5-01 — pattern-selection 작성 지시문 ### 이전 문제 다음과 같은 문장이 있었다. ```text 성공 응답과 실패 응답까지 봐야 한다. 어떤 보안 요구사항과 운영 조건 때문에 그 구조를 골랐는지 함께 적는다. 운영 항목까지 같이 적는다. ``` 이 표현은 패턴 선택 기준 자체가 아니라 “문서를 어떻게 작성해야 하는가”를 설명하는 문장에 가까웠다. ### 현재 상태 **닫힘** 현재는 실제 비교 기준을 직접 서술한다. 예: ```text 비교 입력에는 엔드포인트와 메서드, 중간에 생기는 자격 증명, 성공·실패 응답이 포함되고 로그인 구간과 로그인 뒤 API 호출 구간을 각각 나눠 본다. ``` 또 선택 기록에 어떤 운영 조건이 들어가야 하는지도 “작성 지시”가 아니라 선택 기준의 구성 요소로 바뀌었다. --- ## F-S5-02 — Public / Confidential Client 반복 정의 ### 이전 문제 같은 정의를 여러 위치에서 반복하면서 Reference 전체가 정의의 재진술처럼 읽혔다. 또 general OAuth definition과 이 프로젝트의 `client_secret_basic` 구현 사실이 섞여 있었다. ### 현재 상태 **닫힘** 현재 첫 정의는 다음처럼 정리됐다. ```text OAuth 클라이언트 종류는 인증 서버에 대해 장기 자격 증명의 기밀성을 유지하고 신뢰할 수 있는 클라이언트 인증을 수행할 수 있는지로 구분한다. ``` 그 뒤에는 같은 정의를 다시 반복하지 않고 다음 실제 프로젝트 차이로 넘어간다. - AP1 SPA → public client - AP2~AP4 → confidential client - 이 프로젝트의 confidential client 인증 방식 → `client_secret_basic` - Confidential Client 인증 수단 자체는 shared secret에 한정되지 않음 - client type과 browser token custody는 별도 축 이 구성이 훨씬 낫다. --- ## F-S5-03 — IdP Federation 장문 ### 이전 문제 한 문장 안에 현재 경계, 예외 조건, 직접 연동 시 변화, 미검증 범위가 함께 들어가 읽기 부담이 컸다. ### 현재 상태 **닫힘** 현재는 다음 축으로 나뉘어 있다. - broker 경계 - external identity key - email collision - mock provider 검증 범위 - broker를 쓰지 않는 direct OIDC 예외 내용은 그대로 유지하면서 문장 구조만 단순해졌다. --- ## F-S5-04 — BFF State Store의 `여기까지` ### 이전 문제 ```text 여기까지는 한 대에서 실행한 학습 환경에서 코드와 테스트로 확인한 것이다. ``` 이 표현은 사실 범위를 말하는 데 필요한 내용이지만, “여기까지”는 문서 진행을 설명하는 메타 표현이었다. ### 현재 상태 **닫힘** 현재 문장: ```text 현재 확인 범위는 한 대에서 실행한 학습 환경의 코드와 테스트다. ``` 범위만 직접 남겼다. --- ## F-S5-05 — Multi-instance 선택지의 기계적 대칭 ### 이전 문제 각 선택지가 모두: ```text 정의 → 장점 → 다만 → 추가 설계 필요 ``` 패턴으로 반복돼 AI가 템플릿으로 만든 선택지처럼 읽혔다. ### 현재 상태 **닫힘** 지금은 각 선택지가 서로 다른 판단 축을 제목과 본문에서 직접 드러낸다. ```text 공유 저장소 → 상태 일관성 / 저장소 가용성 Session affinity → 라우팅 고정 / node loss는 해결하지 못함 브라우저 토큰 → 서버 공유 상태 제거 / credential ownership이 browser로 이동 Client-side cookie → 저장소 문제가 아니라 trust boundary 변화 ``` 질문의 성격상 선택지 병렬 구조 자체는 유지해야 하므로, 현재 수준이면 충분하다. --- # 6. S3 기술 범위 수정 확인 ## Public / Confidential Client 정의 **닫힘** 현재 SSOT와 Case에서도 다음 방향으로 정리됐다. ```text 브라우저 실행 환경에서 장기 client credential의 기밀성을 유지하고 신뢰할 수 있는 client authentication을 수행하기 어렵기 때문에 public client ``` AP2는: ```text server에서 client credential을 보호하고 client authentication을 수행할 수 있는 confidential client ``` 로 표현한다. 즉: ```text public/confidential ≠ 브라우저가 토큰을 받느냐 ``` 라는 프로젝트의 핵심 구분도 유지된다. --- ## Token Endpoint 제목 **닫힘** 이전의: ```text Token Endpoint에서 비로소 클라이언트를 인증한다 ``` 같은 일반화 대신 현재는: ```text confidential client는 Token Endpoint에서 자신을 인증한다 ``` 로 범위를 좁혔다. 본문도 AP1 public SPA와 AP2~AP4 confidential client를 분리해서 설명한다. --- ## Referrer-Policy **닫힘** 현재는 Authorization Endpoint URL 노출 범위를 다음처럼 적는다. ```text 다른 문서나 origin으로 이동할 때 referrer에 어느 범위까지 전달되는지는 브라우저의 Referrer-Policy와 이동 대상의 관계에 따라 달라진다. ``` 따라서 “항상 query 전체가 referrer에 남는다”는 식의 과도한 일반화는 제거됐다. --- # 7. S5 / S6 자동 검사 현재 24개 기록 전체 검사 결과: ```text Natural Prose - FAIL 0 Voice - FAIL 0 ``` Style profile에는 일부 advisory outlier가 남아 있다. 예: - OAuth 식별자와 영문 기술명 때문에 Hangul ratio가 낮은 문서 - 120자 초과 문장 비율이 약간 높은 문서 - 이유 연결 표현 빈도가 reference 범위보다 조금 낮은 문서 하지만 style profile은 하네스에서도 advisory다. 현재 outlier를 없애기 위해 다음과 같은 행동을 하면 오히려 문서 품질이 떨어진다. - `Authorized Client`, `Token Endpoint`, `client_secret_basic` 같은 보호된 기술어를 억지 번역 - 문장 길이 수치만 맞추려고 의미 단위 파괴 - 이유 연결어미 수치를 맞추려고 불필요한 “때문에”, “따라서” 추가 따라서 현재 자동 style metric만을 이유로 추가 수정을 요구하지 않는다. --- # 8. Command Pedagogy 현재 Keycloak Studio 기록에는 shell/CLI block이 없다. 검사 결과: ```text shell blocks = 0 findings = 0 ``` 따라서 이 프로젝트의 Command Pedagogy는 **정상 SKIP / N/A**다. HTTP 예시, JSON 예시, text flow를 shell 명령어처럼 취급해서는 안 된다. 또 “명령어 품질도 리뷰 기준이니 shell command를 추가하자”는 식으로 대응하면 안 된다. --- # 9. 자동 검증 결과 Keycloak 단독: ```text verify-tech-log-tree.py keycloak PASS records=24 topics=1 nodes=24 written=24 unwritten=0 verify-project-layout.py keycloak PASS error=0 audit-records.py keycloak PASS check-figure-text.py keycloak PASS check-figure-provenance.py keycloak PASS check-figure-overlap.py keycloak PASS check-required-content.py keycloak PASS check-ssot-facts.py keycloak PASS git diff --check -- docs/keycloak runs/keycloak PASS ``` 전체 하네스 회귀: ```text verify-pipeline.py PASS exit 0 ``` 전체 테스트: ```text Ran 391 tests OK (skipped=14) ``` 따라서 이번 수정으로 하네스 자체나 다른 프로젝트가 깨진 것은 아니다. --- # 10. 남은 문제 — 이번 수정의 run ledger 현재 Keycloak에는: ```text records = 24 run.json = 13 run이 덮은 unique record = 12 ``` 기존 12개의 historical record에 run ledger가 없는 것은 이번에 새로 발견된 결함으로 취급하지 않는다. 하네스 규칙상 과거 실행을 하지 않았는데 과거 원장을 만들어 내면 안 된다. > **historical run ledger를 소급 작성하지 않는다.** 문제는 이번 2026-09-19 수정이다. 이번 재검토 시점에 변경된 Keycloak Studio Record는 17개인데, `runs/keycloak`의 최신 실행 원장은: ```text 2026-09-16-2130-fact-redis-preference ``` 다. 즉 **이번 수정 작업을 위한 current run이 하나도 없다.** 이 상태에서는: - S3를 누가 수행했는지 - S4에서 왜 SVG를 추가했거나 SKIP했는지 - S5를 다시 거쳤는지 - S6를 다시 거쳤는지 - command lane을 왜 SKIP했는지 - fact review를 수행했는지 - S7을 왜 SKIP했는지 를 절차적으로 증명할 수 없다. 자동 결과가 PASS라고 해도, 사용자가 요구한 “7단계 절차를 기반으로 문서를 작성했는가”에는 아직 답이 부족하다. --- # 11. 수정 실행 시 지켜야 할 원칙 ## 하지 말 것 ### 1. 과거 12개 무원장 기록을 소급해서 만들지 않는다 이번 수정과 관계없는 historical record까지 fake ledger로 채우면 안 된다. ### 2. 기존 run.json을 고쳐서 이번 실행처럼 만들지 않는다 과거 영수증을 수정하는 것도 금지한다. ### 3. 문서를 다시 대규모 rewrite하지 않는다 현재 문서 내용 finding은 닫혔다. 다시 손댈 이유가 없다. ### 4. SVG를 다시 그리지 않는다 현재 12개 모두 Figure gate를 통과한다. ### 5. shell command를 추가하지 않는다 Keycloak에는 현재 command pedagogy lane이 적용될 shell/CLI가 없다. --- # 12. 필요한 실제 조치 이번 수정 대상에 대해 **새 current remediation run**을 만든다. 수정된 Record마다 현재 하네스 규칙을 적용한다. 권장 흐름: ```text run 시작 ↓ S1 기존 SSOT로 충분하면 SKIPPED + 구체적인 이유 ↓ S2 기존 PROMOTE / CONFIRMED tree node라면 SKIPPED + 이유 ↓ S3 현재 수정 결과 확인 ↓ Command initial analysis shell/CLI 없음 → SKIPPED + 이유 ↓ S4 Bearer JWT / IdP Brokering은 DONE 나머지는 figure 필요 여부 판단 후 SKIPPED + 이유 ↓ S5 현재 prose 확인 ↓ S6 현재 voice 확인 ↓ Command final analysis shell/CLI 없음 → SKIPPED ↓ Fact review ↓ S7 Studio import 요청이 없으므로 SKIPPED + 이유 ↓ verify-pipeline-run.py ``` 중요한 점은 **이미 한 작업을 과거 시점에 했다고 꾸미는 것이 아니라, 현재 수정 결과를 대상으로 remediation run을 실제로 수행하는 것**이다. --- # 13. 완료 조건 다음 조건을 모두 만족하면 `keycloak = 완료`로 바꿀 수 있다. - [x] Bearer JWT validation chain SVG 추가 - [x] IdP Brokering SVG 추가 - [x] 두 SVG 모두 TechViz context/spec/provenance 존재 - [x] Figure Text PASS - [x] Figure Overlap PASS - [x] Figure Provenance PASS - [x] pattern-selection 작성 지시형 문장 제거 - [x] Public / Confidential Client 반복 정의 정리 - [x] IdP Federation 장문 정리 - [x] BFF State Store 메타 진행 표현 제거 - [x] Multi-instance 선택지 기계적 리듬 정리 - [x] Public / Confidential 정의 scope 수정 - [x] Token Endpoint 제목 scope 수정 - [x] Referrer-Policy 조건 반영 - [x] Natural Prose PASS - [x] Voice PASS - [x] command pedagogy 정상 SKIP - [ ] 이번 수정 대상에 대한 current run ledger 생성 - [ ] 새 run ledger 각각 `verify-pipeline-run.py` PASS - [x] Tree / Layout / Required Content / Figure gates PASS - [x] standalone pipeline PASS - [x] full unittest PASS - [ ] source repo가 계속 없으면 최종 보고에 live source reconciliation = UNVERIFIABLE 명시 --- # 14. 최종 판정 현재 Keycloak 문서의 **내용 품질은 직전 리뷰 기준을 충족했다.** 새 SVG도 적절하고, AI 티 제거 수정도 제대로 됐으며, 기술 범위 수정도 반영됐다. 남은 것은 문서 자체를 다시 고치는 일이 아니다. **이번 수정 작업이 7단계 문서 하네스를 실제로 통과했다는 current run ledger를 남기는 일이다.** 따라서 현재 최종 상태: > **keycloak = 아직 더 봐야댐** 다음 수정에서는 문서 본문을 또 건드리지 말고, 이번 remediation에 대한 실행 원장과 검증 결과만 정확하게 닫는 것을 우선한다.