Metadata-Version: 2.4
Name: reportgen-pipeline
Version: 0.2.5
Summary: LLM 기반 국책과제계획서(HWPX) 자동 작성 파이프라인
License: MIT License
        
        Copyright (c) 2026 Yoojin Nam
        
        Permission is hereby granted, free of charge, to any person obtaining a copy
        of this software and associated documentation files (the "Software"), to deal
        in the Software without restriction, including without limitation the rights
        to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
        copies of the Software, and to permit persons to whom the Software is
        furnished to do so, subject to the following conditions:
        
        The above copyright notice and this permission notice shall be included in all
        copies or substantial portions of the Software.
        
        THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
        IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
        FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
        AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
        LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
        OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
        SOFTWARE.
        
Project-URL: Homepage, https://github.com/kaismin82/ReportGen-pipeline
Project-URL: Repository, https://github.com/kaismin82/ReportGen-pipeline
Project-URL: Bug Tracker, https://github.com/kaismin82/ReportGen-pipeline/issues
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: python-hwpx>=0.1.0
Requires-Dist: lxml>=4.9.0
Requires-Dist: pypdf>=3.0.0
Requires-Dist: python-dotenv>=1.0.0
Provides-Extra: test
Requires-Dist: pytest>=7.0.0; extra == "test"
Requires-Dist: pytest-cov; extra == "test"
Dynamic: license-file

# ReportGen-pipeline

**LLM 기반 국책과제계획서(HWPX) 자동 작성 파이프라인** — v0.2.5

한국 국가 R&D 제안서(연구개발계획서) 양식을 참고자료(PDF·TXT·HWPX)와 함께 입력하면, 양식의 구조를 분석해 외부 LLM 에이전트가 채울 수 있는 매핑 요청(JSON)을 생성하고, 에이전트가 작성한 매핑을 적용해 HWPX를 완성하는 파이프라인입니다.

---

## 목차

- [동작 원리](#동작-원리)
- [주요 기능](#주요-기능)
- [아키텍처](#아키텍처)
- [설치](#설치)
- [실행 방법](#실행-방법)
- [Claude Code 스킬](#claude-code-스킬)
- [프로젝트 구조](#프로젝트-구조)
- [테스트](#테스트)
- [출처 및 라이선스](#출처-및-라이선스)

---

## 동작 원리

```
참고파일(PDF/TXT)  ─┐
                    ├──▶  [Phase 1] 양식 분석 & 매핑 요청 생성
HWPX 양식 템플릿  ──┘        StructureAnalyzer
user_data.json (선택)         · 표/단락 구조 파싱
                              · 표 5종 분류 (DATA/INSTR/SKIP/SCHED/IDENT)
                              · fill target 탐지
                              · 매핑 요청 JSON 출력 (request.json)
                              · 선택: Markdown 프롬프트 출력 (prompt.md)
                                    │
                                    ▼
                   ┌──── 외부 LLM 에이전트 (Sisyphus / Claude Code 등) ────┐
                   │  request.json 읽기 → FieldMapping[] 생성 → mappings.json  │
                   └────────────────────────────────────────────────────────┘
                                    │
                                    ▼
                          [Phase 2] 매핑 적용
                          SmartFillEngine
                          · replace(단락)    linesegarray 캐시 제거
                          · fill_cell(표 셀) 실존 좌표 검증
                          · insert_after     맑은 고딕 12pt 적용
                                    │
                                    ▼
                          검증 + 저장
                          verify_output       표 손실 / 단락 채움률 게이트
                          measure_fill_rate   DATA 표 기준 정확 측정
                                    │
                                    ▼
                          output.hwpx  ←  한글(Hangul)에서 바로 열기
```

### 핵심 설계 원칙

| 원칙 | 내용 |
|---|---|
| **양식 불변** | 작성요령(제출 시 삭제) 표·난해 표·신원 표는 원형 보존, 일반 데이터 표만 채움 |
| **줄바꿈 보호** | `<hp:linesegarray>` stale 캐시 제거 → 한글 재배치 트리거, 겹침 없음 |
| **동적 분류** | 간트 일정표·편성도·빈 격자를 패턴으로 자동 식별, 하드코딩 없음 |
| **외부 LLM** | 내용 생성은 외부 에이전트에 위임 — 제공사·모델 전환이 자유로움 |
| **정확한 측정** | SKIP/SCHED 표 제외, 원본 템플릿 기준 단락 채움률 계산 |

---

## 주요 기능

- **HWPX 구조 자동 분석**: TOC 탐지, 표 종류 분류(일반/instruction/난해/일정/신원), 단락 placeholder 인식
- **매핑 요청 아티팩트 생성**: 외부 LLM 에이전트가 읽을 수 있는 `request.json` + `prompt.md` 출력
- **FieldMapping 적용 엔진**: JSON 매핑 → HWPX XML 편집 (replace/fill_cell/insert_after)
- **폰트 일관성**: 맑은 고딕 12pt non-bold charPr 자동 적용, 줄바꿈 무결성 보장
- **참고자료 흡수**: PDF·TXT 파일을 자동 파싱해 요청 페이로드에 포함
- **구조 검증 게이트**: 표 손실·좌표 이상·단락 채움률을 파이프라인 직후 자동 검사
- **HWP → HWPX 변환**: Java fat JAR을 통한 바이너리 HWP → ZIP 기반 HWPX 변환

---

## 아키텍처

### 모듈 구성

```
scripts/
├── universal_pipeline.py        # 📌 메인 진입점 (CLI)
├── document_model.py            # 데이터 클래스 (DocumentElement, TableInfo, FieldMapping)
├── structure_analyzer.py        # HWPX 구조 분석 · 표/단락 분류
├── dynamic_template_analyzer.py # 분석 오케스트레이터 (LLM 호출 없음)
├── smart_fill_engine.py         # HWPX XML 편집 엔진 (replace/fill_cell/insert_after)
├── table_resolve.py             # 중첩 표 리졸버 (레이아웃 프레임 통과)
├── toc_detection.py             # TOC 탐지 · 표 분류 헬퍼 · blank 감지 regex
├── reference_reader.py          # PDF/TXT 참고파일 파서
├── schedule_handler.py          # 간트 일정표 메타 추출
├── verify_output.py             # 출력 구조 검증 게이트
├── measure_fill_rate.py         # 채움률 측정 (템플릿 기준 정확 계산)
├── hwpx_compat.py               # HWPX 패키지 호환 레이어
└── hwpx_utils.py                # 공유 유틸 (네임스페이스, 폰트 ID, env 로드)
```

### 표 분류 체계

| 분류 | 기준 | 처리 방식 |
|---|---|---|
| `DATA` | 일반 데이터 표 | LLM 채움 (fill_cell) |
| `INSTR` | 작성요령 포함 ("제출 시 삭제") | **보존** (건드리지 않음) |
| `SKIP` | 편성도·WBS·빈 격자 | 원형 보존 |
| `SCHED` | 간트 일정표 (추진내용+월별 컬럼) | 외부 에이전트가 처리 |
| `IDENT` | 연구책임자·기관 정보 | user_data 있으면 자동반영, 없으면 SKIP |

---

## 설치

### 사전 요구사항

- **Python 3.10+**
- **Java 11+** (HWP → HWPX 변환 시)
- **Maven** (Java 빌드 시)

### PyPI 설치 (권장, 자동 업그레이드 안내)

```bash
pip install reportgen-pipeline
```

`hwp-pipeline` CLI 명령이 등록됩니다. 실행 시 **최신 버전을 하루 1회 자동 확인**하여, 새 버전이 있으면 업그레이드 방법을 안내합니다:

```bash
pip install -U reportgen-pipeline   # 업그레이드
hwp-pipeline --version              # 현재 버전 확인
```

> ℹ️ pip은 설계상 자동으로 재설치하지 않습니다(안전상 정상 동작). 따라서 CLI는 gh·npm처럼 **"새 버전 있음 → `pip install -U` 하세요"** 알림만 출력합니다. 알림을 끄려면 `REPORTGEN_NO_UPDATE_CHECK=1` 또는 `--no-update-check`.
>
> 이 저장소는 **Private**이지만 PyPI 배포에는 영향이 없습니다 — PyPI는 저장소와 별개의 공개 레지스트리이므로, 이 채널은 누구나 접근할 수 있습니다.

### Standalone 바이너리 설치 (사내/협업자 전용, OpenCode 방식 진짜 자가 업데이트)

Python 없이 실행파일 하나로 쓰고 싶거나, **명령 없이 완전 자동으로 최신 버전을 유지**하고 싶다면 이 채널을 씁니다. GitHub Release에 `hwp-pipeline-<os>-<arch>[.exe]` 실행파일이 자동 첨부됩니다(`.github/workflows/build-binaries.yml`).

> ⚠️ **이 저장소가 Private이므로, 이 채널은 저장소 접근 권한이 있는 사람(사내 협업자)만 사용할 수 있습니다.** 익명 사용자는 GitHub API/자산 다운로드가 404로 막힙니다 — 공개 배포가 필요하면 위 PyPI 채널을 쓰세요.

```bash
# 1) 접근 권한이 있는 상태로 다운로드 (gh CLI 로그인되어 있으면 그대로 사용)
gh release download v0.2.4 --repo kaismin82/ReportGen-pipeline \
  --pattern "hwp-pipeline-<os>-<arch>*"   # 예: hwp-pipeline-windows-x86_64.exe

# 2) 실행
./hwp-pipeline-windows-x86_64.exe --template ... --emit-mapping-request request.json
```

이후부터는 **명령 없이 자동으로 최신 버전을 유지**합니다:
- 실행할 때마다 하루 1회 GitHub Releases 확인 → 새 버전이 있으면 **자기 실행파일을 교체하고 같은 명령으로 즉시 재실행**(사용자가 친 명령은 그대로 수행됨)
- 인증은 `gh auth token`(gh CLI 로그인 상태 재사용) 또는 `GITHUB_TOKEN`/`GH_TOKEN` 환경변수로 자동 처리
- 지금 바로 확인/적용하려면: `hwp-pipeline --upgrade`
- 끄려면: `REPORTGEN_NO_AUTOUPDATE=1`

이게 바로 pip 채널과의 근본적 차이입니다 — pip 패키지는 공유 환경/고정 버전을 깰 위험이 있어 "알림만" 하지만, 이 standalone 실행파일은 자기 자신만 소유하므로 OpenCode의 `opencode upgrade`처럼 **실제 자가 교체**가 가능합니다.

### 소스에서 설치 (개발용)

```bash
git clone https://github.com/kaismin82/ReportGen-pipeline.git
cd ReportGen-pipeline

# 의존성만 설치
pip install -r requirements.txt

# 또는 editable 설치 (hwp-pipeline CLI 명령 포함)
pip install -e .

# (선택) HWP→HWPX 변환기 빌드
bash setup.sh --java
```

`pip install -e .` 또는 PyPI 설치 시 `hwp-pipeline` CLI 명령이 등록되어 `python scripts/universal_pipeline.py` 대신 사용할 수 있습니다.

### ⚠️ conda 환경 주의사항

conda 환경에서는 `hwpx`라는 **별개의** 패키지가 설치되어 있을 수 있습니다.

```bash
pip install python-hwpx --force-reinstall
```

> `pip install hwpx`(❌)와 `pip install python-hwpx`(✅)는 서로 다른 패키지입니다.

---

## 실행 방법

### Phase 1 — 양식 분석 & 매핑 요청 생성

```bash
# Linux / macOS
python scripts/universal_pipeline.py \
  --template  input/연구개발계획서_양식.hwpx \
  --reference input/과제요약.txt "input/RFP.pdf" \
  --data      user_data.json \
  --emit-mapping-request request.json \
  --prompt-output        prompt.md
```

```powershell
# Windows PowerShell
python scripts/universal_pipeline.py `
  --template  input/연구개발계획서_양식.hwpx `
  --reference input/과제요약.txt "input/RFP.pdf" `
  --data      user_data.json `
  --emit-mapping-request request.json `
  --prompt-output        prompt.md
```

이 단계는 LLM API를 호출하지 않습니다. 생성된 `request.json`과 `prompt.md`를 외부 LLM 에이전트(Claude Code, OpenCode, Sisyphus 등)에 전달하면 에이전트가 `mappings.json`을 작성합니다.

### Phase 2 — 매핑 적용 & HWPX 출력

```bash
python scripts/universal_pipeline.py \
  --template input/연구개발계획서_양식.hwpx \
  --mappings mappings.json \
  --output   output/result.hwpx \
  --measure
```

### 전체 옵션

```bash
python scripts/universal_pipeline.py \
  --template   <HWPX 양식 경로>              # 필수
  --output     <출력 HWPX 경로>              # Phase 2 필수
  --reference  <파일1> <파일2> ...            # 참고파일 (PDF/TXT/HWPX)
  --data       <user_data.json>               # 추가 구조화 데이터 (선택)
  --instructions "추가 지시문"                # 에이전트 추가 지시 (선택)
  --emit-mapping-request <request.json>       # Phase 1: 매핑 요청 생성
  --prompt-output <prompt.md>                 # Phase 1: Markdown 프롬프트 저장 (선택)
  --mappings   <mappings.json>                # Phase 2: 매핑 적용
  --analysis-output <분석결과.json>            # 양식 분석 결과 저장 (선택)
  --measure                                   # 완료 후 채움률 출력
  --verbose
```

### HWP → HWPX 변환 후 실행

```bash
# HWP를 HWPX로 먼저 변환
java -jar java/hwp2hwpx-fat.jar input/양식.hwp input/양식.hwpx

# Phase 1 실행
python scripts/universal_pipeline.py \
  --template input/양식.hwpx \
  --emit-mapping-request request.json
```

### 채움률 측정 (별도)

```bash
python scripts/measure_fill_rate.py \
  --file     output/result.hwpx \
  --template input/양식.hwpx
```

출력 예시:
```
=======================================================
Fill Rate Report: result.hwpx  [template]
=======================================================
TABLE CELLS (DATA tables only, SKIP/SCHED excluded):
  Total data cells  : 86
  Filled cells      : 86
  Fill rate         : 100.0%  [##################################################]

PARAGRAPH TARGETS (from template):
  Total targets     : 66
  Filled            : 60
  Fill rate         : 90.9%  [#############################################-----]
=======================================================
```

---

## Claude Code 스킬

`/hwp-pipeline` 스킬을 Claude Code에서 사용할 수 있습니다. 두 가지 경로가 있습니다.

### 방법 1 — 플러그인으로 설치 (권장, 자동 업그레이드)

v0.2.3부터 이 저장소는 **Claude Code 플러그인 마켓플레이스**를 겸합니다. 최초 1회만 마켓플레이스를 등록하고 플러그인을 설치하면, 이후 새 릴리즈가 나올 때 **백그라운드로 자동 업데이트**됩니다.

> ⚠️ 이 저장소가 **Private**이므로, `/plugin marketplace add`도 저장소 접근 권한이 있는 사람만 사용할 수 있습니다(사내 협업자 전용). 공개 배포가 필요하면 저장소를 Public으로 전환해야 합니다.

```
# 최초 1회
/plugin marketplace add kaismin82/ReportGen-pipeline
/plugin install hwp-pipeline@reportgen-marketplace
```

이후 유지관리자가 새 버전(`hwp-pipeline--vX.Y.Z` 태그)을 릴리즈하면:

1. Claude Code가 새 태그를 **자동 감지·다운로드** (third-party 마켓플레이스는 자동 업데이트를 한 번 켜야 함)
2. 활성화:
   - **다음 세션(재시작)** 시 → **명령 없이 자동 활성화** ✅
   - **현재 세션에서 즉시** 반영하려면 → `/reload-plugins` **한 번** 실행

> ⚠️ **"설치 즉시 자동 활성화"는 Claude Code 구조상 불가능합니다.** 플러그인은 활성화되기 전에는 자기 훅을 실행할 수 없어(닭-달걀), 설치가 `/reload-plugins`를 스스로 실행하게 만들 방법이 없습니다. 최초 설치도 마찬가지로 `/reload-plugins` 1회 또는 재시작이 필요합니다. **가장 매끄러운 경로는 "설치 후 Claude Code 재시작"** — 이 경로만 추가 명령이 필요 없습니다. (Claude Code 플러그인은 pull 기반: 사용자 쪽이 마켓플레이스를 폴링)

### 방법 2 — 저장소에서 직접 사용 (프로젝트 스코프)

이 저장소를 클론해 작업하면 `.claude/skills/hwp-pipeline/SKILL.md`가 프로젝트 스코프 스킬로 인식되어 별도 설치 없이 바로 `/hwp-pipeline`을 호출할 수 있습니다. 업데이트는 `git pull`로 받습니다.

### 사용법 (공통)

```
/hwp-pipeline 스킬을 활용하여 아래 양식에 맞게 연구개발계획서를 작성해줘.
- template: input/연구개발계획서_양식.hwpx
- 참고 파일들: input/과제요약.txt input/RFP.pdf
- 출력 파일: output/result.hwpx
```

스킬이 자동으로:
1. Phase 1 (`--emit-mapping-request`) 실행 → `request.json` 생성
2. 참고자료(PDF/TXT) + 웹 검색을 바탕으로 `mappings.json` 작성
3. Phase 2 (`--mappings`) 실행 → 최종 HWPX 출력
4. `--measure`로 채움률 확인

> **참고**: 스킬은 작성 지시와 오케스트레이션을 담당하고, 실제 HWPX 편집은 `scripts/universal_pipeline.py`(또는 `pip install`로 등록되는 `hwp-pipeline` CLI)가 수행합니다. 플러그인만 단독 설치한 경우 CLI(저장소 또는 pip 패키지)가 별도로 필요합니다.

### 버전/릴리즈 관리 — 단일 진실원

버전 문자열은 여러 곳(`pyproject.toml`, `universal_pipeline.py`, README 헤더, `plugin.json`)에 흩어져 있어 수동 관리 시 누락되기 쉽습니다. 이를 `scripts/bump_version.py`로 일원화합니다:

```bash
# 버전만 일괄 갱신 (모든 위치 + SKILL.md 미러 동기화)
python scripts/bump_version.py 0.2.4

# 갱신 + 커밋 + 태그(v0.2.4 & hwp-pipeline--v0.2.4) + 푸시 + GitHub 릴리즈
python scripts/bump_version.py 0.2.4 --release

# CI 일관성 검사 (불일치 시 실패) — .github/workflows/ci.yml 에서 자동 실행
python scripts/bump_version.py --check
```

두 SKILL.md 사본(`.claude/skills/…`와 플러그인 `hwp-pipeline/skills/…`)은 이 스크립트가 항상 동일하게 동기화하며, CI가 어긋남을 차단합니다.

### PyPI 자동 게시 (릴리즈 시)

`bump_version.py … --release`로 GitHub Release가 발행되면, `.github/workflows/publish.yml`이 sdist/wheel을 빌드해 **PyPI에 자동 게시**합니다. 게시는 **PyPI Trusted Publishing(OIDC)** 을 사용하므로 API 토큰/시크릿이 필요 없습니다.

**최초 1회 설정** (저장소 소유자가 PyPI에서 직접 — 자동화 불가):

1. [pypi.org](https://pypi.org) 로그인 → **Publishing → Add a pending publisher** 등록
   - PyPI Project Name: `reportgen-pipeline`
   - Owner: `kaismin82` / Repository: `ReportGen-pipeline`
   - Workflow: `publish.yml` / Environment: `pypi`
2. GitHub 저장소 **Settings → Environments** 에서 `pypi` 환경 생성

이후 릴리즈마다 CI가 자동으로 새 버전을 PyPI에 올립니다. 사용자는 `pip install -U reportgen-pipeline`로 업그레이드하며, CLI가 새 버전을 자동 안내합니다.

---

## 프로젝트 구조

```
ReportGen-pipeline/
├── scripts/
│   ├── universal_pipeline.py        # 메인 CLI 진입점 (hwp-pipeline 명령)
│   ├── document_model.py            # 데이터 클래스
│   ├── structure_analyzer.py        # HWPX 구조 분석
│   ├── dynamic_template_analyzer.py # 분석 오케스트레이터
│   ├── smart_fill_engine.py         # XML 편집 엔진
│   ├── table_resolve.py             # 중첩 표 리졸버
│   ├── toc_detection.py             # TOC 탐지 · 표 분류 · blank regex
│   ├── reference_reader.py          # PDF/TXT 파서
│   ├── schedule_handler.py          # 간트 메타 추출
│   ├── verify_output.py             # 검증 게이트
│   ├── measure_fill_rate.py         # 채움률 측정
│   ├── hwpx_compat.py               # HWPX 호환 레이어
│   ├── hwpx_utils.py                # 공유 유틸
│   ├── fix_namespaces.py            # 네임스페이스 정규화 CLI
│   ├── text_extract.py              # 텍스트 추출 CLI
│   ├── zip_replace_all.py           # 전역 placeholder 치환 CLI
│   ├── update_check.py             # PyPI 최신 버전 확인·업그레이드 안내 (pip 채널)
│   ├── self_update.py              # standalone 바이너리 자가 업데이트 (private repo, 인증 필요)
│   ├── bump_version.py             # 버전 일괄 갱신·릴리즈·CI 일관성 검사
│   └── archive/                     # 구버전 스크립트 (vision 실험 등)
├── tests/
│   ├── test_output_qa.py            # 불변식 pytest (lineseg·셀 안착·리졸버)
│   ├── test_smart_fill_engine_p0.py # 엔진 단위 테스트
│   ├── test_structure_analyzer_p1.py
│   ├── test_mapping_artifact_handoff.py  # Phase 1/2 CLI 통합 테스트
│   ├── test_self_update.py          # self_update 순수 로직 테스트
│   └── test_e2e_pipeline.py         # E2E 통합 테스트
├── java/
│   ├── Convert.java                 # HWP→HWPX CLI 래퍼
│   ├── pom.xml                      # Maven (shade plugin)
│   └── hwp2hwpx-fat.jar             # 사전 빌드 JAR
├── .claude-plugin/
│   └── marketplace.json             # Claude Code 마켓플레이스 카탈로그
├── hwp-pipeline/                     # Claude Code 플러그인 (배포용)
│   ├── .claude-plugin/
│   │   └── plugin.json               # 플러그인 매니페스트 (name·version)
│   └── skills/hwp-pipeline/
│       └── SKILL.md                  # 플러그인 번들 스킬 (배포 정본)
├── .claude/
│   └── skills/hwp-pipeline/
│       └── SKILL.md                  # 프로젝트 스코프 스킬 (플러그인 미러, 저장소 내 사용)
├── .github/workflows/
│   ├── ci.yml                        # 테스트·린트·버전 일관성·빌드 검증
│   ├── publish.yml                   # 릴리즈 시 PyPI 자동 게시 (Trusted Publishing)
│   └── build-binaries.yml            # 릴리즈 시 플랫폼별 standalone 실행파일 빌드·첨부
├── docs/
│   └── solution_proposal.html       # 설계 제안서
├── .env.example                     # 환경변수 템플릿
├── requirements.txt
├── pyproject.toml                   # 패키지 메타데이터 · 빌드 설정 (PyPI)
└── setup.sh                         # 의존성 설치 스크립트
```

---

## 테스트

```bash
# 전체 테스트 실행
pytest tests/ -v

# 핵심 불변식 테스트만
pytest tests/test_output_qa.py tests/test_smart_fill_engine_p0.py -v

# Phase 1/2 CLI 통합 테스트
pytest tests/test_mapping_artifact_handoff.py -v
```

**주요 테스트 커버리지**

| 테스트 파일 | 검증 내용 |
|---|---|
| `test_output_qa.py` | lineseg 부재·셀 안착·리졸버 불변식 |
| `test_smart_fill_engine_p0.py` | replace/fill_cell/linesegarray strip |
| `test_structure_analyzer_p1.py` | TOC 탐지·헤더 추출·instruction 표 |
| `test_mapping_artifact_handoff.py` | Phase 1/2 CLI 정상 동작 |
| `test_e2e_pipeline.py` | 구조 분석 → SmartFillEngine 전체 흐름 |
| `test_korean_edge_cases.py` | 전각 괄호·ZWSP·전각 공백 blank 감지 |
| `test_schedule_table.py` | 간트 표 탐지·메타 추출 |

---

## 출처 및 라이선스

### 직접 활용 오픈소스

| 프로젝트 | 역할 | 라이선스 | 링크 |
|---|---|---|---|
| **python-hwpx** | HWPX 파일 파싱·패키징 (`HwpxPackage`) | MIT | [PyPI](https://pypi.org/project/python-hwpx/) |
| **hwp2hwpx** by neolord0 | HWP → HWPX 바이너리 변환 (Java) | Apache 2.0 | [GitHub](https://github.com/neolord0/hwp2hwpx) |
| **@ohah/hwpjs** by ohah | HWP → JSON/Markdown/HTML (Node.js) | MIT | [GitHub](https://github.com/niceoasi/hwpjs) |
| **lxml** | HWPX XML 파싱 및 조작 | BSD | [lxml.de](https://lxml.de/) |
| **python-dotenv** | `.env` 환경변수 로드 | BSD | [GitHub](https://github.com/theskumar/python-dotenv) |
| **pypdf** | PDF 텍스트 추출 | BSD | [GitHub](https://github.com/py-pdf/pypdf) |

### 참고 및 영감

| 항목 | 설명 |
|---|---|
| **hwp-pipeline (Yoojin-nam)** | 본 프로젝트의 기반이 된 Claude Code skill. HWPX 편집 파이프라인 초기 설계 참고. [GitHub](https://github.com/Yoojin-nam/hwp-pipeline) |
| **HWP/HWPX 포맷 명세** | 한글과컴퓨터 HWPML 2011/2016 paragraph 네임스페이스 구조 |
| **Claude Code** by Anthropic | AI-assisted development 환경. [docs](https://docs.anthropic.com/en/docs/claude-code) |

### 라이선스

[MIT License](LICENSE) — 자유롭게 사용·수정·배포 가능합니다.

---

## 자주 묻는 질문

**Q. `ImportError: cannot import name 'HwpxPackage' from 'hwpx'` 오류가 납니다.**
> conda 환경에 `hwpx` (별개 패키지)가 설치되어 있어 충돌이 발생한 것입니다.
> ```bash
> pip install python-hwpx --force-reinstall
> ```

**Q. Phase 1 실행 후 어떤 파일을 외부 에이전트에 전달하나요?**
> `--emit-mapping-request`로 저장된 `request.json`과 `--prompt-output`으로 저장된 `prompt.md`를 에이전트에 전달하세요. 에이전트는 `FieldMapping[]` JSON 배열을 `mappings.json`으로 작성해야 합니다.

**Q. 단락 채움률이 낮게 나옵니다.**
> `--measure` 옵션 사용 시 반드시 `--template` 파라미터를 함께 지정하세요. FILL 품질은 외부 에이전트(Sisyphus)의 모델 성능에 따라 달라집니다.

**Q. 작성요령 표가 채워집니다.**
> `structure_analyzer.py`의 `_is_instruction_table()`이 "제출 시 삭제" 마커를 강한 신호로 탐지합니다. 양식에 해당 마커가 없는 경우 다른 instruction 신호를 `_DELETE_RE`에 추가하세요.

**Q. 추진 일정표(간트)가 이상하게 채워집니다.**
> 간트 표의 구조 메타는 `schedule_handler.detect_schedule_meta()`로 분석됩니다. 외부 에이전트에 전달되는 `request.json`에 이 메타가 포함되므로, 에이전트 프롬프트에서 간트 처리 방식을 조정하세요.
