# 人设数据索引构建工具

本目录包含三个索引构建脚本，用于从人设数据和 what 解构结果中构建不同维度的索引，方便快速查询和分析。

---

## 快速开始

### 一键构建所有索引

```bash
# 构建所有三个索引文件
python build_category_index.py --persona-dir data/阿里多多酱/out/人设_1110
python build_point_to_note_index.py --what-dir data/阿里多多酱/out/人设_1110/what解构结果
python build_note_to_all_index.py --persona-dir data/阿里多多酱/out/人设_1110
```

---

## 索引文件说明

### 1. 分类索引_完整.json

**脚本**: `build_category_index.py`

**用途**: 按**分类维度**组织帖子（灵感分类、目的分类、关键点分类）

**数据来源**:
- 灵感分类：来自 `人设.json`
- 目的分类：来自 `what解构结果/`
- 关键点分类：来自 `what解构结果/`

**结构**:
```json
{
  "灵感分类": {
    "职场疲惫共鸣": {
      "分类层级": "二级分类",
      "分类名称": "职场疲惫共鸣",
      "分类定义": "关于工作压力、倦怠及身份认同的普遍情绪宣泄。",
      "分类路径": [
        {"视角名称": "灵感触发源", "视角描述": "..."},
        {"分类名称": "个人感受与思考", "分类定义": "..."},
        {"分类名称": "职场疲惫共鸣", "分类定义": "..."}
      ],
      "帖子ID列表": ["68d1ebb8...", "68d00894..."],
      "帖子详情列表": [{...}, {...}]
    }
  },
  "目的分类": {...},
  "关键点分类": {...}
}
```

**使用场景**:
- 查看某个分类下的所有帖子
- 了解分类的层级结构和定义
- 按分类维度分析内容

**统计**:
- 灵感分类：15 个
- 目的分类：45 个
- 关键点分类：60 个

---

### 2. 点到帖子映射.json

**脚本**: `build_point_to_note_index.py`

**用途**: 按**具体点**组织帖子，提供双向映射（点→帖子，帖子→点）

**数据来源**: 全部来自 `what解构结果/`

**结构**:
```json
{
  "点到帖子映射": {
    "灵感点": {
      "职场投入产出不平衡": {
        "灵感点": "职场投入产出不平衡",
        "维度": "职场观察",
        "描述": "观察到职场中普遍存在的现象...",
        "帖子ID列表": ["68d00894..."],
        "帖子详情列表": [{...}]
      }
    },
    "目的点": {...},
    "关键点": {...}
  },
  "帖子到点映射": {
    "68d00894...": {
      "灵感点列表": [
        {
          "灵感点": "职场投入产出不平衡",
          "来源字段": "共性差异",
          "维度": "职场观察",
          "描述": "..."
        }
      ],
      "目的点列表": [...],
      "关键点列表": [...],
      "帖子详情": {...}
    }
  }
}
```

**使用场景**:
- 查看某个具体灵感点/目的点/关键点的所有帖子
- 反查：某个帖子有哪些点
- 分析点与帖子的关联关系

**统计**:
- 灵感点：46 个（关联 20 个帖子）
- 目的点：45 个（关联 19 个帖子）
- 关键点：60 个（关联 19 个帖子）
- 平均每个帖子：2.3 个灵感点、2.2 个目的点、3.2 个关键点

---

### 3. 帖子到分类和点映射.json

**脚本**: `build_note_to_all_index.py`

**用途**: 按**帖子ID**组织，包含每个帖子的完整信息（分类 + 点 + 详情）

**数据来源**:
- 分类信息：来自 `人设.json`
- 点信息：来自 `what解构结果/`
- 帖子详情：通过详情接口获取

**结构**:
```json
{
  "68d00894...": {
    "帖子ID": "68d00894...",
    "所属分类": [
      {
        "分类类型": "灵感分类",
        "视角名称": "灵感触发源",
        "一级分类": "个人感受与思考",
        "二级分类": "职场疲惫共鸣",
        "分类定义": "..."
      }
    ],
    "灵感点列表": [
      {
        "灵感点": "职场投入产出不平衡",
        "来源字段": "共性差异",
        "维度": "职场观察",
        "描述": "..."
      }
    ],
    "目的点列表": [...],
    "关键点列表": [...],
    "帖子详情": {
      "channel_content_id": "68d00894...",
      "title": "上班要显贵 就不能太基础",
      "body_text": "...",
      "like_count": 768,
      "images": [...],
      "content_type": "normal",
      "publish_time": "2025-09-22 10:01:05"
    }
  }
}
```

**使用场景**:
- 通过帖子ID快速获取完整信息
- 查看某个帖子属于哪些分类
- 查看某个帖子有哪些点
- 一站式获取帖子的所有元数据

**统计**:
- 帖子总数：20
- 有分类信息的帖子：17 个
- 有灵感点信息的帖子：20 个
- 有目的点信息的帖子：19 个
- 有关键点信息的帖子：19 个
- 平均每个帖子：2.0 个分类、2.3 个灵感点、2.2 个目的点、3.2 个关键点

---

## 使用指南

### 脚本 1: build_category_index.py

构建按分类维度组织的索引。

**基本使用**:
```bash
python build_category_index.py --persona-dir data/阿里多多酱/out/人设_1110
```

**参数说明**:
- `--persona-dir`: 人设目录路径（必填）
- `--output`: 输出文件路径（可选，默认: `{persona_dir}/分类索引_完整.json`）
- `--no-details`: 不获取帖子详情（可选，只构建索引结构）

**示例**:
```bash
# 基本使用（包含帖子详情）
python build_category_index.py --persona-dir data/阿里多多酱/out/人设_1110

# 只构建索引结构，不获取详情（速度快）
python build_category_index.py --persona-dir data/阿里多多酱/out/人设_1110 --no-details

# 自定义输出文件
python build_category_index.py --persona-dir data/阿里多多酱/out/人设_1110 --output my_index.json
```

---

### 脚本 2: build_point_to_note_index.py

构建点到帖子的双向映射索引。

**基本使用**:
```bash
python build_point_to_note_index.py --what-dir data/阿里多多酱/out/人设_1110/what解构结果
```

**参数说明**:
- `--what-dir`: what解构结果目录路径（必填）
- `--output`: 输出文件路径（可选，默认: `{what_dir}/../点到帖子映射.json`）
- `--no-details`: 不获取帖子详情（可选）

**示例**:
```bash
# 基本使用
python build_point_to_note_index.py --what-dir data/阿里多多酱/out/人设_1110/what解构结果

# 只构建索引结构
python build_point_to_note_index.py --what-dir data/阿里多多酱/out/人设_1110/what解构结果 --no-details

# 自定义输出文件
python build_point_to_note_index.py --what-dir data/阿里多多酱/out/人设_1110/what解构结果 --output custom.json
```

---

### 脚本 3: build_note_to_all_index.py

构建帖子ID到分类和点的完整映射。

**基本使用**:
```bash
python build_note_to_all_index.py --persona-dir data/阿里多多酱/out/人设_1110
```

**参数说明**:
- `--persona-dir`: 人设目录路径（必填）
- `--output`: 输出文件路径（可选，默认: `{persona_dir}/帖子到分类和点映射.json`）
- `--no-details`: 不获取帖子详情（可选）

**示例**:
```bash
# 基本使用
python build_note_to_all_index.py --persona-dir data/阿里多多酱/out/人设_1110

# 只构建索引结构
python build_note_to_all_index.py --persona-dir data/阿里多多酱/out/人设_1110 --no-details

# 自定义输出文件
python build_note_to_all_index.py --persona-dir data/阿里多多酱/out/人设_1110 --output custom.json
```

---

## 查询场景对比

| 查询需求 | 使用哪个索引 | 示例查询 |
|---------|-------------|---------|
| 查看某个**分类**下的所有帖子 | `分类索引_完整.json` | "职场疲惫共鸣"分类有哪些帖子？ |
| 查看某个**具体点**的所有帖子 | `点到帖子映射.json` → 点到帖子映射 | "职场投入产出不平衡"这个灵感点有哪些帖子？ |
| 查看某个**帖子**的所有分类 | `帖子到分类和点映射.json` | 帖子 68d00894 属于哪些分类？ |
| 查看某个**帖子**的所有点 | `帖子到分类和点映射.json` | 帖子 68d00894 有哪些灵感点/目的点/关键点？ |
| 反查：帖子有哪些点 | `点到帖子映射.json` → 帖子到点映射 | 帖子 68d00894 有哪些点？ |
| 获取帖子的完整信息 | `帖子到分类和点映射.json` | 帖子 68d00894 的详情、分类、点是什么？ |

---

## 数据流程图

```
人设.json
  ↓
build_category_index.py  →  分类索引_完整.json
  (灵感分类)

what解构结果/
  ↓
build_category_index.py  →  分类索引_完整.json
  (目的分类 + 关键点分类)
  ↓
build_point_to_note_index.py  →  点到帖子映射.json
  (灵感点 + 目的点 + 关键点)

人设.json + what解构结果/
  ↓
build_note_to_all_index.py  →  帖子到分类和点映射.json
  (完整映射)
```

---

## 核心特性

### 1. 自动缓存

所有脚本都会利用帖子详情的缓存机制：
- 已获取过的帖子详情会自动使用缓存
- 只有新帖子才会调用详情接口
- 大大提升重复运行的速度

### 2. 数据去重

- 帖子ID自动去重
- 图片URL自动去重（保持顺序）
- 确保数据一致性

### 3. Null处理

- 不存在的字段统一使用 `null`（而非空字符串或 0）
- 保持数据结构的一致性和可靠性

### 4. 时间格式化

- 自动将时间戳转换为可读格式
- `publish_timestamp`: 毫秒时间戳
- `publish_time`: "YYYY-MM-DD HH:MM:SS"

### 5. 内容类型判断

- 根据 `video` 字段自动判断
- 有视频: `content_type = "video"`
- 无视频: `content_type = "normal"`

---

## 常见问题

### Q1: 三个索引文件有什么区别？

**A**: 它们从不同维度组织相同的数据：
- **分类索引**: 按分类维度（灵感/目的/关键点分类）
- **点到帖子映射**: 按具体点（具体的灵感点/目的点/关键点）
- **帖子到分类和点映射**: 按帖子ID（一站式获取所有信息）

### Q2: 为什么需要三个不同的索引？

**A**: 不同的查询场景需要不同的数据组织方式：
- 分析分类 → 用分类索引
- 分析具体点 → 用点到帖子映射
- 查看帖子完整信息 → 用帖子到分类和点映射

### Q3: 如何更新索引？

**A**: 重新运行对应的脚本即可：
```bash
# 更新所有索引
python build_category_index.py --persona-dir data/阿里多多酱/out/人设_1110
python build_point_to_note_index.py --what-dir data/阿里多多酱/out/人设_1110/what解构结果
python build_note_to_all_index.py --persona-dir data/阿里多多酱/out/人设_1110
```

### Q4: `--no-details` 什么时候使用？

**A**: 适用于以下场景：
- 只需要索引结构，不需要帖子详情
- 快速验证索引构建是否正确
- 减少API调用（开发测试时）

### Q5: 帖子详情从哪里来？

**A**: 通过 `script.detail.get_xiaohongshu_detail()` 接口获取：
- 自动使用缓存（如果已获取过）
- 自动保存到 `data/detail/xiaohongshu_detail/{note_id}/`
- 包含 raw 和 clean 两种格式

---

## 技术细节

### 数据来源

| 数据类型 | 来源文件 | 提取字段 |
|---------|---------|---------|
| 灵感分类 | `人设.json` | `灵感点列表` → `模式列表` → `二级细分` |
| 目的分类 | `what解构结果/*.json` | `三点解构.目的点.main_purpose` / `secondary_purposes` |
| 关键点分类 | `what解构结果/*.json` | `三点解构.关键点.key_points` |
| 具体灵感点 | `what解构结果/*.json` | `三点解构.灵感点.{全新内容,共性差异,共性内容}` |
| 具体目的点 | `what解构结果/*.json` | `三点解构.目的点.main_purpose` / `secondary_purposes` |
| 具体关键点 | `what解构结果/*.json` | `三点解构.关键点.key_points` |
| 帖子详情 | 详情接口 | `get_xiaohongshu_detail(note_id)` |

### 依赖

```python
from script.detail import get_xiaohongshu_detail
```

确保 `script/detail/` 模块可用。

---

## 输出文件位置

默认输出位置：
```
data/阿里多多酱/out/人设_1110/
├── 人设.json                    # 输入
├── what解构结果/                 # 输入
├── 分类索引_完整.json            # 输出1
├── 点到帖子映射.json             # 输出2
└── 帖子到分类和点映射.json       # 输出3
```

---

## 版本历史

- **v1.0** (2025-11-13): 初始版本
  - 支持三种索引构建
  - 自动获取帖子详情
  - 支持缓存机制

---

## 相关文档

- [搜索模块 README](script/search/README.md)
- [详情模块 README](script/detail/README.md)
- [灵感点可视化 README](README_可视化.md)
