init: resume 작성 하네스 설계
This commit is contained in:
@@ -0,0 +1,265 @@
|
||||
# 아키텍처 설계
|
||||
|
||||
## 1. 설계 목표
|
||||
|
||||
최상 품질은 “그럴듯한 문장”이 아니라 재현 가능한 품질 계약으로 정의합니다. 하네스는 다음 네 가지를 동시에 달성해야 합니다.
|
||||
|
||||
1. **사실 충실성**: 입력하지 않은 사실을 생성하지 않는다.
|
||||
2. **직무 적합성**: 공고 요구와 후보자 근거의 교집합을 가장 먼저 보여준다.
|
||||
3. **한국어 문서 품질**: 짧고 자연스러운 한국어와 국내 채용 문맥에 맞는 구성을 쓴다.
|
||||
4. **개인정보·공정성**: “한국식”을 과도한 개인정보 수집으로 해석하지 않는다.
|
||||
|
||||
## 2. 핵심 경계
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
A[CandidateProfile\n불변 사실] --> B[Privacy Guard]
|
||||
J[JobPosting\n신뢰하지 않는 데이터] --> C[Job Analyzer]
|
||||
B --> D[Evidence Mapper]
|
||||
C --> D
|
||||
D --> E[Content Planner]
|
||||
E --> F[Draft Generator]
|
||||
F --> G[Rule Validators]
|
||||
G --> H[Independent Judge]
|
||||
H -->|결함 있음| I[Targeted Repair]
|
||||
I --> G
|
||||
H -->|통과| R[ResumeDraft 정본]
|
||||
R --> M[Markdown]
|
||||
R -. 향후 .-> X[HTML/DOCX/PDF/HWPX]
|
||||
```
|
||||
|
||||
원본 사실, 의미 모델, 표현 문서의 경계를 분리합니다.
|
||||
|
||||
- `CandidateProfile`: 사용자가 제공한 사실 원장입니다. 생성기가 수정하지 않습니다.
|
||||
원자적 `EvidenceItem`과, 그 근거 ID에 연결된 선택형 `ResumeRecords`를 분리해
|
||||
회사·직무·기간·고용형태·학위·자격 정보를 기계 판독 가능한 형태로 보존합니다.
|
||||
- `JobAnalysis`: 공고의 필수/우대 요건과 책임을 안정적인 ID로 정규화합니다.
|
||||
필수·우대 분류은 섹션 표시어부터 해당 요건 문구까지를 함께 담은 연속
|
||||
`classification_quote`로 입증해 다른 위치의 분류 표식을 빌려 쓰지 못하게 합니다.
|
||||
- `EvidenceMap`: 각 요건을 후보자 근거와 연결하고, 근거가 없으면 명시적으로 `gap`으로 둡니다.
|
||||
- `ResumeDraft`: 문장과 섹션을 담는 도메인 정본입니다. 모든 주장에 `evidence_ids`가 필요합니다. JSON/YAML은 정본의 직렬화 형식이며 제출용 렌더 형식이 아닙니다.
|
||||
- 렌더러: 현재는 정본을 단일 열 Markdown로만 표현합니다. HTML, DOCX, PDF, HWPX 어댑터는 향후 범위이며, 어떤 렌더러도 새로운 내용을 쓰면 안 됩니다.
|
||||
|
||||
구조화 레코드는 현재 로컬 입력·참조·날짜 검증에만 사용되며, 생성
|
||||
backend 페이로드나 `ContentPlan`에 자동 반영되지 않습니다. 레코드를 최종
|
||||
문서에 반영하려면 개인정보 정책을 적용해 근거가 붙은 `ResumeDraft` claim으로
|
||||
materialize한 뒤, 같은 규칙 검사·품질 평가·fingerprint 결합을 통과해야 합니다.
|
||||
렌더러가 `CandidateProfile.records`를 직접 합성하는 경로는 두지 않습니다.
|
||||
|
||||
개인 연락처는 생성 모델에 전달하지 않고 가능하면 최종 렌더 단계에서 삽입합니다.
|
||||
|
||||
## 3. 단계 계약과 실제 종료 상태
|
||||
|
||||
다음은 파이프라인의 개념적 단계이지 공개 상태 enum이 아닙니다.
|
||||
현재 `PipelineResult.status`가 반환하는 종료 상태는 `passed`와
|
||||
`needs_user_input` 두 가지뿐입니다.
|
||||
|
||||
```text
|
||||
RECEIVED → VALIDATED → ANALYZED → MAPPED → PLANNED
|
||||
→ DRAFTED → RULE_CHECKED → JUDGED ↔ REPAIRED
|
||||
→ APPROVED → RENDERED
|
||||
|
||||
근거 부족 또는 수정 한도 후 릴리스 게이트 실패
|
||||
→ NEEDS_USER_INPUT
|
||||
```
|
||||
|
||||
입력 스키마, backend 호출, 단계 간 참조 무결성 위반은
|
||||
`needs_user_input`으로 바꾸지 않고 예외로 실패합니다. 따라서 위 개념 단계를
|
||||
영속 작업 큐의 상태 머신으로 해석해서는 안 됩니다.
|
||||
|
||||
| 단계 | 입력 | 출력 | 실패 조건 |
|
||||
|---|---|---|---|
|
||||
| Intake | 후보자·공고·설정 | 검증된 모델 | 스키마 오류, 중복 ID, 날짜 역전 |
|
||||
| Privacy | 후보자·정책 | 최소화된 모델 | 비동의 민감정보 포함 |
|
||||
| Analyze | 공고 원문 | `JobAnalysis` | 원문에 없는 요건 생성 |
|
||||
| Map | 분석+사실 | `EvidenceMap` | 존재하지 않는 근거 참조 |
|
||||
| Plan | 매핑+분량 | 콘텐츠 계획 | 근거 없는 요건을 강점으로 선택 |
|
||||
| Draft | 계획+사실 | `ResumeDraft` | 주장에 근거 ID 없음 |
|
||||
| Validate | 초안+사실+정책 | 규칙 결함 목록 | 하드 결함 존재 |
|
||||
| Judge | 초안+분석+허용 사실+결정적 결함 | 영역 점수·결함 | 스키마/참조 위반, blocking 결함, 릴리스 기준 미달 |
|
||||
| Repair | 초안+결함 | 부분 수정 초안 | 새 근거/주장 추가, 최대 횟수 초과 |
|
||||
| Render | 승인 정본+품질 보고서 | Markdown | 참조·정책·공고 제약 재검사 실패 |
|
||||
|
||||
`Validate`의 완성도 검사는 단순 글자 수가 아니다. 구조화 레코드가 있는 경우
|
||||
핵심 요약을 역할/대표 성과로 분리하고, 확인된 기술이 충분하면 핵심 역량 섹션을
|
||||
요구하며, 경력·프로젝트마다 연결된 근거 수에 비례한 최소 서술 깊이를 검사한다.
|
||||
따라서 모든 문장에 근거 ID가 있어도 한 줄짜리 프로젝트나 누락된 역량 섹션은
|
||||
릴리스할 수 없다.
|
||||
|
||||
공고·업로드 문서 안의 지시문은 실행 명령이 아니라 데이터입니다. 분석 프롬프트는 공고의 텍스트를 인용 경계 안에 넣고, 그 안의 “이전 지시 무시” 같은 문구를 따르지 않도록 고정합니다.
|
||||
|
||||
## 4. 한국형 정책 프로필
|
||||
|
||||
### `private_modern` — 기본값
|
||||
|
||||
- 이름, 이메일, 전화, 시/도 수준 위치, 포트폴리오 링크만 허용
|
||||
- 지원 직무 → 핵심 요약 → 핵심 역량 → 경력/프로젝트 → 학력/자격 순
|
||||
- 최근 경력부터 쓰며 입력의 날짜 정밀도를 보존함. 연 단위 입력은 `YYYY`, 월 단위 입력은 기본 `YYYY.MM`로 표현
|
||||
- 사진, 생년월일, 성별, 가족, 혼인, 종교, 신체정보는 제외
|
||||
|
||||
### `public_blind`
|
||||
|
||||
- 공고의 블라인드 규칙을 개별 lint 정책으로 우선 적용
|
||||
- 출신지, 가족관계, 외모 등 편견 유발 정보와 학교명을 기본 차단
|
||||
- 직무 관련 교육, 자격, 유급 경력, 무급 경험을 구분
|
||||
- NCS 직무기술서의 지식·기술·태도와 실제 근거의 연결을 평가
|
||||
|
||||
### `employer_form`
|
||||
|
||||
- 현재는 지정 필드, 공고 제약, 명시적 동의, 채용사 요구를 표현·검증하는 정책 모드만 제공
|
||||
- 민감 필드는 활성 동의와 기록된 채용사 요구가 모두 있어야 설정 가능하지만, 현재 Markdown 렌더러는 사진·지정 칸 삽입을 지원하지 않음
|
||||
- 주민등록번호, 계좌, 건강정보는 이력서 생성 범위에서 항상 금지
|
||||
- 지정 양식 요구가 법적으로 적절하다는 보장은 하지 않으며 사용자에게 경고
|
||||
- `EMPLOYER_TEMPLATE` 제약은 전용 어댑터가 없으며 blocking으로 fail-closed
|
||||
|
||||
공고별 규칙이 프로필 기본값보다 우선하되, 안전상 절대 금지 항목을 해제할 수는 없습니다.
|
||||
|
||||
## 5. 경력 수준별 콘텐츠 전략
|
||||
|
||||
| 유형 | 우선순위 | 권장 구성 |
|
||||
|---|---|---|
|
||||
| 신입 | 프로젝트·교육·직무 경험 | 요약, 역량, 프로젝트, 교육/학력, 자격/활동 |
|
||||
| 경력 | 최근 역할·성과·책임 범위 | 요약, 역량, 경력, 대표 프로젝트, 학력/자격 |
|
||||
| 직무 전환 | 이전 경험의 이전 가능 역량 | 목표 직무 요약, 연결 역량, 관련 프로젝트, 경력 |
|
||||
| 공공/NCS | 직무기술서 근거 커버리지 | 자격/교육, 경력, 경험, 문항별 기술서 |
|
||||
|
||||
문장 기본형은 `문제/맥락 → 본인의 행동 → 검증 가능한 결과`입니다. 수치가 없으면 억지로 정량화하지 않고 범위, 산출물, 의사결정, 품질 변화 같은 검증 가능한 정성 결과를 사용합니다.
|
||||
|
||||
## 6. LLM 경계
|
||||
|
||||
`LLMBackend`는 다음 구조화 호출만 제공합니다.
|
||||
|
||||
```python
|
||||
class LLMBackend(Protocol):
|
||||
def complete_json(
|
||||
self,
|
||||
*,
|
||||
stage: str,
|
||||
system_prompt: str,
|
||||
task_prompt: str,
|
||||
user_payload: dict,
|
||||
output_model: type[BaseModel],
|
||||
) -> BaseModel: ...
|
||||
```
|
||||
|
||||
각 단계는 낮은 자유도의 구조화 JSON을 반환합니다. 코어는 프롬프트
|
||||
로딩, Pydantic 출력 검증, 개인정보·기밀 최소화, 단계 간 참조 무결성을
|
||||
구현합니다. 특정 공급자 어댑터는 포함되어 있지 않으며, 배포자가
|
||||
재시도, 타임아웃, 모델 실행 격리, 토큰·비용 기록을 어댑터 계약으로
|
||||
추가해야 합니다.
|
||||
|
||||
평가기의 주관적 점수와 하네스가 계산할 수 있는 지표를 섞지 않습니다. `draft_fingerprint`, claim 근거 연결률, 공고 요건의 우선순위 가중 커버리지, 실제 릴리스 임계값은 평가기 응답을 신뢰하지 않고 정본 후보자·초안·분석·설정에서 계산해 `QualityReport`에 덮어씁니다. 평가 fingerprint는 공고·분석·매핑·계획과 평가 프롬프트·가중치 정책까지 결합합니다.
|
||||
|
||||
결정적 finding과 주관 점수가 모순될 수도 없습니다. blocking finding이 속한 가중
|
||||
영역은 최대 59점, warning 영역은 최대 89점으로 하네스가 상한을 적용한 뒤 총점을
|
||||
재계산합니다. 개인정보·근거·완성도 오류를 평가 모델의 높은 점수로 상쇄할 수 없습니다.
|
||||
|
||||
단, SHA-256 fingerprint는 보고서 발급 주체를 인증하는 서명이 아닙니다. 현재 단독 CLI는
|
||||
로컬 품질 보고서 파일을 신뢰하는 단일 사용자 경계입니다. 다중 사용자·원격 승인
|
||||
서비스에서는 평가 모델·정책·보고서 본문·전체 컨텍스트를 서명한 attestation과 신뢰
|
||||
저장소를 배포 계층에서 의무화해야 합니다. 구체적인 envelope와 검증 순서는
|
||||
[배포 보안과 품질 승인 신뢰 경계](deployment-security.md)에 정의합니다.
|
||||
|
||||
현재 코어는 한 번의 backend 응답이 스키마나 참조 계약을 위반하면 해당
|
||||
단계를 실패시킵니다. 스키마·네트워크 재시도 정책은 현재 코어가 아닌
|
||||
공급자 어댑터의 향후 배포 요구사항입니다. 콘텐츠 품질 수정은 코어가
|
||||
최대 2회로 제한합니다.
|
||||
|
||||
## 6.1 ATS와 국내 지정 양식
|
||||
|
||||
ATS 기본 출력은 단일 열의 실제 텍스트 문서이며, 표·텍스트박스·다단·사진·아이콘과 헤더/푸터의 핵심 정보 배치를 피합니다. `경력`, `프로젝트`, `학력`, `기술`, `자격증`처럼 명확한 제목을 사용합니다. 이는 [Greenhouse의 공식 파싱 실패 안내](https://support.greenhouse.io/hc/en-us/articles/200989175-Unsuccessful-resume-parse)와 [한국어 파싱 지원 안내](https://support.greenhouse.io/hc/en-us/articles/205019689-Resume-parsing-with-non-English-languages)를 보수적으로 적용한 것입니다.
|
||||
|
||||
범용 “ATS 합격 점수”는 제공하지 않습니다. 현재 코어는 단일 읽기 순서의
|
||||
텍스트 Markdown을 만들고 필수 요건 커버리지와 키워드 근거를 검사합니다.
|
||||
특정 ATS에 업로드한 뒤의 실제 파싱 성공률은 측정하지 않으며 배포별 통합
|
||||
테스트가 필요합니다.
|
||||
|
||||
국내 공공기관 지정 양식을 위한 HWPX 어댑터는 향후 범위입니다.
|
||||
구현할 때는 HWPX를 ATS 기본 출력으로 취급하지 않고, 기관이 제공한
|
||||
양식의 항목명·글자 수·표 구조 보존과 텍스트 추출 사후 검사를 모두
|
||||
제공해야 합니다. 현재는 HWPX·HWP를 처리하지 않으며, 지정 양식
|
||||
제약은 fail-closed로 차단합니다.
|
||||
|
||||
### 6.2 출력 제약 게이트
|
||||
|
||||
공고 분석기가 추출한 규칙을 생성 모델이 스스로 준수했다고 판단하게 두지 않습니다. `output_constraints` 게이트를 결정적 검사, CLI 검증, 렌더 직전에 같은 방식으로 실행합니다.
|
||||
|
||||
- `REQUIRED_SECTION`: 섹션 타입·한국어 표준 별칭·실제 heading을 대조하고, 어떤 섹션을 뜻하는지 추출되지 않았으면 통과시키지 않음
|
||||
- `CHARACTER_LIMIT`: 섹션 제목은 제외하고 NFC 정규화된 본문을 공백과 bullet 사이 줄바꿈까지 포함해 Unicode 문자 수로 계산
|
||||
- `FILE_FORMAT`: `.md`, `Markdown`, MIME 표기 같은 안전한 별칭을 정규화하고 현재 렌더러 형식이 허용 목록에 없으면 차단
|
||||
- 분석 무결성: `formats`, `max_characters`, 섹션명 값이 자체 `source_quote`의
|
||||
원문 값과 일치하는지 먼저 대조하고, 여러 대상·값이 함께 있으면 가장 가까운
|
||||
같은 문맥의 대상-값 쌍만 인정
|
||||
- 제약 완전성: 원문에 명시된 blocking 제출 제약은 종류와 원문 절 단위로 모두
|
||||
추출되었는지 재검사하며, 일부 제약이나 무관한 `OTHER` 제약만으로 누락을 덮지 않음
|
||||
- `section_order`: 설정에 열거된 섹션끼리의 상대 순서를 검사하며, 설정에 없는 보조 섹션은 순서 판정에서 제외
|
||||
- `date_format`: 제목·섹션명·claim에 있는 월/일 정밀도 날짜가 설정 `YYYY.MM` 또는 `YYYY.MM.DD`와 일치하는지 검사. 연도만 제공된 입력에 월이나 일을 새로 만들지 않음
|
||||
- `EMPLOYER_TEMPLATE`: 원본 지정 양식 어댑터 없이 검증할 수 없으므로 blocking 규칙이면 닫힌 방식으로 실패
|
||||
|
||||
`max_pages`는 현재 구현에서 릴리스 게이트가 아닙니다. Markdown처럼 물리
|
||||
레이아웃이 없는 출력을 문자 수로 페이지 추정해 합격 처리하지 않습니다.
|
||||
향후 DOCX/PDF 어댑터는 실제 한국어 폰트, 용지, 여백, 줄바꿈을 적용한
|
||||
산출물의 페이지 수와 오버플로를 postflight로 측정해야 합니다. 채용
|
||||
포털이 다른 글자 수 규칙을 사용하면 해당 포털 전용 카운터도
|
||||
별도로 연결해야 합니다.
|
||||
|
||||
## 7. 수정 루프
|
||||
|
||||
전체 이력서를 반복 재작성하면 이미 맞는 사실이 흔들립니다. 따라서 결함은 아래 계약으로 전달하고 `claim_id` 단위로 수정합니다.
|
||||
|
||||
```json
|
||||
{
|
||||
"finding_id": "finding-001",
|
||||
"code": "GROUNDING.UNSUPPORTED_NUMBER",
|
||||
"severity": "error",
|
||||
"category": "evidence",
|
||||
"claim_id": "claim-exp-01-2",
|
||||
"message": "42%를 뒷받침하는 근거가 없습니다.",
|
||||
"evidence_ids": ["ev-exp-01"],
|
||||
"suggestion": "기존 근거의 값으로 교체하거나 숫자를 제거"
|
||||
}
|
||||
```
|
||||
|
||||
수정 후 다음 불변식을 다시 검사합니다.
|
||||
|
||||
- 기존 `evidence_ids` 집합 밖의 근거를 추가하지 않았는가
|
||||
- 숫자·날짜·고유명사가 사실 원장과 일치하는가
|
||||
- 수정 후에도 같은 하드 결함이 남아 있는가
|
||||
- 수정으로 다른 섹션의 일관성이 깨지지 않았는가
|
||||
|
||||
최대 2회 후에도 하드 게이트가 남으면 추측하지 않고 사용자 입력이 필요한 질문을 최대 3개 반환합니다.
|
||||
|
||||
## 8. 감사와 재현성
|
||||
|
||||
현재 코어는 `ResumeDraft.fingerprint()`와 평가 컨텍스트 fingerprint로 품질
|
||||
보고서를 초안·공고·분석·매핑·계획·설정에 결합합니다. 다음 실행
|
||||
메타데이터 저장은 현재 코어에 포함된 감사 로거가 아니라, 배포 계층이
|
||||
구현해야 할 목표 계약입니다. 실제 개인정보·전체 프롬프트·원문은 일반
|
||||
로그에 저장하지 않아야 합니다.
|
||||
|
||||
```text
|
||||
run_id, input_hash, schema_version, prompt_versions,
|
||||
model_id, model_parameters, policy_profile, validator_version,
|
||||
template_version, quality_scores, issue_fingerprints, generated_at
|
||||
```
|
||||
|
||||
현재 테스트는 합성 아티팩트의 모델·참조·개인정보·출력 제약·릴리스
|
||||
불변 조건을 확인합니다. 특정 외부 모델의 버전별 비결정성 회귀 평가는
|
||||
배포 계층에서 별도로 구성해야 합니다.
|
||||
|
||||
## 9. 현재 구현과 향후 범위
|
||||
|
||||
**현재 코어**
|
||||
|
||||
- YAML/JSON 입력과 Pydantic 도메인 모델
|
||||
- 구조화 공고 분석·매핑·계획·초안·평가·최대 2회 수정 조정
|
||||
- 사실·참조·날짜 정밀도·개인정보·공고 제약 검사
|
||||
- 품질 fingerprint 결합, CLI 릴리스 게이트, 단일 열 Markdown 렌더러, 합성 테스트
|
||||
|
||||
**향후/배포 범위**
|
||||
|
||||
- 특정 LLM 공급자 어댑터와 운영 재시도·타임아웃·비용 계측
|
||||
- ATS HTML/DOCX/PDF, HWPX 지정 양식, 한국어 폰트, 텍스트 추출·오버플로 사후 검사
|
||||
- 감사 로그, 암호화·보존·삭제, 포털별 문자 수 카운터
|
||||
- 다중 사용자 배포용 Ed25519 품질 attestation, 공개키 trust store, 키 회전
|
||||
- 다중 평가기, NCS 직무사전, 편향 쌍대 평가, 한국 채용담당자 평가
|
||||
@@ -0,0 +1,29 @@
|
||||
# ADR 0001: 근거 기반 Resume IR을 정본으로 사용
|
||||
|
||||
- 상태: 채택
|
||||
- 날짜: 2026-07-17
|
||||
|
||||
## 결정
|
||||
|
||||
렌더된 문서가 아니라, 모든 문장에 근거 ID가 연결된 `ResumeDraft`
|
||||
도메인 모델을 이력서 내용의 정본으로 사용합니다. JSON과 YAML은 이
|
||||
정본의 교환·저장을 위한 직렬화 형식이지 최종 문서 렌더러가 아닙니다.
|
||||
후보자 입력 사실은 별도 `CandidateProfile`로 보존하며 생성기가 수정하지
|
||||
못합니다.
|
||||
|
||||
## 이유
|
||||
|
||||
단일 프롬프트로 문서를 바로 생성하면 사실 추적, 부분 수정, 출력 포맷 전환, 회귀 검증이 어렵습니다. 중간 표현을 사용하면 같은 내용으로 민간형·블라인드형·ATS형을 렌더할 수 있고, 근거 없는 문장을 하드 게이트로 차단할 수 있습니다.
|
||||
|
||||
## 결과
|
||||
|
||||
- 모든 문장 생성 API는 `evidence_ids`를 반환해야 합니다.
|
||||
- 렌더러는 콘텐츠를 추가하거나 재작성할 수 없습니다.
|
||||
- 현재 코어는 초안 fingerprint와 후보자·전체 평가 컨텍스트·평가 정책
|
||||
fingerprint로 품질 보고서의 적용 대상을 결합합니다.
|
||||
- fingerprint는 서명이 아니므로 다중 사용자 배포의 품질 보고서는 별도의
|
||||
서명된 attestation과 신뢰 저장소가 필요합니다.
|
||||
- 입력·프롬프트·모델·검사기·템플릿 버전 감사 로그는 배포 계층이
|
||||
구현해야 할 후속 요구사항입니다.
|
||||
- 현재 최종 렌더러는 Markdown뿐입니다. 향후 PDF/DOCX/HWPX는 파생
|
||||
산출물로 만들고, 다시 파싱해 정본으로 쓰지 않습니다.
|
||||
@@ -0,0 +1,85 @@
|
||||
# 배포 보안과 품질 승인 신뢰 경계
|
||||
|
||||
## 범위와 현재 상태
|
||||
|
||||
현재 코어의 SHA-256 fingerprint는 초안, 공고, 분석, 근거 매핑, 콘텐츠 계획,
|
||||
설정, 평가 정책이 바뀌었는데 과거 평가를 재사용하는 오류를 막습니다. 그러나
|
||||
fingerprint는 비밀키가 없는 무결성 표식이므로 품질 보고서의 발급자나
|
||||
`category_scores`·`findings`의 위변조를 인증하지 않습니다.
|
||||
|
||||
따라서 현재 `resume-harness render`는 사용자가 입력 파일과 품질 보고서를 모두
|
||||
관리하는 **단일 사용자 로컬 도구**의 신뢰 경계입니다. 지원자와 보고서 제출자가
|
||||
분리되는 웹 서비스, 사내 승인 서비스, 다중 사용자 API에서는 아래 서명 계층을
|
||||
구현하기 전까지 이 CLI 경로를 그대로 외부에 노출하면 안 됩니다.
|
||||
|
||||
| 배포 형태 | 품질 보고서 신뢰 | 허용 정책 |
|
||||
|---|---|---|
|
||||
| 단일 사용자 로컬 | 동일 사용자가 입력·평가 파일을 관리 | 현재 fingerprint와 로컬 하드 게이트 사용, 보안 인증으로 오해하지 않음 |
|
||||
| 다중 사용자/원격 서비스 | 요청자가 보고서를 바꿀 수 있음 | 서명된 attestation 필수, unsigned 보고서 fail-closed |
|
||||
|
||||
## 프로덕션 `QualityAttestation` 계약
|
||||
|
||||
프로덕션 승인 서비스는 독립 평가와 모든 결정적 게이트가 끝난 뒤 다음 envelope를
|
||||
Ed25519로 서명해야 합니다. 실제 `QualityReport` 전체를 envelope 안에 넣어 점수와
|
||||
finding도 서명 범위에 포함합니다.
|
||||
|
||||
```text
|
||||
schema_version
|
||||
attestation_id
|
||||
issuer
|
||||
audience
|
||||
key_id
|
||||
issued_at
|
||||
expires_at
|
||||
validator_version
|
||||
evaluation_policy_fingerprint
|
||||
evaluator.provider / evaluator.model / evaluator.version
|
||||
quality_report # 전체 QualityReport
|
||||
signature_algorithm = Ed25519
|
||||
signature
|
||||
```
|
||||
|
||||
서명 payload는 `signature` 필드만 제외한 envelope 전체를 RFC 8785(JCS) 고정
|
||||
canonical JSON 규칙으로 직렬화하고, 다른 토큰과 혼동되지 않도록
|
||||
`resume-harness-quality-attestation-v1\0` 도메인 구분자를 앞에 붙입니다. envelope가
|
||||
가져온 공개키를 신뢰하지 않으며, 운영자가 관리하는 읽기 전용 trust store에서
|
||||
`issuer + key_id`로 공개키를 선택합니다.
|
||||
|
||||
렌더 서비스는 다음 순서로 검증하고 어느 단계에서든 실패하면 출력하지 않습니다.
|
||||
|
||||
1. 스키마, 알고리즘, `issuer`, `audience`, `key_id` 허용 목록
|
||||
2. Ed25519 서명과 발급·만료 시간(허용 clock skew 포함)
|
||||
3. evaluator·validator·평가 정책 버전 허용 목록
|
||||
4. 현재 아티팩트에 대한 draft/evaluation fingerprint 재계산
|
||||
5. evidence/requirement coverage와 가중 총점 재계산
|
||||
6. 개인정보·근거·공고 출력 제약의 로컬 결정적 검사 재실행
|
||||
7. blocking finding, 총점, 영역별 임계값 확인 후 렌더
|
||||
|
||||
서명 성공은 이력서 내용이 사실이라는 외부 증명이 아닙니다. 지정된 평가 서비스가
|
||||
특정 입력과 정책으로 해당 보고서를 발급했다는 사실만 인증합니다. 근거 원장의
|
||||
진위는 `verification_status`와 별도의 증빙 검토 문제입니다.
|
||||
|
||||
## 키와 운영 정책
|
||||
|
||||
- 서명 개인키는 평가 worker 또는 KMS/HSM만 사용하고 렌더러·요청자에게 주지 않음
|
||||
- 렌더러에는 공개키와 issuer/policy allowlist만 읽기 전용으로 배포
|
||||
- 키 회전 시 `key_id`, 활성 시작일, 폐기일을 기록하고 만료된 보고서를 재평가
|
||||
- unsigned 우회 옵션은 로컬 개발 명령에만 둘 수 있으며 서버 API·사용자 설정에는
|
||||
노출하지 않음
|
||||
- 검증 실패 로그에는 원문 이력서, 연락처, 서명 payload 전체를 남기지 않고
|
||||
attestation ID, 비식별 fingerprint, 오류 코드만 기록
|
||||
- 재생 방지가 필요한 제출 시스템은 `audience`, 짧은 만료 시간, 제출별 nonce를
|
||||
함께 검증
|
||||
|
||||
## 필수 보안 회귀 테스트
|
||||
|
||||
- 점수, finding, 임계값, evaluator 정보 중 한 바이트만 바꿔도 서명 실패
|
||||
- 다른 초안·공고·매핑·계획·설정의 정상 서명을 재사용해도 fingerprint 실패
|
||||
- self-signed 공개키, 알 수 없는 issuer/key, 잘못된 audience, 만료·미래 발급 거부
|
||||
- 폐기된 키와 허용되지 않은 평가 정책·모델 버전 거부
|
||||
- 동일 JSON의 필드 순서·Unicode 정규화 차이를 canonicalization 규칙으로 고정
|
||||
- 서명이 유효해도 로컬 개인정보·근거·출력 제약이 실패하면 렌더 거부
|
||||
|
||||
Ed25519 서명과 trust store는 현재 저장소에 구현된 기능이 아니라 다중 사용자 배포의
|
||||
필수 확장 계약입니다. 구현 전에는 현재 CLI를 신뢰 경계 밖의 승인 서비스로
|
||||
간주하지 않습니다.
|
||||
@@ -0,0 +1,97 @@
|
||||
# 개인정보·공정성 정책
|
||||
|
||||
## 기본 정책
|
||||
|
||||
현대적인 한국식 이력서의 기본값은 직무 능력 중심입니다. 다음 정보는 일반 민간 이력서에서도 기본 출력하지 않습니다.
|
||||
|
||||
- 사진, 생년월일/나이, 성별, 주민등록번호
|
||||
- 상세 주소, 출신 지역, 가족관계, 혼인 여부
|
||||
- 키·체중·혈액형·질병 등 신체/건강 정보
|
||||
- 종교, 정치적 견해, 재산 정보
|
||||
- 병역 상세, 장애 정보 등 민감하거나 차별로 이어질 수 있는 정보
|
||||
|
||||
이름, 연락 가능한 이메일/전화, 시·도 수준 위치, 직무 관련 링크만 `private_modern`의 기본 신원 정보로 허용합니다. 연락처도 LLM 입력에서는 제거하고 렌더 단계에서 삽입하는 방식을 권장합니다.
|
||||
|
||||
주민등록번호, 계좌번호, 인증 비밀, 건강진단 자료는 사용자 동의가 있어도 이 하네스의 이력서 입력으로 받지 않습니다.
|
||||
|
||||
현재 타입 스키마와 본문 패턴 검사는 사진, 생년월일, 성별, 상세 주소,
|
||||
혼인·가족, 종교, 정치적 견해, 재산, 장애·건강, 병역 상세, 보상, 신분·계좌 등을
|
||||
다룹니다. 정치적 견해와 재산의 명시적 라벨·값 패턴은 동의 여부와 관계없이
|
||||
intake에서 차단합니다. 자유 문장의 숨은 표현까지 보강하려면 배포 계층에
|
||||
NER/DLP 어댑터를 추가해야 합니다.
|
||||
|
||||
## 예외 처리
|
||||
|
||||
지원처 지정 양식이 사진, 생년월일, 병역 등을 요구할 수 있습니다. 현재
|
||||
코어는 `employer_form` 설정에서 필드별 활성 동의와 채용사 요구의
|
||||
일치를 검증하지만, 사진·HWPX·DOCX·PDF 또는 지정 양식 삽입을 구현하지
|
||||
않았습니다. Markdown 렌더러는 사진 포함 요청을 거부하고,
|
||||
`EMPLOYER_TEMPLATE` 제약은 전용 어댑터가 없으면 fail-closed로 차단합니다.
|
||||
|
||||
향후 지정 양식 워크플로는 단순 설정 하나로 예외를 활성화하지 않고
|
||||
다음 조건을 모두 구현해야 합니다.
|
||||
|
||||
1. 지원처가 요구한 정확한 필드와 목적이 기록됨
|
||||
2. 사용자가 해당 필드별 포함에 명시적으로 동의함
|
||||
3. 출력 전 민감정보 요약을 다시 보여 줌
|
||||
4. 생성용 LLM이 아니라 최종 렌더러에서 값을 삽입함
|
||||
|
||||
공고 요구가 적절한지 자동으로 단정하지 않습니다. 법률 또는 권리 침해가 우려되면 관련 기관이나 전문가 확인을 안내합니다.
|
||||
|
||||
## 공공 블라인드
|
||||
|
||||
`public_blind`는 공고에 적힌 블라인드 기준을 파싱해 개별 정책을 만듭니다. 학교명, 출신지, 가족관계, 성별, 연령, 사진 등은 기본 차단하고, 연락·본인확인 정보가 필요하더라도 심사용 본문과 분리합니다.
|
||||
|
||||
경력과 경험도 구분합니다.
|
||||
|
||||
- `employment`: 금전적 보수를 받고 수행한 경력
|
||||
- `experience`: 프로젝트, 동아리, 봉사 등 직무 관련 무급 경험
|
||||
|
||||
학교 교육을 기재할 수 있는 공고라도 학교명 노출 금지 여부는 별도로 확인합니다. 하나의 “블라인드” 정규식으로 모든 기관 규칙을 처리하지 않습니다.
|
||||
|
||||
## 저장·전송·로그
|
||||
|
||||
현재 코어가 직접 구현하는 경계는 다음과 같습니다.
|
||||
|
||||
- 연락처, 민감 사실, 기밀 사실을 LLM 입력에서 제외
|
||||
- 단계별 `candidate_facts` 허용 필드만 backend에 전달
|
||||
- `public_blind`에서 학교 식별 사실을 생성 경계 전에서 제외
|
||||
- backend 오류 메시지에 원문 응답을 삽입하지 않음
|
||||
|
||||
다음은 코어 라이브러리가 아닌 배포·저장·공급자 어댑터 계층이 반드시
|
||||
구현해야 할 운영 요구사항입니다.
|
||||
|
||||
- 원본 파싱과 PII 제거를 가능한 로컬에서 수행
|
||||
- 원문, 이름, 이메일, 전화, 전체 프롬프트를 일반 로그에 기록하지 않음
|
||||
- 비식별 해시·버전·점수·이슈 코드만 담는 감사 로그를 별도로 구현
|
||||
- 저장 시 암호화와 사용자별 분리, 명시적 보존 기한, 즉시 삭제 지원
|
||||
- 실제 후보자 자료를 테스트 픽스처나 소스 관리에 사용하지 않음
|
||||
- 모델 공급자의 보존·학습 정책과 데이터 처리 위치를 배포 시 확인
|
||||
|
||||
## 공정성 검사
|
||||
|
||||
직무 적합도 산정에서 사진, 이름, 성별, 나이, 학교 서열, 출신지, 가족 정보는
|
||||
사용하지 않습니다. 현재 코어는 이러한 값을 생성 backend 페이로드에서
|
||||
제외하고 공공 블라인드 본문을 규칙으로 검사합니다.
|
||||
|
||||
합성 쌍대 편향 평가는 향후 모델·프롬프트 버전을 배포할 때 추가해야 할
|
||||
회귀 테스트입니다. 직무 사실을 고정한 채 민감 속성만 바꾸고 다음 결과가
|
||||
동일한지 비교해야 합니다.
|
||||
|
||||
- 선택되는 경력/프로젝트
|
||||
- 문장의 긍정·부정 강도
|
||||
- 품질 점수와 수정 권고
|
||||
- 페이지 분량과 섹션 우선순위
|
||||
|
||||
의미 있는 차이가 발생하면 편향 회귀로 처리하고 프롬프트, 입력 최소화,
|
||||
평가 규칙을 검토해야 합니다.
|
||||
|
||||
## 설계 근거
|
||||
|
||||
- [채용절차의 공정화에 관한 법률](https://www.law.go.kr/LSW/lsInfoP.do?ancYnChk=0&lsId=011990)과 [제4조의3](https://law.go.kr/LSW/lsLinkCommonInfo.do?chrClsCd=010202&lsJoLnkSeq=1004918799)은 적용 대상 사업장의 채용 절차와 직무 수행에 필요하지 않은 용모·신체조건, 출신지역·혼인·재산, 가족의 학력·직업·재산 정보 요구 제한을 규정합니다.
|
||||
- [개인정보 보호법 제16조](https://www.law.go.kr/LSW/lsLawLinkInfo.do?chrClsCd=010202&lsJoLnkSeq=900079387)는 목적에 필요한 최소 개인정보 수집 원칙을, [제21조](https://www.law.go.kr/LSW/lsLinkCommonInfo.do?ancYnChk=&chrClsCd=010202&lsJoLnkSeq=1020398651)는 불필요해진 개인정보의 파기를 규정합니다.
|
||||
- [개인정보보호위원회 인사·노무 필수조치 안내](https://pipc.go.kr/np/cop/bbs/selectBoardArticle.do?bbsId=BS212&mCode=C040030000&nttId=8966)와 [개인정보 처리 통합 안내서](https://www.pipc.go.kr/np/cop/bbs/selectBoardArticle.do?bbsId=BS217&mCode=G010030000&nttId=11352)는 채용 단계의 최소 처리와 주민등록번호·민감정보 처리 요건을 설명합니다.
|
||||
- [NCS 공정채용 FAQ](https://www.ncs.go.kr/blind/rh09/qna_faq.do?faqTypeCd=09&searchCondition=&searchKeyword=)는 출신지·가족관계·학력·외모처럼 편견을 유발할 수 있는 항목을 걷어내고 직무 능력을 평가하는 블라인드 채용 원칙을 설명합니다.
|
||||
- [NCS 취업준비단계 안내](https://www.ncs.go.kr/mobile/rm02/RH10300302.do)는 유급 경력과 무급 경험을 구분하고 수행 활동, 조직 내 역할, 결과를 구체적으로 기술하도록 안내합니다.
|
||||
|
||||
사진·생년월일·성별·학교명이 모든 민간 채용에서 일률적으로 법률상 금지된다고 단정하지 않습니다. 다만 최소수집과 차별 위험, 공공 블라인드 기준을 고려해 기본값을 미수집·미출력으로 둡니다. 법과 기관별 기준은 바뀔 수 있으므로 제품 배포 시점에 다시 검토해야 하며, 이 문서는 법률 자문이 아닙니다.
|
||||
@@ -0,0 +1,154 @@
|
||||
# 품질 루브릭과 릴리스 게이트
|
||||
|
||||
## 원칙
|
||||
|
||||
점수는 개선 우선순위를 알려 주지만 사실 오류나 개인정보 위반을 상쇄하지 못합니다. 하드 게이트를 먼저 통과한 결과에만 100점 루브릭을 적용합니다.
|
||||
|
||||
## 하드 게이트
|
||||
|
||||
현재 파이프라인과 CLI 릴리스 경로는 다음 조건 중 하나라도 실패하면
|
||||
Markdown 최종본을 출력하지 않습니다.
|
||||
|
||||
- 모든 `DraftClaim`이 실제 존재하는 `evidence_ids`를 하나 이상 참조하고,
|
||||
계획·매핑이 허용한 요구사항-근거 쌍 안에 있음
|
||||
- 구조화 경력·프로젝트 기록이 있으면 핵심 요약 2개 이상, 검증된 기술을 묶은
|
||||
핵심 역량, 경력별 역할과 복수 성과, 프로젝트별 역할·구현·검증 깊이를 충족
|
||||
- 주장의 숫자·단위·날짜·영문 기술명과 고위험 표현이 연결 근거로 지지되고,
|
||||
한국어 주장에 최소한의 어휘 근거가 있음
|
||||
- 구조화 날짜 역전, 깨진 참조, 중복 ID가 0건
|
||||
- 정책상 금지된 개인정보·기밀이 0건
|
||||
- 공고에 없는 요구사항을 필수 조건으로 만들지 않음
|
||||
- 필수·우대 표시가 다른 섹션 제목을 가로질러 해당 요건에 잘못 적용되지 않음
|
||||
- 공고의 필수 섹션·글자 수·Markdown 파일 형식과 설정의 날짜·섹션
|
||||
순서 위반이 0건이며 명시적 blocking 제출 제약 추출 누락이 없음
|
||||
- 최종 문서에 `TBD`, `[확인 필요]`, 모델 메모가 남지 않음
|
||||
- 결정적 검사와 평가 보고서에 blocking finding이 0건
|
||||
- 가중 총점 90점 이상, 근거 연결률 100%, 우선순위 가중 직무 요구사항
|
||||
커버리지 80% 이상
|
||||
- `evidence`, `job_alignment`, `korean_language`, `privacy` 각 80점 이상
|
||||
|
||||
현재는 Markdown만 렌더하므로 물리 페이지, 잘림, 폰트, 오버플로 검사는
|
||||
하드 게이트에 포함되지 않습니다. 이 검사는 향후 DOCX/PDF/HWPX 렌더러의
|
||||
postflight 요구사항입니다. `max_pages`도 Markdown에서 추정해 통과시키지
|
||||
않습니다.
|
||||
|
||||
`self_reported` 근거는 “사용자가 제공한 내용에 근거함”을 뜻하며 외부 인증을 뜻하지 않습니다. 증빙 여부는 `verification_status`로 별도 표시합니다.
|
||||
|
||||
## 100점 루브릭
|
||||
|
||||
| 영역 | 배점 | 만점 기준 |
|
||||
|---|---:|---|
|
||||
| `evidence` 사실 충실성·근거 추적 | 25 | 모든 주장과 세부 표현이 근거 범위 안이며 모호한 사실을 확정하지 않음 |
|
||||
| `job_alignment` 목표 직무 적합성 | 20 | 필수 요건과 근거 있는 우대 요건을 중요도에 맞게 연결 |
|
||||
| `completeness` 정보 완결성 | 15 | 근거가 있는 핵심 기간·역할·행동·결과·산출물을 누락하지 않음 |
|
||||
| `korean_language` 한국어 품질 | 15 | 짧고 자연스럽고 문체가 일관되며 번역투·상투어·중복이 없음 |
|
||||
| `readability` 가독성·스캔 가능성 | 10 | 핵심 정보가 먼저 보이고 bullet과 문장 호흡을 빠르게 파악할 수 있음 |
|
||||
| `formatting` 형식·ATS 표현 | 5 | 표준 제목, 단일 읽기 순서, 추출 가능한 텍스트, 설정 형식을 준수 |
|
||||
| `consistency` 일관성 | 5 | 섹션 순서, 날짜 정밀도, 명칭, 숫자·단위, 문장 종결이 일관됨 |
|
||||
| `privacy` 개인정보·기밀 절제 | 5 | 필요한 정보만 포함하고 블라인드·동의·기밀 정책을 적용 |
|
||||
|
||||
총점은 하네스가 각 0~100점 영역 점수에 위 가중치를 곱해 계산합니다.
|
||||
평가 모델이 제공한 `overall_score`는 신뢰하지 않습니다. 릴리스 기준은
|
||||
가중 총점 90점 이상이며, `evidence`, `job_alignment`, `korean_language`,
|
||||
`privacy`는 각각 80점 이상이어야 합니다.
|
||||
|
||||
평가 모델의 영역 점수도 결정적 검사와 모순될 수 없습니다. 해당 영역에 blocking
|
||||
finding이 있으면 점수 상한은 59점, warning이 있으면 89점입니다. 상한 적용 후
|
||||
가중 총점을 다시 계산하므로 얇은 이력서에 `completeness: 99`를 제출해도 통과하지
|
||||
못합니다.
|
||||
|
||||
## 결정적 검사
|
||||
|
||||
LLM 평가 전에 빠르고 재현 가능한 검사를 수행합니다.
|
||||
|
||||
| 검사기 | 대표 규칙 |
|
||||
|---|---|
|
||||
| Schema | 필수 값, enum, 문자열 공백, 중복 ID |
|
||||
| Chronology | 구조화 날짜 범위 역전·진행 중 모순, 입력 정밀도 보존, 초안 날짜 형식 |
|
||||
| Grounding | 근거 없는 claim, 존재하지 않는 ID, 매핑에 없는 요구-근거 쌍, 미지원 숫자·단위·기술명·표현 |
|
||||
| Privacy/Confidentiality | 모드별 금지 필드, 본문 내 우회 노출, 숨겨진·기밀 근거 사용 |
|
||||
| Content | 플레이스홀더, 정규화한 중복 claim |
|
||||
| Output contract | 필수 섹션, 섹션별 글자 수, 제출 파일 형식, 날짜 형식, 섹션 상대 순서 |
|
||||
|
||||
정규식만으로 전체 의미 동일성을 보장하지 않습니다. 수치 검사는 claim의
|
||||
값과 단위가 연결 근거에서 확인되지 않으면 현재 `strict_evidence=true`
|
||||
릴리스 경로에서 blocking 오류로 처리합니다. 회사명·직함·자격명 같은
|
||||
일반적 의미 일치는 근거 어휘 게이트와 독립 평가를 함께 사용하며,
|
||||
규칙만으로 외부 진위를 인증하지는 않습니다.
|
||||
|
||||
## LLM 평가 계약
|
||||
|
||||
평가기는 문장을 새로 쓰지 않습니다. 평가기가 제출하는 원시 JSON은
|
||||
`report_id`, `draft_id`, 아래 8개 `category_scores`, `findings`만 담으며,
|
||||
하네스가 계산해야 할 점수·커버리지·fingerprint·임계값은 생성하지
|
||||
않습니다.
|
||||
|
||||
```json
|
||||
{
|
||||
"report_id": "report-001",
|
||||
"draft_id": "draft-001",
|
||||
"category_scores": {
|
||||
"evidence": 96,
|
||||
"job_alignment": 92,
|
||||
"completeness": 90,
|
||||
"korean_language": 94,
|
||||
"readability": 92,
|
||||
"formatting": 95,
|
||||
"consistency": 94,
|
||||
"privacy": 100
|
||||
},
|
||||
"findings": [
|
||||
{
|
||||
"finding_id": "finding-001",
|
||||
"code": "STYLE.GENERIC_CLAIM",
|
||||
"severity": "warning",
|
||||
"category": "korean_language",
|
||||
"claim_id": "claim-summary-02",
|
||||
"message": "근거는 있으나 지원 직무와의 연결이 추상적입니다.",
|
||||
"evidence_ids": ["ev-project-01"],
|
||||
"suggestion": "관련 근거의 행동과 결과를 한 문장으로 명시"
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
평가기의 모든 finding에는 `code`, 정확한 `claim_id` 또는 `location`, 이유,
|
||||
허용된 수정 방향이 있어야 합니다. 근거 없이 “더 전문적으로” 같은
|
||||
지시는 허용하지 않습니다.
|
||||
|
||||
평가기 응답을 스키마와 참조 계약으로 검증한 뒤, 서버 측 하네스가
|
||||
다음을 덮어써 최종 `QualityReport`를 만듭니다.
|
||||
|
||||
- 8개 영역 점수의 가중합인 `overall_score`
|
||||
- claim 근거 연결률인 `evidence_coverage`
|
||||
- 검증된 요구사항-근거 쌍을 사용한 우선순위 가중 `requirement_coverage`
|
||||
- 현재 초안의 `draft_fingerprint`
|
||||
- 후보자·초안·공고·분석·매핑·계획·설정·평가 정책을 묶는 `evaluation_fingerprint`
|
||||
- 파이프라인과 설정을 반영한 `minimum_*` 임계값
|
||||
|
||||
fingerprint는 평가 컨텍스트의 일치를 확인하지만 `QualityReport` 파일의 발급
|
||||
주체나 점수·finding 위변조를 인증하는 전자서명은 아닙니다. 신뢰할 수 없는
|
||||
사용자가 보고서 파일을 편집할 수 있는 배포는 서명된 attestation 검증을 릴리스
|
||||
게이트에 추가해야 합니다. 현재 구현과 프로덕션 필수 확장의 경계는
|
||||
[배포 보안 설계](deployment-security.md)를 참고하세요.
|
||||
|
||||
## 테스트 데이터와 지표
|
||||
|
||||
현재 테스트는 합성 프로필과 가짜 backend를 사용해 모델·참조 무결성,
|
||||
개인정보 최소화, 공공 블라인드, 숫자·단위·기술명 근거, 공고 제약,
|
||||
최대 2회 수정, 품질 fingerprint, Markdown 안전성을 검사합니다.
|
||||
|
||||
다음은 배포 전에 추가해야 할 회귀 매트릭스이며, 모두가 현재 자동화되어
|
||||
있다는 뜻은 아닙니다.
|
||||
|
||||
- 신입, 3년 경력, 10년 이상 경력, 직무 전환
|
||||
- 공백기, 동시 재직, 프리랜서, 사내 이동, 미완료 프로젝트
|
||||
- 수치 없는 성과, 단위가 불명확한 수치, 팀 성과만 있는 사례
|
||||
- 공공 블라인드, 회사 지정 양식, 영문 기술명이 많은 개발 직무
|
||||
- 공고 안 프롬프트 인젝션, 민감정보, 기밀 프로젝트명
|
||||
|
||||
근거 없는 주장 검출률, 민감정보 검출률, 수정 후 결함 재발률, 품질
|
||||
점수 분산, 문서 렌더 텍스트 보존율은 현재 하드 게이트와 별개의 평가
|
||||
지표입니다. 특히 문서 렌더 보존율은 DOCX/PDF/HWPX 어댑터가 추가된 뒤
|
||||
측정할 수 있습니다. 실제 이력서로 회귀셋을 만들 때에는 명시적 동의와
|
||||
비식별화가 필요합니다.
|
||||
@@ -0,0 +1,50 @@
|
||||
# 구조화 레코드 계약
|
||||
|
||||
`EvidenceItem.content`는 다양한 원자료를 수용하기 위한 원자적 사실 문장입니다.
|
||||
회사·직무·기간 같은 핵심 이력을 자유 문장에만 보관하면 정렬, 날짜 검증, 양식
|
||||
변환이 불안정해지므로 `CandidateProfile.records`에 다음 타입을 선택적으로
|
||||
병행 저장합니다.
|
||||
|
||||
| 타입 | 필수 구조 | 의미 |
|
||||
|---|---|---|
|
||||
| `CareerRecord` | 회사, 직무, 기간, 고용형태, 근거 ID | 금전적 보수를 받은 경력 (`paid=true`) |
|
||||
| `ExperienceRecord` | 역할, 기간, 경험 유형, 근거 ID | 프로젝트·봉사 등 무급 경험 (`paid=false`) |
|
||||
| `EducationRecord` | 학교, 학위, 기간, 상태, 근거 ID | 학력·교육 이력 |
|
||||
| `CertificationRecord` | 자격명, 발급기관, 취득일, 근거 ID | 자격·인증 이력 |
|
||||
|
||||
`EmploymentType`은 채용공고와 경력 레코드가 함께 쓰는 enum입니다. 정규직,
|
||||
시간제, 기간제, 계약직, 인턴, 프리랜서, 파견직, 기타를 구분합니다.
|
||||
|
||||
## 불변 조건
|
||||
|
||||
- 모든 레코드는 하나 이상의 기존 `EvidenceItem.evidence_id`를 참조합니다.
|
||||
- 회사·직무·학교·학위·자격명·발급기관·날짜 같은 핵심 값은 연결된 근거의
|
||||
`content`, `keywords`, `metrics`, `date_range` 정보에서 확인되어야 합니다.
|
||||
- 레코드 ID는 프로필 전체에서 유일하며 하나의 근거 ID는 한 레코드만 소유합니다.
|
||||
- 경력은 `career`, 학력은 `education`, 자격은 `certification` 범주의 근거만
|
||||
참조합니다. 무급 경험은 프로젝트·봉사·활동 계열 근거만 참조합니다.
|
||||
- 완료된 기간은 종료일이 필수입니다. 시작일 이후의 종료일만 허용하고, 진행 중인
|
||||
기간은 종료일을 함께 둘 수 없습니다.
|
||||
- 재학 상태는 진행 중 기간과 일치해야 하며 자격 만료일은 취득일보다 빠를 수 없습니다.
|
||||
- 입력 순서에 의존하지 않고 `*_chronological()`이 최신순 정본 뷰를 제공합니다.
|
||||
|
||||
날짜는 연, 연월, 연월일 정밀도를 그대로 보존합니다. 입력에 없는 일자를 임의로
|
||||
만들지 않으며 한국식 표기는 각각 `YYYY`, `YYYY.MM`, `YYYY.MM.DD`입니다.
|
||||
|
||||
## 개인정보·출력 경계
|
||||
|
||||
구조화 레코드는 현재 로컬 intake 및 검증 계층입니다. LLM에 전달되는
|
||||
`candidate_facts` whitelist나 Markdown 렌더러에 자동으로 추가되지 않습니다.
|
||||
따라서 학교명이나 회사명이 `public_blind` 필터, 기밀 근거 차단, 글자 수 제한,
|
||||
`ResumeDraft.fingerprint()`를 우회할 수 없습니다.
|
||||
|
||||
향후 구조화 레코드를 초안에 자동 반영하는 materializer는 다음 순서를 지켜야 합니다.
|
||||
|
||||
1. 민감·기밀 근거 제외 및 공고별 블라인드 필드 제거
|
||||
2. 허용된 근거 ID를 가진 `DraftClaim` 생성
|
||||
3. `ContentPlan` 및 공고 제약과의 참조 무결성 검사
|
||||
4. 결정적 validator와 독립 품질 평가 수행
|
||||
5. 승인된 `ResumeDraft` fingerprint에 품질 보고서를 결합한 뒤 렌더
|
||||
|
||||
레코드에서 곧바로 Markdown/DOCX 행을 만드는 공개 API는 정본 불변 조건을
|
||||
깨뜨리므로 제공하지 않습니다.
|
||||
Reference in New Issue
Block a user