# 补丁4·get_chapter_content 章节内容直读工具

## 问题

模型想读第500章内容，但 search_notion 只能搜到633-639（最近编辑的），list_subpages 被折叠只显示总数。模型搜不到中间章节的页面ID。

## 解法

从 chaishu_page_scan SQLite表直接查 page_id → 调 Notion API 读内容。不走搜索。

---

## 第一步：notion_[tools.py](http://tools.py) 末尾追加函数

```python
# ============ 补丁4: get_chapter_content 章节直读 ============
def get_chapter_content(args):
    """从SQLite查章节page_id，直接读Notion页面内容"""
    import sqlite3
    chapter_num = args.get("chapter_num")
    if not chapter_num:
        return "请提供 chapter_num 参数，例如 500"
    try:
        chapter_num = int(chapter_num)
    except:
        return f"chapter_num 必须是数字，收到: {chapter_num}"

    db_path = os.path.expanduser('~/chenxing-aircraft/chenxing.db')
    conn = sqlite3.connect(db_path)
    cur = conn.cursor()
    cur.execute("SELECT page_id, title, has_content FROM chaishu_page_scan WHERE chapter_num = ?", (chapter_num,))
    row = cur.fetchone()
    conn.close()

    if not row:
        return f"第{chapter_num}章不存在。全书639章（有10章跳号：385/407/415/451/530/538/542/549/569/571）"

    page_id, title, has_content = row
    if not has_content:
        return f"第{chapter_num}章页面存在但内容为空。标题: {title}"

    # 用现有的 _read_blocks 读页面内容
    try:
        children = notion.blocks.children.list(block_id=page_id)
        blocks = children.get("results", [])
        output_lines = [f"📖 {title}", ""]
        for b in blocks:
            btype = b.get("type", "")
            if btype in ("paragraph", "heading_1", "heading_2", "heading_3", "bulleted_list_item", "numbered_list_item", "quote", "callout", "toggle"):
                rich = b.get(btype, {}).get("rich_text", [])
                text = "".join(r.get("plain_text", "") for r in rich)
                if btype.startswith("heading"):
                    level = btype[-1]
                    output_lines.append(f"{'#' * int(level)} {text}")
                elif btype == "bulleted_list_item":
                    output_lines.append(f"- {text}")
                elif btype == "numbered_list_item":
                    output_lines.append(f"1. {text}")
                elif btype == "quote":
                    output_lines.append(f"> {text}")
                else:
                    output_lines.append(text)
            elif btype == "table":
                output_lines.append("[表格内容]")
            elif btype == "divider":
                output_lines.append("---")

        result = "\n".join(output_lines)
        # 截断保护
        if len(result) > 6000:
            result = result[:6000] + f"\n\n...（内容截断，完整内容共{len(result)}字符）"
        return result
    except Exception as e:
        return f"找到第{chapter_num}章（ID: {page_id}），但读取失败: {e}"
```

---

## 第二步：[main.py](http://main.py) 的 NOTION_TOOLS 数组追加工具定义

在 `NOTION_TOOLS = [...]` 数组末尾（最后一个 `}` 之前）追加：

```python
{
    "type": "function",
    "function": {
        "name": "get_chapter_content",
        "description": "读取拆书的某一章的完整内容。直接从本地数据库查找章节，不需要先搜索。",
        "parameters": {
            "type": "object",
            "properties": {
                "chapter_num": {
                    "type": "integer",
                    "description": "章节号，例如 500"
                }
            },
            "required": ["chapter_num"]
        }
    }
}
```

---

## 第三步：[tools.py](http://tools.py) 的 _execute_tool 添加分发

在 `_execute_tool` 函数的 `if/elif` 链里加：

```python
elif name == "get_chapter_content":
    from backend.notion_tools import get_chapter_content
    return get_chapter_content(args)
```

---

## 第四步：系统提示词已自动更新（上面补丁2已包含）

确认 [main.py](http://main.py) 的 CHENXING_SYSTEM 里已有：

> 妈妈问「第X章内容是什么」→ 直接调用 get_chapter_content（不需要先搜索）
> 

如果没有，在工具规则里加一行：

```
- 妈妈问「第X章内容」「某一章写了什么」→ 直接调用 get_chapter_content(chapter_num=X)，不需要先search
```