---
name: dart-notebooklm
description: >
  DART(전자공시시스템)에서 기업의 정기보고서(사업보고서·반기보고서·분기보고서)를
  자동으로 PDF 다운로드하여 NotebookLM 노트북에 소스로 등록하고,
  등록된 소스를 기반으로 AI 분석 인사이트가 포함된 종합 한국어 기업 분석 보고서(.docx)를 생성하는 스킬.
  사용자가 "DART", "사업보고서", "공시", "기업 분석", "종합 보고서 생성", "NotebookLM 등록" 등을
  언급하거나, 특정 기업의 공시 문서를 기반으로 분석 보고서를 요청할 때 반드시 이 스킬을 사용.
  종목코드나 회사명만 제시해도 트리거됨.
compatibility:
  python: ">=3.9"
  uv : requests, beautifulsoup4, python-docx
  mcp: notebooklm-mcp (NotebookLM MCP 연결 필요)
  env:
    DART_API_KEY: "DART Open API 인증키 (https://opendart.fss.or.kr 발급)"
---

# DART → NotebookLM 기업 분석 스킬

## 전체 워크플로우

```
[사용자 입력] 회사명/종목코드, 보고서 종류, 연도
     ↓
[Step 1] DART API → corp_code 조회
     ↓
[Step 2] DART API → rcept_no(접수번호) 조회
     ↓
[Step 3] DART 웹 → dcm_no 파싱 → PDF 다운로드
     ↓
[Step 4] NotebookLM MCP → 노트북 생성 + PDF 소스 등록
     ↓
[Step 5] NotebookLM MCP → notebook_query로 섹션별 분석 
     ↓
[Step 6] 보고서 조합 → 채팅 출력 + .docx 파일 저장 (AI 분석 내용 포함)
```

현재 이 저장소에서 직접 구현·관리하는 스크립트는 다음 두 가지다.

- `scripts/dart_fetch.py` — Step 1~3 담당
- `scripts/build_report_docx.py` — Step 6 담당

Step 4~5의 NotebookLM MCP 단계는 권장 흐름에 포함되지만, 현재 저장소에 전용 스크립트는 없다.

---

## Step 1 — 사용자 입력 수집

스킬 시작 시 다음을 확인한다. 이미 대화에서 제공된 경우 재질문 생략.

| 항목 | 필수 | 기본값 |
|------|------|--------|
| 회사명 또는 종목코드 | ✅ | - |
| 보고서 종류 | ✅ | 사업보고서 |
| 사업연도 | ✅ | 직전연도 |

**보고서 코드 매핑:**
- 사업보고서: `11011`
- 반기보고서: `11012`
- 1분기보고서: `11013`
- 3분기보고서: `11014`

---

## Step 2~3 — `dart_fetch.py` 실행

회사명 또는 종목코드로 `corp_code`를 찾고, 사업연도·보고서 종류에 맞는 `rcept_no`를 조회한다.
DART 웹의 PDF 다운로드 팝업을 파싱해 실제 PDF 링크를 따라가며, DART가 내려주는 원본 파일명으로 저장한다.
PDF 다운로드가 실패하면 OpenDART `document.xml` ZIP에서 텍스트를 추출해 `{rcept_no}_document.txt`로 저장한다.

```bash
python scripts/dart_fetch.py \
  --company "씨에스윈드" \
  --report-type 11011 \
  --year 2024 \
  --download-pdf \
  --pdf-output /tmp/report.pdf \
  --output /tmp/dart_result.json
```

**주요 옵션:**

| 옵션 | 설명 |
|------|------|
| `--company` | 회사명으로 조회 |
| `--stock-code` | 종목코드로 조회 (`--company`와 택일) |
| `--report-type` | 보고서 코드 또는 이름 (기본: `11011`) |
| `--year` | 공시연도가 아닌 **사업연도** 기준 |
| `--download-pdf` | PDF 다운로드 시도 |
| `--pdf-output` | PDF 저장 경로. `Content-Disposition` 헤더의 파일명이 우선 적용될 수 있음 |
| `--output` | 결과 JSON 저장 경로 (기본: `./dart_result.json`) |

**PDF URL 패턴 (비공식):**
- 뷰어 페이지: `https://dart.fss.or.kr/dsaf001/main.do?rcpNo={rcept_no}`
- PDF 다운로드: `https://dart.fss.or.kr/pdf/download/main.do?rcp_no={rcept_no}&dcm_no={dcm_no}`

`dcm_no`는 뷰어 페이지 HTML에서 `openPdfDownload('{rcept_no}', '{dcm_no}')` 패턴을 파싱해 추출.

**주의사항:**
- User-Agent 헤더 설정 필수 (없으면 403)
- 요청 간 1~2초 sleep 권장 (rate limit 방지)
- 사업보고서(`11011`)는 다음 해 상반기에 접수될 수 있으므로, 다음 해 6월까지 포함해 조회함
- `Content-Disposition` 한글 파일명은 cp949 → euc-kr → utf-8 순서로 디코딩 시도

**결과 JSON 계약:**

```json
{
  "corp_name": "씨에스윈드",
  "corp_code": "00000000",
  "rcept_no": "20250331000000",
  "report_nm": "사업보고서 (2024.12)",
  "rcept_dt": "20250331",
  "requested_pdf": true,
  "pdf_path": "./씨에스윈드_사업보고서.pdf",
  "text_path": null,
  "source_type": "pdf",
  "dcm_no": "10293847",
  "pdf_error": null
}
```

해석 기준:
- `source_type = "pdf"` — PDF 다운로드 성공
- `source_type = "text"` — PDF 실패 후 ZIP 원문 텍스트 fallback 사용
- `pdf_path` — PDF 저장 성공 시에만 채워짐
- `text_path` — fallback 텍스트 추출 성공 시에만 채워짐

---

## Step 4 — NotebookLM MCP로 노트북 생성 및 소스 등록

NotebookLM MCP 툴을 순서대로 호출한다.

```
1. notebook_create(title="{회사명}")
2. source_add(notebook_id=..., source_type="file", content="/tmp/report.pdf")
3. 처리 완료 대기 (source_list로 상태 확인)
```

노트북 제목 예시: `"씨에스윈드 사업보고서 2024"`

---

## Step 5 — NotebookLM 기반 기업 분석 보고서 생성

노트북이 준비되면 `notebook_query`를 섹션별로 순차 호출한다.
각 쿼리는 **구체적이고 답변 형식을 지정**해야 품질이 높아진다.

### 쿼리 템플릿

```python
QUERIES = {
    "company_overview": """
        이 기업의 사업 개요를 다음 형식으로 작성해주세요:
        - 설립연도, 주요 사업 영역
        - 핵심 제품/서비스 3~5가지와 각각의 매출 비중
        - 주요 고객 및 시장 (지역별 포함)
        - 경쟁사 대비 포지셔닝
        보고서의 실제 내용에 근거하여 작성하세요.
    """,

    "financial_summary": """
        최근 보고서 기준 재무 실적을 요약해주세요:
        - 매출액 (전년 대비 증감률)
        - 영업이익 및 영업이익률
        - 순이익 및 순이익률
        - 부채비율, 유동비율 등 재무건전성 지표
        - 주요 재무 변화 원인
        숫자는 보고서에 기재된 정확한 수치를 사용하세요.
    """,

    "growth_drivers": """
        이 기업의 성장 동력과 투자 포인트를 분석해주세요:
        - 중장기 성장 전략 및 신사업
        - 수주 현황 및 파이프라인
        - 시장 확대 기회
        - 경쟁우위 (기술력, 특허, 시장점유율 등)
        보고서 내 경영진 코멘트와 사업계획을 반영하세요.
    """,

    "risk_factors": """
        이 기업의 주요 리스크 요인을 분석해주세요:
        - 사업 리스크 (경쟁, 기술 변화, 고객 집중도)
        - 재무 리스크 (환율, 이자율, 유동성)
        - 규제/정책 리스크
        - 공급망 및 원가 리스크
        각 리스크의 심각도와 대응 방안도 포함하세요.
    """,

    "valuation_comment": """
        보고서 내용을 바탕으로 밸류에이션 관련 코멘트를 작성해주세요:
        - 현재 수익성 수준과 개선 방향
        - 업계 평균 대비 재무 지표 비교 (보고서 내 언급된 내용 기준)
        - 향후 실적 방향성에 영향을 줄 핵심 변수
        - 투자 판단 시 주목해야 할 지표
        투자 권유가 아닌 정보 제공 목적으로 작성하세요.
    """
}
```

**중요: 종합 보고서 생성을 위해 분석 결과는 반드시 JSON 파일로 저장해야 한다.**
분석이 완료되면 다음과 같은 형식으로 `/tmp/analysis_result.json` 등에 저장한다.
```json
{
  "company_overview": "...분석 결과...",
  "financial_summary": "...분석 결과...",
  "growth_drivers": "...분석 결과...",
  "risk_factors": "...분석 결과...",
  "valuation_comment": "...분석 결과..."
}
```

---

## Step 6 — 보고서 조합 및 출력

### 채팅 출력 (인라인)

수집한 섹션을 마크다운으로 조합하여 채팅창에 출력한다.

```markdown
# {회사명} 기업 분석 보고서
**분석 기준:** {보고서종류} {연도} | **데이터 소스:** DART 공시 원문

---
## 1. 사업 개요
{company_overview 쿼리 결과}

## 2. 재무 실적 요약
{financial_summary 쿼리 결과}

## 3. 성장 동력 및 투자 포인트
{growth_drivers 쿼리 결과}

## 4. 리스크 요인 분석
{risk_factors 쿼리 결과}

## 5. 밸류에이션 코멘트
{valuation_comment 쿼리 결과}

---
*본 보고서는 DART 공시 원문을 기반으로 AI가 생성한 참고자료이며,
투자 권유 목적이 아닙니다.*
```

### `build_report_docx.py`로 종합 보고서 저장

`dart_fetch.py` 결과 JSON과 Step 5에서 생성한 AI 분석 JSON을 모두 읽어 종합 리포트를 생성한다.

```bash
python scripts/build_report_docx.py \
  --input /tmp/dart_result.json \
  --analysis-json /tmp/analysis_result.json \
  --output /mnt/user-data/outputs/{회사명}_종합분석보고서_{연도}.docx
```

**주요 옵션:**

| 옵션 | 설명 |
|------|------|
| `--input` | `dart_fetch.py` 결과 JSON 경로 (기본: `./dart_result.json`) |
| `--analysis-json` | **(필수)** AI 분석 결과 JSON 경로 |
| `--output` | 생성할 DOCX 경로 (기본: `./dart_report.docx`) |
| `--text-source` | 본문 발췌용 텍스트 파일 경로. 생략 시 자동 탐색 |
| `--excerpt-length` | 본문 발췌 최대 글자 수 (기본: `12000`) |

**DOCX 구성:**
- 표지 성격의 제목(회사명)과 부제(보고서명)
- 기본 정보 메타데이터 표
- 수집 결과 요약
- **🚀 AI 기업 분석 (사업 개요, 재무 실적, 성장 동력, 리스크, 밸류에이션)**
- fallback 텍스트가 있을 경우 본문 발췌 섹션 추가

완료 후 `present_files` 툴로 파일을 사용자에게 제공한다.

---

## 오류 처리

| 상황 | 대응 |
|------|------|
| corp_code 미조회 | 회사명 재확인 요청, 종목코드 입력 유도 |
| PDF 없음 (구형 공시) | ZIP 원문 다운로드 → HTML 텍스트 변환 후 텍스트 소스로 등록 |
| NotebookLM 소스 처리 지연 | 30초 간격으로 최대 5회 status 재확인 |
| notebook_query 응답 빈약 | 쿼리를 더 구체적으로 재시도 (최대 2회) |

---

## 환경 변수 설정

DART API 키는 절대 스킬 파일이나 코드에 직접 입력하지 않는다.

### 방법 A — 터미널 세션에 일시 설정 (빠른 테스트용)

```bash
export DART_API_KEY="발급받은_40자리_키"
python scripts/dart_fetch.py ...
```

세션 종료 시 자동 소멸. 매번 재설정 필요.

### 방법 B — `~/.bashrc` 또는 `~/.zshrc`에 영구 등록 (권장)

```bash
echo 'export DART_API_KEY="발급받은_40자리_키"' >> ~/.bashrc
source ~/.bashrc
```

설정 후 `echo $DART_API_KEY`로 확인.

### PowerShell 환경

```powershell
$env:DART_API_KEY="발급받은_40자리_키"
```

### Claude 대화 중 사용 시

사용자가 대화 중 DART API 키를 제공한 경우, 스크립트 실행 시 환경변수로 주입하여 사용한다.
키는 대화 컨텍스트 내에서만 사용하며, 파일에 기록하거나 출력하지 않는다.

```bash
DART_API_KEY="사용자_제공_키" python scripts/dart_fetch.py \
  --company "씨에스윈드" --report-type 11011 --year 2024 \
  --download-pdf --pdf-output /tmp/report.pdf
```

### API 키 발급

https://opendart.fss.or.kr/guide/main.jsp?menu=080
(무료, 하루 10,000건 요청 한도)

---

## 수정 원칙

- DART 뷰어 구조, PDF 링크 구조, 파일명 인코딩 처리 변경 → `scripts/dart_fetch.py` 수정
- DOCX 형식, 요약 구성, 포함 섹션 변경 → `scripts/build_report_docx.py` 수정
- 후속 도구와의 호환성이 깨지지 않도록 결과 JSON 계약은 가능한 한 유지한다
