Files
Sidney Zhang b8bd749f43 feat(scripts): 支持动态指标和维度参数配置
为 build_studio_urls.py 添加指标和维度的可配置支持,包括:
- 新增 metrics.json 和 dimensions.json 映射文件加载
- 支持中文/英文别名映射及指标代码透传
- 列别名扩展以识别"指标"和"维度"列
- 空值时自动回退到 CONFIG 默认值
2026-08-24 15:28:48 +08:00

135 lines
8.5 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# 映射文件维护指南
`scripts/` 下有三个映射文件,把「人类可读的中文/英文名」翻译成「URL 内部代码」。本指南说明它们各自的作用、数据来源、结构规则,以及如何新增/更新条目。
- `countries.json`:中文国家名 → ISO 3166-1 alpha-2 代码(两位大写)。
- `metrics.json`:指标中文/英文名 → 指标代码(大写、下划线风格)。
- `dimensions.json`:细分维度中文名 → 维度代码(大写)。
三者都是**扁平 `key -> value` 的 JSON 对象**UTF-8 编码。脚本按 UTF-8-SIG 读取,带 BOM 无影响。
## 1. 脚本如何加载它们
| 文件 | 加载函数 | 参数 | 缺失/文件不存在时的行为 |
|---|---|---|---|
| countries.json | `load_country_map` | `--countries` | 仅支持两位 ISO 代码透传,中文名会报「未识别的国家」 |
| metrics.json | `load_metric_map` | `--metrics` | 仅支持 `CONFIG` 里的已知指标代码透传,中文/英文名会报「未识别的指标」 |
| dimensions.json | `load_dimension_map` | `--dimensions` | 仅支持 `CONFIG["dimension"]` 已知维度代码透传,中文名会报「未识别的维度」 |
加载时统一做了`strip` + 值 `upper()`,因此**文件里大小写、首尾空格不影响结果**——但建议源文件就保持规范,便于 diff 和阅读。
## 2. 数据来源Source of Truth
内部代码的真实来源是 YouTube Studio 后台 explore 报告 URL 里的 `metric=` / `dimension=` / `t_metrics=` 参数(或捕获的 `search_groups`/analytics 请求)。仓库内 `assets/YouTube_Studio_细分维度_时间颗粒度_完整清单.xlsx` 已把已知清单整理好,是当前映射的**基准数据源**
| 映射文件 | 对应 Excel 表 | 取「同名」列 → 值列 |
|---|---|---|
| dimensions.json | `细分维度` 表 | `中文名称(显示名)``URL 参数值dimension=` |
| metrics.json | `数据指标` 表 | `中文名称(显示名)``URL 参数值t_metrics=/metric=` |
| countries.json | 无 Excel 源 | 基于 ISO 3166-1 alpha-2 标准手工维护 |
`时间颗粒度` 表对应脚本 `CONFIG["granularity"]`**不落入 JSON 文件**`URL参数总览` 表是对 URL 各参数的说明,供核对。
## 3. 三个文件的结构与规则
### 3.1 dimensions.json细分维度
- 键:维度中文显示名,如 `内容``地理位置``收入来源`
- 值:维度代码(大写),如 `VIDEO``COUNTRY``EARNINGS_SOURCE_ALL`
规则:
- 一个中文名对应一个代码;多个不同中文名可指向**同一**代码(如需,但避免冗余)。
- 新增一个维度后,其代码会被 `load_dimension_map` 自动加入「可透传集合」——即该代码立刻可作为裸代码在 `维度` 列直接填写,**无需改 `build_studio_urls.py`**。
- 维度代码只影响 URL 的 `dimension` 参数。
### 3.2 metrics.json数据指标
标准条目(来自 Excel「数据指标」表57 条):
- 键:指标中文名,如 `观看次数``估算的合作伙伴收入`
- 值:指标代码(大写),如 `EXTERNAL_VIEWS``TOTAL_ESTIMATED_EARNINGS`
别名条目(手工追加,用于同义词/英文名,**不会出现在 Excel 中**
- 多个中文同义词 → 同一代码。如 `税前收益``税前收入``预计收益``收益``收入` 都指向 `TOTAL_ESTIMATED_EARNINGS`
- 英文 snake_case → 同一代码。如 `subscribers_net_change``SUBSCRIBERS_NET_CHANGE`
规则:
- 一个键对应唯一一个代码JSON 键唯一,重复键后者覆盖前者,应避免手写重复)。
- 一个代码可有多个键(同义词),方向只能多对一。
- 新增一个指标后,其代码会被 `load_metric_map` 自动加入「可透传集合」,可直接作为裸代码填写。
- 指标只影响 URL 的 `metric``o_column`(排序字段)两个参数;`t_metrics`(表格列指标集合)仍是 `CONFIG` 固定值,**不在 JSON 里维护**。
### 3.3 countries.json国家
- 键:中文国家名(可含别名,如 `台湾``中国台湾` 都指向 `TW`)。
-ISO 3166-1 alpha-2 两位大写代码,如 `US``JP``CN`
规则:
- 值必须为**两位大写字母**。多字/小写虽能被脚本 upper 后处理,但透传逻辑依赖 `[A-Z]{2}` 正则,非两位会走中文名映射路径。
- 两位 ISO 代码本身**无需在此文件登记**即可透传(`parse_countries` 正则直接识别),所以国家列填 `US` 永远可行;只有在需要「中文名 → 代码」时才在这加一行。
## 4. 当改什么 / 怎么改
| 场景 | 改动位置 | 例子 |
|---|---|---|
| 新增一个细分维度 | dimensions.json 加 `"中文名": "代码"` | `"播放来源": "PLAYBACK_SOURCE_TYPE"` |
| 新增一个指标 | metrics.json 加 `"中文名": "代码"` | `"新增指标": "SOME_NEW_METRIC"` |
| 给指标加中文同义词/英文别名 | metrics.json 加 `"别名": "同一代码"` | `"税前收益": "TOTAL_ESTIMATED_EARNINGS"` |
| 给维度加别名 | dimensions.json 加 `"别名": "同一代码"` | `"地区": "COUNTRY"` |
| 新增中文国家名 | countries.json 加 `"中文名": "XX"` | `"瑞典": "SE"` |
| 调整默认主指标/维度/粒度 | 改 `build_studio_urls.py` 顶部 `CONFIG`**不是 JSON 文件** | `CONFIG["metric"] = "..."` |
## 5. 从 Excel 重新同步(可选脚本)
`assets/YouTube_Studio_细分维度_时间颗粒度_完整清单.xlsx` 更新后,可用以下片段把「数据指标」「细分维度」两张表重新导出为 JSON再合并回文件别名条目需要手工保留
```python
import openpyxl, json
xlsx = r"assets/YouTube_Studio_细分维度_时间颗粒度_完整清单.xlsx"
wb = openpyxl.load_workbook(xlsx, data_only=True)
def dump(sheet_name, name_col, code_col):
ws = wb[sheet_name]
rows = list(ws.iter_rows(values_only=True))
header = rows[0]
ni, ci = header.index(name_col), header.index(code_col)
return {str(r[ni]).strip(): str(r[ci]).strip().upper()
for r in rows[1:] if r[ni] and r[ci]}
metrics = dump("数据指标", "中文名称(显示名)", "URL 参数值t_metrics=/metric=")
dims = dump("细分维度", "中文名称(显示名)", "URL 参数值dimension=")
json.dump(metrics, open("skills/yt-studio-url-builder/scripts/metrics.json", "w", encoding="utf-8"),
ensure_ascii=False, indent=2)
json.dump(dims, open("skills/yt-studio-url-builder/scripts/dimensions.json", "w", encoding="utf-8"),
ensure_ascii=False, indent=2)
```
> 该片段生成的是「标准条目全量覆盖」,会**丢失**你在 metrics.json 里追加的别名;建议先备份,再把别名手工合并回去。
## 6. 更新后的校验
改完任一 JSON按下面顺序自检
1. **JSON 语法有效**
```bash
uv run python -m json.tool scripts\metrics.json > $null
uv run python -m json.tool scripts\dimensions.json > $null
uv run python -m json.tool scripts\countries.json > $null
```
2. **键非空、值非空**:加载函数已过滤空键值,但建议源文件里就不要出现空串。
3. **值大写**:脚本会 `upper()`,但提交前统一大写更清晰;国家值必须是两位字母。
4. **无重复键**JSON 标准允许重复键但后者覆盖,属于隐性错误;手改时避免。
5. **跑一条真实需求验证**:造一行含新中文名/新代码的输入,确认输出 CSV 的「指标代码/维度代码/国家代码」解析正确、URL 里 `metric`/`dimension`/`ur_values` 正确。
6. **回归测试**
```bash
uv run python -m pytest tests/test_build_studio_urls.py tests/test_build_studio_urls_cli.py -q
```
## 7. 常见坑
- **文件缺失**三个文件单个缺失只会降级stderr 提示),名称/代码透传受限;务必恢复同目录下的文件,不要依赖降级路径长期运行。
- **以为改 JSON 能改默认值**:默认主指标/维度/粒度在 `build_studio_urls.py` 的 `CONFIG`,不在 JSON。JSON 只提供「可按行选择」的名称→代码映射。
- **`t_metrics` 不在 metrics.json 里**:表格列指标集合是 `CONFIG["t_metrics"]` 固定数组,加指标时若想让其进入表格列,需同时在 `CONFIG["t_metrics"]` 追加(否则只影响 `metric`/`o_column`)。
- **国家值写三位或带空格**:透传按 `[A-Z]{2}` 匹配,非两位值不会命中透传分支,中文名若也查不到就会报「未识别的国家」。
- **别名覆盖了标准名**:手动追加别名时不要与现有键重复,否则后者覆盖,标准名会失效。