Files
document-haness/docs/clean-architecture-backend-template/final/evidence/meta/a19-f006-messaging-cloudevents.json
T
DongHyeonkaandClaude Opus 5 b2963105a8 docs(keycloak-session-store): import the session-storage lab as a new project
The keycloak project ended with four open questions that design could not
settle. A two-VM lab was built to answer them by measurement, and this is
that material: 26 experiments, 125 raw command outputs, 22 browser captures.

Follows the import procedure in README.md.

  source/     the originating repository verbatim — 78 documents, 28 SVGs,
              8 manifests, plus .source-revision recording the commit
  final/      the SSOT
    document.md   729 lines written from the 29 experiment documents, not
                  concatenated: what was predicted, what was measured, and
                  where the measurement itself was wrong
    evidence/raw    125 outputs, flattened to <experiment>__<file> because
                    the originals collided (01-baseline.txt appeared three
                    times) and the audit only globs the top level
    evidence/meta   one per raw file; command and exitCode are null and the
                    README says why rather than inventing them
    evidence/browser  22 captures
    assets/       three diagrams through techviz
    .techviz/     their VizSpecs

A separate project rather than an addition to keycloak: the B-layer answers
that project's four questions, but the A, C and D layers are about cluster
failure, SSO and operations, and one document.md should hold one subject.
The four question records there can point here through 관계.

Recorded rather than papered over: only three of the 28 diagrams were
remade. The repository forbids hand-drawn SVG and forbids titles inside the
canvas; all 28 originals carry both, so converting them is redrawing, not
reformatting. They stay in source/ and the gap is written into the document.

verify-pipeline.py passes. audit-records.py reports no issues.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-04 22:51:59 +09:00

15 lines
5.2 KiB
JSON

{
"assetKey": "a19-f006-messaging-cloudevents",
"kind": "terminal",
"command": "set -e\nset -o pipefail\nL=src/messaging/messaging-cloudevents\nstrip() { sed -E 's#^src/[^:]*/src/(main|test)/[^:]*/([^:/]+):([0-9]+):# \\1 · \\2:\\3 #'; }\n\necho \"# 이 leaf 가 담은 파일과 줄 수\"\nfor f in $(find $L/src -name '*.java' | sort); do\n set=$(echo \"$f\" | sed -E 's#.*/src/([a-z]+)/.*#\\1#')\n printf \" %-8s %-32s %s 줄\\n\" \"$set\" \"$(basename $f)\" \"$(wc -l < $f)\"\ndone\n\necho\necho \"# 출하 산출물에 들어간다는 것을 무엇이 말하는가\"\npython3 - <<'PY'\nimport json\nd = json.load(open('src/config/architecture/modules.json'))\ndef walk(o):\n if isinstance(o, dict):\n if o.get('id') == 'messaging-cloudevents':\n print(f\" modules.json runtime_memberships={o.get('runtime_memberships')}\")\n for v in o.values(): walk(v)\n elif isinstance(o, list):\n for v in o: walk(v)\nwalk(d)\nPY\nawk 'NR>=24 && NR<=26 {printf \" messaging-spring-boot-starter/build.gradle:%d %s\\n\", NR, $0}' src/messaging/messaging-spring-boot-starter/build.gradle\ngrep -n 'messaging-cloudevents' src/app-bootstrap/build/architecture/runtime-project-closure.txt 2>/dev/null \\\n | sed 's#^# app-bootstrap/build/architecture/runtime-project-closure.txt:#' || echo \" (closure 파일 없음)\"\ngrep -n 'io.cloudevents' src/app-bootstrap/gradle.lockfile | sed 's#^# app-bootstrap/gradle.lockfile:#'\n\necho\necho \"# DefaultCloudEventMapper 를 만드는 자리, 그리고 계약 타입을 참조하는 main 파일\"\ngit grep -n 'new DefaultCloudEventMapper' -- 'src/**/*.java' | strip\ngit grep -l 'CloudEventMapper\\|CloudEventExtensions' -- 'src/**/*.java' | grep '/main/' | sed 's#^src/# #'\n\necho\necho \"# CloudEvent 라는 이름을 main 자바 소스 전체에서 찾으면\"\ngit grep -l 'CloudEvent' -- 'src/**/*.java' | grep '/main/' | sed 's#^src/# #'\necho \" 설정 클래스 계수 :\"\na=$(find src -name '*AutoConfiguration.java' -path '*/main/*' | wc -l || true)\nc=$(git grep -l '@Configuration' -- 'src/**/*.java' | grep -c '/main/' || true)\ni=$(find src -name 'org.springframework.boot.autoconfigure.AutoConfiguration.imports' -not -path '*/build/*' -exec grep -ch . {} + | awk '{s+=$1} END {print s}')\necho \" 이름이 *AutoConfiguration.java 인 main 클래스 : $a\"\necho \" @Configuration 을 단 main 클래스 : $c\"\necho \" AutoConfiguration.imports 등재 클래스 : $i\"\necho \" 그 어느 집합에서도 CloudEvent 를 언급하는 것 : 0 (위 main 전수 목록이 leaf 세 파일뿐이므로)\"\necho \" META-INF/services 파일 수 : $(find src -path '*/META-INF/services/*' -not -path '*/build/*' | wc -l || true)\"\n\necho\necho \"# 원문이 28 로 적은 수의 출처\"\necho -n \" starter autoconfigure 패키지 파일 수 : \"\nls src/messaging/messaging-spring-boot-starter/src/main/java/dev/caskeleton/messaging/autoconfigure/ | wc -l\necho -n \" 그중 이름이 *AutoConfiguration 인 것 : \"\nls src/messaging/messaging-spring-boot-starter/src/main/java/dev/caskeleton/messaging/autoconfigure/ | grep -c AutoConfiguration || true\n\necho\necho \"# 매핑의 반대편 — CanonicalEnvelopeHeaders 를 쓰는 main 코드와 그 성격\"\ngit grep -n 'CanonicalEnvelopeHeaders\\.' -- 'src/**/*.java' | grep '/main/' | strip\necho \" 그 넷은 값을 싣는 곳이 아니라 거절·건너뛰기 판정이다 :\"\nawk 'NR>=88 && NR<=92 {printf \" KafkaHeaderMapper.java:%d %s\\n\", NR, $0}' src/messaging/messaging-kafka/src/main/java/dev/caskeleton/messaging/kafka/KafkaHeaderMapper.java\necho \" 실제로 헤더를 싣는 줄은 따로 있다 :\"\nawk 'NR>=36 && NR<=44 && /put\\(headers/ {printf \" KafkaHeaderMapper.java:%d %s\\n\", NR, $0}' src/messaging/messaging-kafka/src/main/java/dev/caskeleton/messaging/kafka/KafkaHeaderMapper.java\n\necho\necho \"# 그 네 호출 중 조립되는 경로에 있는 것\"\ngit grep -n 'new KafkaHeaderMapper()\\|new RabbitHeaderMapper()' -- 'src/**/*.java' | grep -E '/(main|test)/' | strip\necho \" 그 위의 transport 를 만드는 main 코드 :\"\nfor t in KafkaMessagingTransport RabbitMessagingTransport; do\n h=$(git grep -n \"$t\" -- 'src/**/*.java' | grep '/main/' | grep -v \"/$t.java\" | grep 'new ' || true)\n if [ -z \"$h\" ]; then echo \" $t : main 생성 0 건\"; else echo \"$h\" | strip; fi\ndone\n\necho\necho \"# 상호운용을 약속한 문서와, 약속이 없는 문서\"\ngrep -rn 'CloudEvents' docs/superpowers/specs/2026-08-10-messaging-platform-design.md 2>/dev/null | head -2 | cut -c1-140 | sed 's#^# #'\nfor f in docs/messaging/support-matrix.md docs/messaging/configuration-reference.md; do\n n=$(grep -ci 'cloudevent' $f 2>/dev/null || true)\n printf \" %-46s CloudEvents 언급 %s 건\\n\" \"$f\" \"${n:-0}\"\ndone\n",
"cwd": "/shared/codebase/clean-architecture-backend-template",
"exitCode": 0,
"executedAt": "2026-09-04T00:26:36+00:00",
"sourceRevision": "21234e38cdb9a926cbc92bb97a2aee2e4a7d2916",
"raw": "evidence/raw/a19-f006-messaging-cloudevents.txt",
"svg": "evidence/rendered/a19-f006-messaging-cloudevents.svg",
"rawSha256": "8eaac0b663944898eed36a10762676c52ed416d04e2d46607262776b46b5c6e0",
"lines": 75,
"redaction": "코드베이스 측정으로 교체"
}