test(ncm): M6 缓存命名宿主单测(63 PASS)+ core 全量用例 + REPORT §39
- 新增 test/test_ncm_cache.c + build_ncm_cache_host.sh(纯 libc:真实 ncm_cache.c + ncm_tag.c,仅桩 strlcpy/mkdir_p/档位映射,不依赖 vendor/mbedtls) - 覆盖:实际档映射、降级后写入名、hires 命中已存 exhigh/lossless、低档不命中高档、 旧命名命中/扫描/删除/双点名迁移、列表去重、LRU/清空/删除兼容、level_from_path 边界 - test_ncm_core.c 新增 test_cache_actual_naming(接入 core 全量测试集,同语义断言) - REPORT §39:命名/命中/兼容方案、质量取舍与未执行项(vendor/交叉/真机)
This commit is contained in:
1 parent
68833cf642
commit
e60642217a
4 files changed
+678
No files matched your search
@@ -3369,3 +3369,63 @@ MP3 ≤128k→标准,>128k→极高 HQ。列表显示**实际档**(如 hires
|
||||
dispose 的 join 可能多等 ~0.3–1s。磁盘瞬时要 2× 单曲空间(失败自动降级裸流)。
|
||||
- **缓存队列点播的时长/封面**取自旁路 `meta/<id>.bin`(单次 ≤600B 读);无旁路的旧条目只有歌名/歌手/大小。
|
||||
- **列表上限 512 条**(最近访问优先);池内更多时页脚仍显示展示条数,超出部分需 LRU 或搜索触达。
|
||||
|
||||
## 39. M6:缓存文件名改为「实际档」(2026-11-04)
|
||||
|
||||
用户原话:「有降级显示,但是那个缓存文件名误导人」。背景:现缓存命名 `song_<id>_<请求档>.<实际格式>`,
|
||||
当服务端对无损档只给 mp3 时降级链落到 exhigh,文件名却仍写 hires(真机 `song_171650_hires.mp3`),名不副实。
|
||||
|
||||
### 39.1 设计(先写方案再动代码)
|
||||
|
||||
- **命名**:新写入一律 `song_<id>_<实际档>.<实际格式>`,实际档由 `ncm_cache_actual_level(req, 音频参数,
|
||||
响应生效档)` 判定(**单一事实源**:写盘名 / 播放页显示 / 已缓存列表三处共用)。
|
||||
规则:`min(请求档, 容器可承载档, 降级链生效档)`,只降不升——
|
||||
mp3 码率 >128k→exhigh、≤128k→standard(mp3 永不高于极高,码率未知时也钳到极高);
|
||||
flac 16bit/44.1k→lossless、24/48→hires、24/96→jyeffect、24/192→jymaster。
|
||||
典型:hires 请求 + 320k mp3 响应 → `song_171650_exhigh.mp3`。
|
||||
- **命中语义(同歌同档不重复下载)**:`ncm_cache_lookup` 在请求档精确 miss 后**只降不升**逐档下探
|
||||
(`surround→sky→jymaster→jyeffect→hires→lossless→exhigh→higher→standard`,DOLBY 不在链内)。
|
||||
于是 hires 请求命中已存的 `song_<id>_exhigh.mp3` / `song_<id>_lossless.flac`,不重下;低档请求
|
||||
不会向上命中高档实体(不偷跑流量/存储)。`.part` 续传键也用实际档,同名才续传/commit。
|
||||
- **旧文件兼容(不强制迁移)**:旧命名 `song_<id>_hires.mp3`(及无档位段 `song_<id>.mp3`、历史双点名)
|
||||
原样保留:按原键可命中、可播放、可单曲删除、可 LRU 淘汰;列表按文件头探测显示实际档(M5 既有链路)。
|
||||
播放/列表的生效档由 `ncm_cache_level_from_path`(文件名档位)+ 容器钳顶得出:mp3 实体不可能高于
|
||||
极高,故旧 `hires.mp3` 标注「极高」,与实际一致。**不再**像 §NEW 任务2 那样把旧 mp3 改名 + 强制重下。
|
||||
- **去重展示**:同曲同实际档、两种命名并存时(旧请求档名 + 新实际档名),`ncm_cache_scan` 只保留
|
||||
最近访问的一条;不同实际档(如 lossless.flac + exhigh.mp3)照常各列一行。
|
||||
|
||||
### 39.2 改动
|
||||
|
||||
| 文件 | 改动 |
|
||||
|---|---|
|
||||
| `core/ncm_cache.c/.h` | 新增 `ncm_cache_actual_level`(容器/码率/位深/响应档→实际档,只降不升)、`ncm_cache_level_from_path`(文件名档位解析,含 `sky_c51`);`ncm_cache_lookup` 拆出精确查找 + 档位下探链;`ncm_cache_scan` 复用实际档判定并按 (id, actual_level, ext) 去重 |
|
||||
| `app/play/player_manager.c` | 写盘键改用响应实际档(`ext` 判定后计算,`.part`/`open`/日志同键);`eff_level` = 实际档;命中路径按文件名档位 + mp3 钳顶标注实际档;删除旧「stale-degraded 改名+强制重下」与「无档位键迁移」块(老卡文件免迁移) |
|
||||
| `test/test_ncm_cache.c` + `build_ncm_cache_host.sh` | 新增纯 libc 宿主单测:命名生成/解析、降级后写入名、hires 命中已存 exhigh/lossless、低档不命中高档、旧命名命中/扫描/删除、双点名迁移、列表去重、LRU/清空/删除对两种命名兼容、`level_from_path` 边界 |
|
||||
| `test/test_ncm_core.c` | 新增 `test_cache_actual_naming`(同一组语义接入 core 全量测试集;本机缺 vendor 未整链,仅 `-fsyntax-only` 0 warning) |
|
||||
| `bench/player_flow_sim.c` | 适配:补 `ncm_cache_actual_level`/`ncm_cache_level_from_path` 桩与 M5 后缺失的链接桩(`appstate_cache_*`、`ncm_tag_embed_file`);P7/P12 期望键改实际档;P13 改为「旧命名命中即播 + 实际档显示,不重下不迁移」 |
|
||||
|
||||
### 39.3 验证
|
||||
|
||||
| 项 | 结果 |
|
||||
|---|---|
|
||||
| `./build_ncm_cache_host.sh`(真实 `core/ncm_cache.c` + `core/ncm_tag.c`,仅桩 `ncm_strlcpy`/`mkdir_p`/档位映射) | **63 PASS / 0 FAIL**,`-Wall -Wextra` 0 warning |
|
||||
| `player_manager.c` / `player_flow_sim.c` 语法+告警检查(`gcc -O2 -Wall -Wextra -fsyntax-only`,临时 jsmn 头垫片) | 0 warning |
|
||||
| `bench/player_flow_sim.c` 链接(真实 player_manager + stream_src + mem_watch + meow_cachegov) | 链接通过(运行需可写 `/tmp`,本机 Termux 不可写,见 39.4) |
|
||||
| `test_ncm_tag_host.sh` 既有链路 | 未改 `ncm_tag.c`,未重跑(非本批改动面) |
|
||||
|
||||
### 39.4 诚实出入 / 遗留
|
||||
|
||||
- **本机缺 vendor(mbedtls/jsmn/minimp3/qrcodegen)与交叉工具链**,`build_core.sh`/`build_ncm.sh`/
|
||||
`build_ncm_host.sh` 未执行;`test_ncm_core_host` 未重编(M5 已记录同一限制)。新语义用
|
||||
`test/test_ncm_cache_host`(真实 core 源)全量覆盖,构建环境需补跑 core 全量回归。
|
||||
- **`player_flow_sim` 未在本机运行**:其路径硬编码 `/tmp`(Termux 不可写),M5 后还缺若干链接桩
|
||||
(本批已补齐);需在常规构建机跑 P1–P15 全量。
|
||||
- **质量取舍(任务口径)**:命中下探后,hires 请求会直接播放已存的 exhigh 实体,不再像 §NEW 任务2
|
||||
那样强制为「更高档」重下。这是「实际档命名 + 同名去重」的必然结果(用户已接受降级显示);
|
||||
如需「换高档时重取」,应作为显式「重新下载」交互另开需求。
|
||||
- **flac 头参数在响应时点未知**:落盘名以降级链生效档为上限,下载完成后由列表探测显示实际档;
|
||||
服务端「声称 hires 实为 16bit」的病态情况,文件名会高于列表实测档(既有取舍,未引入回归)。
|
||||
- **旧命名文件的跨档复用**:旧 `song_<id>_hires.mp3`(实际 exhigh)在 hires 请求下直接命中;若用户
|
||||
切到「极高」档再播同名曲,会按实际档新落一份 `song_<id>_exhigh.mp3`(一次性重下,旧文件不删,
|
||||
列表按 (id,实际档,ext) 去重只显示一行,旧文件由 LRU/清空自然回收)。未对旧名做向上探测扫描
|
||||
(避免每次 miss 扫目录 + 读多份文件头);如需「旧名跨档零重下」,可作为后续优化加一次目录级兼容探测。
|
||||
Reference in new issue
Block a user