user_brief 설계·운영 (design)
user_brief 시스템 설계·운영 문서입니다. 기존 루트
HANDOFF.md의 생성/스크립트·핵심 학습·작업 방식·재실행과 폐지된PLAN.md전체를 위치만 옮긴 것(내용 보존)입니다.
생성/스크립트 파일 (현재 — M4)
- 루트 시드(git 추적):
docs_manifest.json(9엔트리 카탈로그) ·data/decisions.json(active 11건·project 필드: sara 4·global 3·user_brief 4) ·BRIEF.sara.md·BRIEF.user_brief.md(≤12,000자·build_brief.py생성·수동편집 금지) ·BRIEF.global.md(프로젝트 인덱스·아주 작음) ·CLAUDE.md(리포 지침·시드 체인) ·HANDOFF.md·PLAN.md·CODI_M4_*·CODI_M5_*·CONNECT_FROM_SARA.md(SARA 세션용 연결 가이드·미커밋). projects/sara/*.md(8) — 이동된 노션 문서 7 +memory.md.projects/user_brief/memory.md(1) — M5 신규. 본문 H1·파일명 보존.data/✅ 작업 트래커 — SARA 구축.json(89행)+.md(시드, 불변).data/user_brief.sqlite— 생성물(gitignore),tasks89행·14컬럼(+project) ·docs_pages7행·10컬럼(+project·category·html_path·seed, title=manifest 출처).scripts/validate_manifest.py(manifest ⟷projects/*/*.md1:1, 누락·빈 title·id중복 → 비0 종료) ·scripts/build_db.py(MANIFEST 기준, glob 폐기; tasks 적재 로직·COL_MAP 불변, +project; docs_pages는 memory 제외; 시작 시 validate 호출) ·scripts/render_docs.py(manifest 순회 →report/static/docs/<project>/<stem>.html, 서브트리 통째 청소, breadcrumb project-aware) ·scripts/build_brief.py(토큰0 결정형 BRIEF 조립·12,000자 게이트) ·scripts/notion_props.py(prop_val 단일 출처) ·scripts/export_notion.py(DOCS=inbox/notion_export/staging 격하·경고 주석·prop_val import 유지).scripts/rebuild_report.ps1— 단일 커맨드(-Verify로 Playwright). 순서: build_db → build_brief → copy sqlite → render_docs → npm sources → npm build → (Verify) playwright. 빌드 전.evidence·build정리.scripts/serve_report.ps1— 로컬 독립 서빙(npx serve report/build, 127.0.0.1:8788,-s금지).serve_report_hidden.vbs보조.report/— Evidence 프로젝트(git=소스만). 페이지:pages/index.md+pages/SARA/{index,tracker,docs}.md.docs.md=docs_pages동적 링크(/docs/sara/<stem>.html·WHERE project='sara'·표시 제목=docs_pages.title).index.mdiframe =/docs/sara/SARA.html.tests/verify.spec.ts(EXPECT_DOCS=7·PAGES 4). node_modules·build·.evidence·복사 sqlite·static/docs·static/data는 gitignore.inbox/— 임시물 격리(git 추적, 빌드·검증·BRIEF·render 바깥):adh_report_33·adh_report_34·CODI_M1~M3b·CODI_acceptance_verify·GPT_상의문_*(3).inbox/notion_export/만 gitignore(export staging).
핵심 학습 (재현용)
- export_notion.py는 import 시 top-level 실행 →
prop_val은notion_props.py로 분리해 import. - Evidence는 SPA + 페이지별 prerender HTML —
curl은 빈 셸. 데이터 렌더는 prerendered arrow 또는 Playwright 픽셀 검증. 로컬 서빙 =npx serve build(-s금지 — 페이지별 prerender라 SPA 폴백 시 전 페이지가 홈으로 깨짐). - Evidence는 build/
.evidenceorphan을 자동 정리하지 않음 → 페이지·문서를 삭제해도 이전 빌드분이 계속 200으로 서빙됨.rebuild_report.ps1이 빌드 전.evidence·build를 정리해야 삭제가 실제 반영(재빌드=갱신 유지). - DataTable 행수 assert: 0-size 측정 클론 + 실제 표 2개 →
table:visible로 스코프. - DataTable
<Column>색배지: core-components 5.4.2는 범주형 텍스트→색배지 없음,colorscale은 숫자 전용. → 상태는 이모지(✅/🔄/⏳) 폴백. - 완료율 표기: 분수(0~1) +
fmt="pct1"/yFmt="pct0"(Evidence가_pct접미 컬럼 자동 ×100 →7,980%버그 회피). - render_docs 가독성: markdown
toc확장→스티키 TOC(H2~3), blockquote 선두 마커(📌→info·🚨/⚠️→warning·✅→positive·상태=/결정→중립)로 콜아웃 class만 부여(원문 불변), 브레드크럼/메타. sql/plain text 펜스는normalize_fences로 안전. /SARA허브 본문 임베드: 방식①(복사)은 SARA.md 변경 자동 반영 안 됨 → 방식②(iframe/docs/SARA.html)가 재빌드=갱신·토큰 0. M3b 구현완료(854c38f). Evidence(SvelteKit) 페이지에서 iframe 자동높이 스크립트가 까다로워vh(85vh)+내부 스크롤 채택.- docs 표시 제목 = 각 .md 첫 H1(
# …), 파일명 아님(build_db·render_docs 모두 H1 우선, 없으면 stem). 표시 제목을 바꾸려면 파일명+H1 둘 다 수정.docs.md링크는docs_pages.filename을encodeURIComponent로 동적 생성(파일명 공백·한글·이모지 OK). export_notion.py의slug()은 이모지를 보존(\ / : * ? " < > | #만 제거), H1=노션 제목 → 재실행 시 로컬 이름·제목 정리가 노션 원본으로 덮어써짐. 로컬 정리 후엔 재추출=의도적 수동 재pull로만 취급.- docs 경로 참조 지점(이동 시 바꿀 상수):
build_db.py의DOCS_DIR·DOCS_ORDER,render_docs.py의DOCS_SRC,export_notion.py의DOCS,.gitignore의docs/_json/. 렌더 출력(report/static/docs/)·URL(/docs/*.html)·docs.md·iframe·verify.spec.ts는 출력 URL 유지 시 무관. - docs 정적 경로:
report/static/docs/*.html→ 빌드 시report/build/docs/, URL/docs/<filename>.html(200). 복사 docs 본문에C:\dev경로 텍스트가 있으나 빌드 기계 누수가 아닌 문서 내용. - SARA는 정적 디렉토리 서빙 인프라 없음(FastAPI 단일 페이지 + API, StaticFiles 없음, :8770) → user_brief는 독립 서빙. 외부 공유=Tailscale(대기).
- hub(
C:\dev\tools\agent-dialogue-hub, :8780): DB=cmdboard MySQL(RDS). projects 테이블GET /projects, 등록용 POST 없음(INSERT=운영 DB 쓰기, 승인 필요). user_brief는 노션 비동기라 hub 등록해도 GPT 배경 무주입(graceful). - notion2markdown 비호환 → 자체 변환 +
data_sources.query(data_source_id=...). - Windows 콘솔 cp949 → 스크립트
sys.stdout.reconfigure(encoding="utf-8"); 일회성 python은PYTHONIOENCODING=utf-8로 실행. - PowerShell 도구(MCP)는 native exe(python·npm·npx) 출력·exit code 미캡처 → 빌드·서빙·교차검증은 git-bash로 분해 실행. (
*.ps1자체는 일반 pwsh 터미널에선 정상.) - 토큰 출력·커밋 금지.
.env·.venv는 gitignore.
작업 방식 (채티 원칙 — 유지)
- 모든 작업 전
design.md(구 PLAN.md 포함)를 확인한다 — 단계별 계획·확정 전제·위험작업의 단일 출처. (handoff=현재상태 시드, design=계획 원천.) - 한국어 존댓말, 짧게 3단계 보고(무엇을 / 검증 / 다음). 완료 시 검증 여부 명시, 못 한 건 "확인하지 못했습니다".
- think-first · 최소 해결책 · 범위 좁힘 · 검증 가능한 목표.
- 위험작업(삭제·대량변경·운영배포·권한변경·push·DB변경·외부 노출 등)은 사용자 승인 후. broker(
:7777)가 Bash/Write/Edit 게이트. - 채티=PLANNER(운영 읽기전용). 코디가 구현·커밋(단, user_brief 리포 내 소규모 작업은 채티 직접 + 검증 가능). 기본 수동 디스패치: 채티
.md지시문 → Pepe가 코디 실행. 최종 완료 기조: 지시문에 명시 시 코디가 검증 통과 후 로컬 커밋까지(push 제외). - 시크릿 마스킹. 장문은
.md.
재실행
# 데이터 추출(노션 재접속 — 필요시만). M4: 출력이 inbox/notion_export/ staging이라 live projects/는 안전.
# 승격(staging→projects/)은 수동. 트래커 JSON(data/)은 여전히 갱신되므로 신중히.
C:\dev\user_brief\.venv\Scripts\python.exe C:\dev\user_brief\scripts\export_notion.py
# SQLite 적재(로컬, 멱등 — tasks+project / docs_pages, 시작 시 manifest 검증). 단독 검증: validate_manifest.py
C:\dev\user_brief\.venv\Scripts\python.exe C:\dev\user_brief\scripts\build_db.py
# 리포트 재빌드(단일 커맨드; build_db→build_brief→copy→render_docs→sources→build; -Verify로 Playwright)
powershell -ExecutionPolicy Bypass -File C:\dev\user_brief\scripts\rebuild_report.ps1 -Verify
# 로컬 서빙(독립·정적·SARA 무관; http://127.0.0.1:8788)
powershell -ExecutionPolicy Bypass -File C:\dev\user_brief\scripts\serve_report.ps1
구현 계획 (구 PLAN.md)
아래는 폐지된 루트
PLAN.md전체를 위치만 옮긴 것입니다(본문 보존, 헤딩만 한 단계 낮춤).
user_brief 구현 계획 (v7 · 멀티프로젝트 + user_brief 프로젝트 편입 완료)
목적: SARA 노션 콘텐츠(로컬 파일)를 생성형(비-LLM) 정적 HTML 읽기전용 리포트로 변환. 재빌드=갱신=토큰 0. 기준일: 2026-06-03 · 시드:
C:\dev\user_brief\HANDOFF.md· 합의: agent-dialogue-hub report#1, feedback#4 v1→v2:prop_val분리 · 영문 alias 스키마 · SQLite 복사 파이프라인 · 마일스톤 분리(M1/M2/S6) 반영. v2→v3: M2 구현 완료 반영 — S4 페이지 5종(index/tracker/charts/roadmap/pages) 확정 ·docs_pages테이블+정적 복사(report/static/docs/) ·scripts/rebuild_report.ps1(-Verify) · Playwright(Node@playwright/test) 검증 셋업. v3→v4: S6 재정의 — SARA 비종속 독립 서빙. 로컬 1차 =scripts/serve_report.ps1(npx serve report/build, 127.0.0.1:8788, 정적·토큰 0). 외부 공유(Tailscale)=대기 항목. SARA는 정적 디렉토리 서빙 인프라(StaticFiles)가 없어 끼우지 않음(분리 부담 회피). v4→v5: 멀티프로젝트 전환 계획 추가(§13). 합의 #34(에이전트 시드/메모리: sidecar manifest·토큰0 BRIEF·decisions.json) + #35(멀티프로젝트·6분류·inbox)를 통합한 8단계 마이그레이션 + 코디 지시문(CODI_M4_multiproject_seed.md) 계획. v5→v6: M4 구현 완료. 8단계 전부 단계별 검증 통과(projects/sara/이동·docs_manifest.json카탈로그·URL 네임스페이스·tasks.project·decisions.json·토큰0BRIEF.*·inbox/·export_notionstaging).rebuild_report.ps1 -VerifyPlaywright 8/8. 로컬 커밋(push 없음). §13에 구현 결과 반영.
0. 목적 / 범위
- 목적: SARA 노션 콘텐츠(로컬 파일)를 생성형(비-LLM) 정적 HTML 읽기전용 리포트로 변환. 재빌드=갱신=토큰 0.
- 범위: 추출(완료) → SQLite 적재 → Evidence 빌드 → 정적 HTML 서빙. 우선 리포트 1개.
- 비범위: 노션 양방향 동기화, 쓰기/편집 UI, RDS, 인증/권한 시스템.
1. 현재 기준 (완료된 것 — 사실 확인 완료)
- 리포
C:\dev\user_brief: git 커밋 2개, 원격 없음. 미커밋: HANDOFF.md·PLAN.md(신규), login_bug_fix_card.md(삭제). docs/노션 페이지 8개(.md) ·data/✅ 작업 트래커 — SARA 구축.json(89행) + 동명.md테이블.scripts/export_notion.py(멱등) — 노션 → 로컬. 내부prop_val()= Notion property 평탄화(title/rich_text/select/status/multi_select/number/checkbox/date/people/url).- 주의: import 시 top-level 실행(load_dotenv·Client(auth)·walk·export 루프).
from export_notion import ...금지. .venv= Python3(notion-client, python-dotenv). Node v24/npm 11 설치됨. Evidence 미설치.- 트래커 JSON: Notion 페이지 객체 배열. 각 행
id·last_edited_time·url+properties{}(우선순위·상태·담당·Phase·작업(title)·그룹1·그룹2·비고). - Phase 값:
Phase 0~Phase 3+ 빈값 3건(select null).
2. 확정 전제 (재논의 금지)
- 저장소 = 로컬 SQLite.
data/*.json이 시드. 노션 재접속 없음, 로컬이 진실 원천. - HTML 생성기 = Evidence(Node) 단독 (A안 확정). 정적 빌드, 재빌드=갱신.
- 트래커 필터/정렬은 Evidence DataTable(검색·정렬) + 드롭다운 필터(DuckDB-WASM, 클라이언트 동적 재쿼리)로 충족.
- 조합(Datasette 병행)은 향후 옵션으로만 보류 — SQLite 공유 구조라 나중 추가 가능.
- 기존 추출 산출물
docs/·data/는 불변.export_notion.py는prop_val분리 리팩터만 수행하며 출력 결과는 동일해야 한다. 생성 SQLite 내부 테이블만 재생성하며, 외부/운영 DB DROP은 없다.
3. 파이프라인 개요
[노션] --(S1 완료)--> docs/*.md + data/트래커.json
|
(S2a) build_db.py [prop_val ← notion_props.py]
v
data/user_brief.sqlite (tasks 89행, 영문 alias)
|
빌드 직전 복사: data/user_brief.sqlite
→ report/sources/user_brief/user_brief.sqlite
v
(S3a) Evidence 프로젝트 + sqlite 소스 + DataTable 1개 ← M1 끝
|
(S4) docs_pages·차트·로드맵·docs 링크 ← M2
v
(S5) npm run build → build/ 정적 HTML
|
v
(S6) SARA 서빙 ← 별도 승인
각 단계는 새 파일·디렉토리만 추가(또는 export_notion의 prop_val 분리 리팩터 1건)하므로 격리 롤백 가능.
4. 단계별 상세 (입력 / 작업 / 출력 / 검증기준 / 되돌리기)
S1. 추출 — ✅ 완료
- 출력:
docs/*.md(8) +data/트래커.json(89) +.md. 검증:pages ok=8 fail=0,rows=89(달성됨).
S2a. SQLite 적재 (tasks) — M1
- 입력:
data/✅ 작업 트래커 — SARA 구축.json(경로는build_db.py상단 상수 블록에). - 작업: 신규
scripts/notion_props.py(공용prop_val) +scripts/build_db.py. - 각 행
properties를notion_props.prop_val로 평탄화. - 영문 alias 스키마 (매핑 dict 한 곳):
python COL_MAP = {"작업":"task","Phase":"phase","담당":"owner","상태":"status", "우선순위":"priority","그룹1":"group1","그룹2":"group2","비고":"note"} - 테이블
tasks컬럼(13):id, task, phase, owner, status, priority, group1, group2, note, last_edited_time, notion_url, phase_order, row_no.id=행 id,last_edited_time=행 last_edited_time,notion_url=행 url.phase_order=phase에서 정규식\d+추출(int), 빈값 → NULL.row_no=입력 순서 인덱스(0-base).
- 멱등: 매 실행
DROP TABLE IF EXISTS tasks후 재생성 (격리된user_brief.sqlite내부 한정). - 출력:
data/user_brief.sqlite(tasks 89행). - 검증기준:
SELECT COUNT(*) FROM tasks== 89COUNT(DISTINCT id) == COUNT(*)- 빈
task0건 statusdistinct ⊆ {대기, 진행중, 완료, 보류}phase_order:Phase 0~3행은 0~3, 빈 Phase 3건은 NULL- 영문 컬럼 13개 존재
- 되돌리기:
user_brief.sqlite삭제(원본 JSON 불변).
S3a. Evidence DB연결 + DataTable 1개 — M1
- 입력:
data/user_brief.sqlite. - 작업:
- Node 설치 확인(설치됨) →
report/에 Evidence 프로젝트 생성. npm install @evidence-dev/sqlite.- 빌드 직전
data/user_brief.sqlite→report/sources/user_brief/user_brief.sqlite복사(절대경로/심볼릭링크 금지). report/sources/user_brief/connection.yaml:type: sqlite,filename은 sources 기준 상대경로.- 페이지 1개:
SELECT * FROM tasks→<DataTable>1개만. - 출력:
report/Evidence 프로젝트. - 검증기준:
npm run sources성공(연결 + 테스트 쿼리)npm run dev에서 tasks DataTable 89행 렌더- (선택)
npm run build성공 시report/build/index.html존재 + 산출물에C:\dev\절대경로 잔존 0건 - 되돌리기:
report/삭제. - 실측 기록(빌드 후): Evidence 캐시 디렉터리 실제명, static asset 경로 →
.gitignore정정.
S4. 페이지 구성 — M2 ✅ 완료
페이지 5종(report/pages/):
- index.md: BigValue(총 89·완료·진행중·대기·완료율) + 상태 분포 막대 + Phase별 완료율 막대.
- tracker.md: 풀 <DataTable>(검색·정렬, rows=100로 89행 전수 표시) + 드롭다운 필터(상태·Phase·담당·그룹1). DuckDB-WASM 클라이언트 필터 — "전체"(LIKE '%')가 기본값.
- charts.md: 상태 도넛(ECharts) + Phase·담당·우선순위 막대.
- roadmap.md: Phase×상태 매트릭스(조건부 집계, 빈 Phase='' → '미지정') + Phase별 완료율 BigValue({#each}).
- pages.md: docs_pages 목록 + 원본 .md 정적 링크(/docs/<filename>, rel="external").
- docs_pages 테이블(build_db.py): docs/*.md → title/filename/rel_path/size/mtime(8행). 소스: report/sources/user_brief/docs_pages.sql.
- docs 정적 복사: docs/*.md → report/static/docs/(생성물·gitignore). 빌드 시 report/build/docs/로 서빙.
- 검증: 각 페이지 무에러 렌더(Playwright), 상태/Phase/담당/그룹 드롭다운 필터 동작, 상태별·Phase별 건수 합 == 89.
S5. 정적 빌드 + 검증 — M2 ✅ 완료
npm run build→report/build/정적 HTML. 검증: build 성공,build/index.html+tracker|charts|roadmap|pages/index.html생성, 절대경로(C:\dev) 빌드 산출물 잔존 0건(복사 docs 본문 텍스트 제외).- Playwright 검증(
report/tests/verify.spec.ts+playwright.config.ts): build를npx serve build로 정적 서빙 후 chromium 헤드리스 접속. tracker 89행 assert, 페이지별 스크린샷(report/tests/screenshots/), index/charts/roadmap 핵심 요소·docs 링크 200 검증. 검증 주체=코디, 교차검증=채티. 7/7 통과. - 주의: Evidence DataTable은 0-size 측정용 클론+실제 표 2개를 렌더 → 행수 assert는
table:visible로 스코프. SPA 라우팅이므로serve는-s없이(페이지별 prerender HTML 서빙). - 갱신: 데이터 변경 시 S2a→S5 재실행, LLM 토큰 0.
S6. 서빙 — 독립 (SARA 비종속)
- 결정: SARA에 mount하지 않는다.
report/build는 정적 HTML 묶음이라 SARA 코드·DB와 무관하므로 독립 서빙한다. (SARA는 FastAPI 단일 페이지/+ API 구조로 정적 디렉토리 서빙 인프라(StaticFiles)가 없어, 끼우면 추후 분리 부담만 늘어남. 이 리포트는 전체 프로젝트 관리 + 동료 공유 후보라 독립성이 우선.) - 로컬 (✅ 완료):
scripts/serve_report.ps1=npx serve report/build -l tcp://127.0.0.1:8788. Evidence는 페이지별 prerender라-s(SPA 폴백) 미사용. 빌드/갱신은rebuild_report.ps1(별도), 이 스크립트는 서빙만. 검증: 로컬 6페이지(index/tracker/charts/roadmap/pages/docs) HTTP 200 + 127.0.0.1 바인드. - 외부 공유 (⬜ 대기): Tailscale로 구축 예정 — 다른 직원 공유용. 지금 작업 없음, 대기 항목. 정적 산출물이라 바인드/호스팅만 바꾸면 되고 SARA 분리 부담이 없다. (노출 범위 확대 단계라 착수 시 별도 승인.)
- 되돌리기:
serve_report.ps1삭제(서빙 프로세스만 종료, build·소스 불변).
5. 갱신 파이프라인 (단일 커맨드 — M2 ✅ 완료)
scripts/rebuild_report.ps11커맨드(순서):build_db.py → copy sqlite(report/sources/user_brief/) → copy docs(report/static/docs/) →npm run sources→npm run build``.-Verify플래그: 빌드 후npx playwright test(검증)까지 실행.- 리포명/경로는 스크립트 상단 CONFIG 변수 블록으로(다른 리포 복제 시 그 블록만 교체). 복사만(절대경로·심링크 금지). watch(자동 재빌드)는 후순위.
- 서빙은 별도:
scripts/serve_report.ps1(로컬 정적 서빙,npx serve report/build, 127.0.0.1:8788). 빌드(rebuild)와 책임 분리.
6. 목표 디렉토리 구조
C:\dev\user_brief\
docs/ # (기존) 노션 페이지 8 .md
data/
✅ 작업 트래커 ….json # (기존) 시드
✅ 작업 트래커 ….md
user_brief.sqlite # (신규 S2a)
scripts/
export_notion.py # (기존, prop_val 분리 리팩터)
notion_props.py # (신규 S2a) 공용 prop_val
build_db.py # (신규 S2a)
rebuild_report.ps1 # (신규 M2)
report/ # (신규 S3a~S5) Evidence 프로젝트
sources/user_brief/
pages/
build/ # (신규 S5) 정적 산출물
HANDOFF.md / PLAN.md
7. .gitignore (보완 항목)
node_modules/
report/build/
report/.evidence/ # 캐시 실제명은 S3a 빌드 후 정정
report/sources/**/*.sqlite
data/*.sqlite
*.log
8. 마일스톤 분리
- M1 ✅ 완료(커밋
5c0bb06) = S2a(tasks 적재) + S3a(Evidence DB연결 + DataTable 1개). - M2 ✅ 완료(커밋 대기) =
docs_pages· 페이지 5종 · 차트 · 로드맵 매트릭스 · docs 정적 링크 +rebuild_report.ps1(-Verify) + Playwright 검증(7/7). - S6 (독립 서빙) = 로컬 완료(
scripts/serve_report.ps1, 127.0.0.1:8788). 외부 공유(Tailscale)=대기. - M3·M3b ✅ 완료(
42efb77·854c38f) = IA 노션 미러링 +/SARA허브 iframe. - M4 ✅ 완료 = 멀티프로젝트 전환(8단계, §13).
projects/sara/·docs_manifest.json·URL 네임스페이스·tasks.project·decisions.json·토큰0BRIEF.*·inbox/·export_notionstaging. Playwright 8/8. (§6의 단일-docs/구조도는 §13 구조로 대체됨.) - M5 ✅ 완료(지시문
CODI_M5_user_brief_project.md) =user_brief2번째 프로젝트 편입(SARA와 동일 패턴).projects/user_brief/memory.md+ manifestub-memory+ decisions 4 +BRIEF.user_brief.md. tasks-0/docs_pages-0 memory 단독 프로젝트 견고성:build_brief.py최소 방어 2곳(# per CODI_M5). SARA 불변(tasks 89·docs_pages 7). Playwright 8/8. → 이후 추가 프로젝트는 이 패턴(memory + manifest 엔트리 + decisions) 반복.
9. 구조 원칙 (추후 다른 리포 HTML 브리핑 확장 대비)
추후 다른 리포도 "데이터/JSON → SQLite → Evidence 정적 HTML" 대상. 지금 범용 프레임워크/공통 라이브러리 만들지 않는다(과한 추상화 금지). 대신:
- 리포 특화 값(리포명·입력 경로·
COL_MAP·출력 SQLite명)은build_db.py상단 한 블록에 상수로 모은다. - 디렉토리 패턴을 리포 간 동일하게:
<repo>/data/*.sqlite,<repo>/scripts/build_db.py,<repo>/scripts/notion_props.py,<repo>/report/. 다른 리포는 이 골격을 복제해 상단 상수만 변경. notion_props.py는 리포 독립적(특정 리포 값 하드코딩 금지) — 추후 공용 모듈 후보.rebuild_report.ps1(M2)도 리포명/경로를 상단 변수로.
→ 목표는 "복제로 확장 가능한 단순 골격". 공통화·플러그인화는 리포 2~3개 경험 후 별도 판단.
10. 위험 작업 (별도 승인 필요)
- npm 패키지 설치: 네트워크 + 다수 의존성(규모상 명시).
- git 커밋/원격 push (
delix0731/user_brief, 비공개): 별도 승인. 이번 세션 범위 아님. - 외부 노출(S6 외부 단계): Tailscale 등 외부 공유로 노출 범위 확대 시 → 착수 시 별도 승인. (로컬 127.0.0.1 서빙은 위험 낮음. SARA 비종속이라 SARA 운영 영향 없음.)
- 삭제/운영배포/외부 DB DROP: 없음. (S2a의 테이블 재생성은 격리된
user_brief.sqlite한정.)
11. 미결정 / 해소된 질문
- ✅ Q1 로드맵 형태 → Phase×상태 매트릭스 + Phase별 완료율 BigValue (칸반·간트 제외).
- ✅ Q2 docs 처리 → 목록 + 원본 .md 링크 (본문 통합 후순위).
- ✅ Q3 SQLite 위치 → 원본
data/, 빌드 직전report/sources/user_brief/로 복사(절대경로·심링크 금지). - ✅ Q5 갱신 트리거 → 단일 커맨드
scripts/rebuild_report.ps1(M2). watch 후순위. - ✅ Q4 서빙(S6): SARA 비종속 독립 서빙. 로컬 =
scripts/serve_report.ps1(완료). 외부 공유 = Tailscale(대기).
12. 성공 기준
prop_val이notion_props.py로 분리되고export_notion출력 동일.data/user_brief.sqlite의tasks89행이 검증 기준 전부 통과.- Evidence가 그 SQLite를 읽어 DataTable 1개를 dev에서 렌더.
.gitignore가 생성물·node_modules·build를 제외.
13. 멀티프로젝트 전환 (합의 #34 + #35) — 8단계 마이그레이션 + 코디 지시문 계획
상태: 구현 완료(8단계 + 마무리, 로컬 검증 통과·로컬 커밋
8d88e49·push 없음). 이 절이 마이그레이션의 단일 계획 출처. 코디 지시문 =CODI_M4_multiproject_seed.md(이 절을 그대로 구현). 실측 결과: docs_pages 7·tasks 89(+project)·BRIEF.sara.md 8,494자(≤12,000)·Playwright 8/8. 근거:adh_report_34.md(#34) ·협의 결과 #35(inbox/멀티프로젝트) ·GPT_상의문_*.
13.1 배경·확정 (재논의 금지)
- 1순위 재정의: 사람 대시보드가 아니라 에이전트용 메모리/시드(컨텍스트 한계 극복·매 대화 토픽 자동 복원). SARA + user_brief = 최소 2개 프로젝트 → 멀티프로젝트 구조 필수.
- 저장층(#34): sidecar manifest(
docs_manifest.json, frontmatter 기각). 본문 H1 미치환(표시 제목은 manifest title). frontmatter·RAG·대량 rename 보류. - 출력(#34):
BRIEF.<project>.md자동조립(토큰0 결정형, LLM 없음) + 상한 게이트(12,000자 초과 시 빌드 실패). 결정 로그data/decisions.json(active만). - 구조(#35):
projects/<P>/도입, 기존 SARA 문서 7개는 이동만(파일명·H1 보존). 단일 manifest + glob 폐기(문서 처리는 manifest 기준, 누락 시 빌드 실패). URL 네임스페이스/docs/<project>/<stem>.html. - 6분류(category): index·design·handoff·archive·memory(문서 5종) + tasks(SQLite 데이터).
- 트래커: 단일
tasks테이블 +project컬럼. group1/2는 프로젝트 내부 분류로 유지(대체 아님). - 임시 파일:
inbox/(manifest·검증·BRIEF·docs_pages·렌더 전부 바깥). 승격 수동. - export_notion: live 폴더 덮어쓰기 금지 →
inbox/notion_export/staging 전용. - 불변(기존): Evidence 정적·읽기전용·로컬 SQLite 시드, build_db 멱등, 노션 로컬=진실원천, 위험작업 승인 게이트·원격 없음(push 보류), 과한 추상화 금지.
13.2 SARA 문서 분류·식별자 매핑 (확정 — 이번 마이그레이션 적용)
이동만(파일명·H1 보존). manifest title이 표시명(이모지 제거), id 전역 유일(<project>-<slug>).
| order | 현재 파일(보존) | id | category | title(표시) | seed |
|---|---|---|---|---|---|
| 1 | SARA.md | sara-hub | index | SARA | true |
| 2 | 🗂️ 세부 상의 — SARA 시스템 설계.md | sara-design-system | design | SARA 시스템 설계 | false |
| 3 | 📦 SARA 통합 인수인계서 (최신·단일 시드).md | sara-handoff | handoff | SARA 통합 인수인계서 | true |
| 4 | 🗄️ 인수인계서 이력 아카이브.md | sara-archive | archive | 인수인계서 이력 아카이브 | false |
| 5 | 🚨 [긴급·1순위] 멀티에이전트 통합 아키텍처 — 세부 상의 (cmdboard 자원 참조).md | sara-multiagent | design | 멀티에이전트 통합 아키텍처 | false |
| 6 | 협의 결과 — (다) CLI 러너 설계 확정 (hub #28, 2026-06-01).md | sara-cli-runner | design | CLI 러너 설계 확정 | false |
| 7 | 🔍 EVALUATOR 웹페이지 실사용 평가 — 설계 제안.md | sara-evaluator | design | EVALUATOR 웹페이지 평가 | false |
| 8 | memory.md (신규 작성) | sara-memory | memory | 프로젝트 메모리 | true |
- SARA.md = index(허브·iframe 대상). 별도 index.md 만들지 않음(중복 회피). 전 프로젝트 목차는 글로벌 인덱스(
BRIEF.global.md)가 담당. - seed 규칙(BRIEF 포함): handoff=풀, memory=포함, index=목표+포인터, design=seed:true만 excerpt, archive=포인터만.
- topics는 초기 빈 배열(
[]) — 필요 시 후속 보강(대량 rename 보류와 정합).
13.3 8단계 마이그레이션 상세 (각 단계 후 검증 — 코디 지시문 = 이 순서)
① manifest 스키마: 루트 docs_manifest.json 생성. 기존 docs/_order.json(7) → manifest로 흡수(필드 id·project·filename·category·order·title·topics·seed). SARA 8행(기존 7 + memory). 검증 함수(scripts/validate_manifest.py 또는 build_db 내): projects/*/*.md ⟷ manifest 1:1, 누락·title 공백 → 실패.
② 이동: projects/sara/ 생성, git mv docs/*.md(7) → 파일명 보존. docs/_order.json 제거(manifest로 대체). projects/sara/memory.md 신규(스타터). data/ 불변.
③ build_db·render_docs manifest 전환 + URL 네임스페이스:
- build_db: DOCS_DIR/DOCS_ORDER glob → manifest 기준. docs_pages 스키마 확장(+project·category·rel_path·html_path), title=manifest 출처(H1 아님), sort_order=manifest order, +seed. 누락 시 빌드 실패. tasks 로직 이 단계 불변.
- render_docs: DOCS_SRC → manifest 기준 projects/<P>/<filename>. 출력 report/static/docs/<project>/<stem>.html. stale HTML 청소 범위 확장(하위 폴더 통째 재생성). breadcrumb 프로젝트 인지.
- Evidence: pages/SARA/docs.md 링크 /docs/sara/<stem>.html·WHERE project='sara'. pages/SARA/index.md iframe /docs/sara/SARA.html. verify.spec.ts URL·iframe 갱신(EXPECT_DOCS=7 유지). rebuild_report.ps1 청소 범위·render 호출 정합.
④ tasks.project + 백필: build_db에서 tasks에 project 컬럼 추가, 기존 89행 기본값 'sara'. COL_MAP/적재 로직 외 불변. group1/2 유지.
⑤ decisions.json 통합: data/decisions.json 생성(active만, 필드 id·project·status·title·decision·source). 시드 = HANDOFF 확정결정 + #34/#35 핵심. 글로벌은 project:"global". build_brief가 읽음(UI 추가 없음).
⑥ BRIEF.scripts/build_brief.py(토큰0 결정형). manifest category 포함규칙 + tasks 롤업 + decisions로 BRIEF.sara.md 조립. 12,000자 초과 시 빌드 실패. BRIEF.global.md = 프로젝트명·한줄목표·active만(아주 작게). rebuild_report.ps1에 build_brief 단계 추가.
⑦ inbox + validator 경로 좁히기: inbox/ 생성, 루트 임시물(adh_report_*·CODI_M1~M3b·GPT_상의문_*) 이동(삭제 아님). validator는 projects/*/*.md만 검사, inbox 완전 제외. .gitignore 정합(inbox 추적 유지·빌드 제외). docs_pages·BRIEF·render에 inbox 비노출 보장.
⑧ export_notion staging 격하: export_notion.py의 DOCS 출력 → inbox/notion_export/만. live(projects/) 덮어쓰기 금지·경고 주석. 이번 작업서 실행 안 함(코드 변경만).
마무리(검증·문서·시드체인): 전체 rebuild_report.ps1 -Verify(Playwright 전부 통과)·시크릿 누수 0. HANDOFF·PLAN을 "구현 완료"로 갱신. #34 시드 체인 마감: CLAUDE.md/PROMPT_SNIPPET.md(글로벌 시작 관례 — 새 대화: HANDOFF→PLAN→BRIEF.global→해당 BRIEF.
13.4 코디 지시문 계획
- 형식: 단일 묶음
.md1개(CODI_M4_multiproject_seed.md). 8단계가 순차 의존(③은 ①·②에, ⑦은 ③의 manifest 기준 전환에 의존)이라 한 파일이 컨텍스트 단절 없이 효율적(채티 원칙: 확정 변경=큰 묶음 1회 위임). - 분리 승인: 8단계는 전부 git 추적·로컬·되돌리기 가능 → 별도 승인 불요. 단 push 제외(원격 없음·사용자 보류). DB 변경은 격리 sqlite 재생성 한정(운영 DB 아님).
- 각 단계 구조(템플릿): 목적 / 현재 기준 / 작업 범위 / 금지사항 / 진행 방법 / 검증 방법 / 완료 보고 / 되돌리기. 단계마다 검증 게이트 — 실패 시 그 단계에서 정지·보고.
- 공통 금지: 요청 외 파일 수정 금지 · 기존 코드 스타일 유지 · 본문 H1/파일명 변경 금지(이동만) · tasks 적재 로직 변경 금지(③④ 외) · 시크릿 출력/커밋 금지 · push 금지 · 노션 재추출(
export_notion.py) 실행 금지. - 검증 주체: 코디 자체 검증 통과 후 단계별 보고 → 전체 완료 시 채티 독립 교차검증(M1~M3b 방식: git 상태·counts·diff·산출물 정합·시크릿 0).
- 완료 기조: 코디가 검증 통과 후 로컬 커밋까지(push 제외). 최종 HANDOFF/PLAN 갱신 포함.