131 lines
6.1 KiB
Markdown
131 lines
6.1 KiB
Markdown
# Architecture
|
|
|
|
## 1. 설계 목표
|
|
|
|
ClariDoc의 핵심 목표는 생성 모델의 문장 능력보다 **정보 구조, 근거 추적, 검토 독립성, 재현 가능한 품질 판정**을 상위 제어 계층에 두는 것이다.
|
|
|
|
설계 원칙:
|
|
|
|
1. **Contract before prose**: 초안보다 브리프와 문서 유형 계약을 먼저 검증한다.
|
|
2. **Reader-question chain**: 각 절은 하나의 독자 질문에 답한다.
|
|
3. **Deterministic minimums**: 모델이 놓치기 쉬운 형식·안전·인용 조건은 코드로 검사한다.
|
|
4. **Role separation**: 작성자와 리뷰 관점을 분리한다.
|
|
5. **Evidence boundary**: 출처의 사실과 모델의 설명·추천을 구분한다.
|
|
6. **Auditability**: 원문 응답, 정규화 입력, 결과, 이벤트, 해시를 보존한다.
|
|
7. **Safe degradation**: planner가 실패하면 결정적 구조로 폴백하지만 writer 실패는 숨기지 않는다.
|
|
|
|
## 2. 구성요소
|
|
|
|
```text
|
|
models.py 입력/출력 계약과 검증
|
|
structures.py 문서 유형별 필수 section intent와 순서
|
|
prompts.py planner/writer/reviewer/reviser 출력 계약
|
|
providers/ Codex, Claude, Antigravity, Mock 어댑터
|
|
lint.py 모델과 독립적인 Markdown/논리 프록시 검사
|
|
pipeline.py 단계 실행, 수정 루프, 품질 게이트, 감사 산출물
|
|
report.py 사람이 읽는 품질 보고서
|
|
cli.py init/validate/outline/lint/run/doctor 명령
|
|
```
|
|
|
|
## 3. 단계별 상태 전이
|
|
|
|
### 3.1 계약 입력
|
|
|
|
- `Brief`: 독자, 목표, 핵심 메시지, 범위, 비범위, 선행지식, 필수 주제, 버전 맥락, 금지 주장
|
|
- `SourcePack`: 출처 식별자와 출처가 실제로 지지하는 사실 단위
|
|
- `PipelineConfig`: 각 역할의 provider, timeout, 옵션, 품질 게이트
|
|
|
|
입력은 정규화되어 `inputs/`에 기록된다.
|
|
|
|
### 3.2 결정적 기본 outline
|
|
|
|
`structures.py`가 `document_type`에 따라 필수 intent를 만든다. 각 section은 다음 계약을 가진다.
|
|
|
|
```json
|
|
{
|
|
"id": "04-mechanism",
|
|
"intent": "mechanism",
|
|
"title": "해결 방식이 동작하는 과정",
|
|
"reader_question": "구성요소와 데이터 흐름은 어떻게 연결되는가?",
|
|
"purpose": "메커니즘을 단계적 인과 사슬로 설명한다.",
|
|
"must_include": ["구성요소", "데이터 또는 제어 흐름", "불변조건"],
|
|
"evidence_ids": ["S1"],
|
|
"transition_to_next": "다음 독자 질문으로 연결한다."
|
|
}
|
|
```
|
|
|
|
### 3.3 Planner 정교화
|
|
|
|
Planner는 section 제목, 질문, 목적, `must_include`, 근거 배치, 전환을 개선한다. `reconcile_outline`은 다음을 거부한다.
|
|
|
|
- 문서 유형 변경
|
|
- 필수 intent 삭제
|
|
- intent 중복
|
|
- 필수 순서 변경
|
|
- 존재하지 않는 source ID
|
|
|
|
Planner 실행 또는 JSON 파싱이 실패하면 기본 outline을 사용하고 경고를 기록한다.
|
|
|
|
### 3.4 Writer
|
|
|
|
Writer는 exact H1과 exact H2 순서를 지켜 전체 Markdown을 반환해야 한다. 브리프와 출처는 지시가 아닌 untrusted data로 경계 표시된다. Writer 실패는 대체 텍스트로 숨기지 않고 실행 오류로 종료한다.
|
|
|
|
### 3.5 결정적 린트
|
|
|
|
린터는 모델 응답과 독립적으로 구조, 형식, 절차, 안전, 근거 표식을 검사한다. 자연어 의미를 완전히 판단하지 않으며 **최소 품질 바닥**을 제공한다.
|
|
|
|
### 3.6 독립 리뷰
|
|
|
|
각 reviewer는 동일한 초안을 다른 실패 함수로 검사한다.
|
|
|
|
- logic: 전제→결론, 인과 단절, 모순, section 역할
|
|
- reader: 선행지식, 방향 감각, 점진 공개, 예시, scan path
|
|
- evidence: 출처 적합성, 지원되지 않은 확신, 버전 민감성
|
|
- operations: 절차 순서, 검증, 파괴적 조작, 복구, 관측
|
|
- editor: 문장·문단 초점, 용어, 중복
|
|
|
|
리뷰 응답은 고정 JSON 스키마로 파싱된다. 필수 reviewer가 실패하면 기본적으로 실행이 실패한다. `fail_on_reviewer_error: false`는 실패 리뷰를 blocker/0점으로 기록해 산출물을 남긴다.
|
|
|
|
### 3.7 품질 게이트와 수정
|
|
|
|
```text
|
|
model_mean = mean(review.score)
|
|
composite = lint.score * deterministic_weight + model_mean * model_weight
|
|
PASS = composite >= minimum_score
|
|
AND blockers <= max_blockers
|
|
AND errors <= max_errors
|
|
```
|
|
|
|
FAIL이고 수정 한도가 남으면 reviser가 lint와 모든 리뷰를 받아 전체 문서를 다시 작성한다. 수정된 초안은 동일한 린트와 리뷰를 처음부터 통과해야 한다.
|
|
|
|
## 4. 신뢰 경계
|
|
|
|
| 경계 | 신뢰 수준 | 처리 |
|
|
|---|---|---|
|
|
| pipeline config | 로컬 운영자가 승인한 코드 수준 설정 | command 실행 가능하므로 반드시 신뢰된 파일만 사용 |
|
|
| brief/source pack | 비신뢰 데이터 | prompt 내부에서 data로 구획, 지시 무시 명시 |
|
|
| model response | 비신뢰 출력 | JSON 파싱·계약 검증·lint·review 수행 |
|
|
| URL | 메타데이터 | 자동 방문/실행하지 않음 |
|
|
| final document | 검토 후보 | PASS여도 도메인 사실·코드 실행을 별도 검증 |
|
|
|
|
## 5. 실패 정책
|
|
|
|
| 단계 | 기본 실패 처리 | 이유 |
|
|
|---|---|---|
|
|
| planner | 결정적 outline 폴백 + 경고 | 구조의 안전한 기본값이 존재 |
|
|
| writer | 실행 중단 | 내용 없는 대체 초안은 유효하지 않음 |
|
|
| reviewer | 실행 중단 | 독립 검토가 구성 계약의 일부 |
|
|
| reviewer, fail-open 설정 | blocker/0점 리뷰로 기록 | 산출물 보존이 필요한 실험 환경 |
|
|
| reviser | 실행 중단 | 수정 실패를 이전 초안 통과로 위장하지 않음 |
|
|
| quality gate fail | final 산출물은 남기되 exit code 4 | 사람이 결함을 분석할 수 있도록 보존 |
|
|
|
|
## 6. 재현성과 감사
|
|
|
|
- provider 요청의 stage/provider/model/status/duration을 JSONL로 기록
|
|
- 각 모델의 raw response와 parsed JSON을 모두 보존
|
|
- 입력을 정규화해 실행 시점 계약을 고정
|
|
- 최종 산출물을 포함한 파일별 SHA-256 매니페스트 생성
|
|
- Mock provider로 외부 네트워크 없이 파이프라인 배선 재현
|
|
|
|
모델 자체의 비결정성까지 제거하지는 않는다. 운영에서 모델 ID, CLI/SDK 버전, 실행 날짜를 `version_context`, provider `model`, 별도 배포 메타데이터에 고정해야 한다.
|