频道 6 万条评论导出后,我用 jq 清洗时才发现自己一直在丢字段

上个月我把频道从开通到现在的评论都导了出来,大约 6 万条,存成 NDJSON,每行一条。本来只想统计每月评论数,结果 jq 跑完发现总数比后台显示的少了 400 多条。

先说我当时怎么做的。导出文件每行大概长这样:

{"id":"Ugx...","snippet":{"topLevelComment":{"snippet":{"textDisplay":"...","publishedAt":"2023-04-01T12:00:00Z","authorDisplayName":"..."}},"totalReplyCount":3}}

我想取发布时间和作者,写了:

jq -r '.snippet.topLevelComment.snippet | [.publishedAt, .authorDisplayName] | @tsv' comments.ndjson > out.tsv

然后 wc -l 发现 6 万条变成了 5.96 万。

第一反应是文件有坏行。jq -c . comments.ndjson > /dev/null 确实报了几行 parse error,但只有十几行,对不上。

接着我按 id 去重,发现丢的全是 topLevelComment 里没有 authorDisplayName 的条目——频道被删或者作者注销的评论,这个字段直接不存在。jq 的 @tsv 遇到 null 会输出空字符串,不会报错,但后续 awk 按 tab 切列时,如果整行是 \t,有些行会被误判成只有一列。

问题出在我没检查字段是否存在。改成:

jq -r '(.snippet.topLevelComment.snippet.publishedAt // "") + "\t" + (.snippet.topLevelComment.snippet.authorDisplayName // "__gone__")' comments.ndjson

把缺失作者标记成占位符,再统计就对齐了。

为什么之前没发现:我默认以为导出的每一条都有完整 snippet,但 YouTube 的评论资源在作者账号停用后,authorDisplayName 和 authorProfileImageUrl 会直接缺省,而不是给空串。这个行为不是文档里一眼能看到的,我是拿 id 反查才确认的。

边界在于:如果评论本身被平台移除,整条 topLevelComment 可能都不在,我的脚本只处理了字段缺失,没处理对象缺失。后来加了 if .snippet.topLevelComment then ... else empty end 才稳。另一个坑是 publishedAt 偶尔带毫秒,按字符串排序会错位,得先 fromdateiso8601。

你们导出评论做分析时,是怎么处理作者字段缺失的?是直接丢弃还是单独归类?

0
赞同度 100% · 0 条评论 · 4 阅读

0 条评论

支持 Markdown · 回复会实时推送给对方

还没有评论,写下第一条。