@geoly-ai/social-hub-cli 0.3.47 → 0.3.49

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (43) hide show
  1. package/CHANGELOG.md +30 -0
  2. package/dist/cmd-manifest.json +10 -2
  3. package/dist/index.d.ts.map +1 -1
  4. package/dist/index.js +2 -0
  5. package/dist/index.js.map +1 -1
  6. package/dist/permissions-gates-intake.d.ts +8 -0
  7. package/dist/permissions-gates-intake.d.ts.map +1 -0
  8. package/dist/permissions-gates-intake.js +38 -0
  9. package/dist/permissions-gates-intake.js.map +1 -0
  10. package/dist/permissions-gates-intake.test.d.ts +2 -0
  11. package/dist/permissions-gates-intake.test.d.ts.map +1 -0
  12. package/dist/permissions-gates-intake.test.js +37 -0
  13. package/dist/permissions-gates-intake.test.js.map +1 -0
  14. package/dist/permissions.d.ts.map +1 -1
  15. package/dist/permissions.js +2 -0
  16. package/dist/permissions.js.map +1 -1
  17. package/dist/register-intake.d.ts +17 -0
  18. package/dist/register-intake.d.ts.map +1 -0
  19. package/dist/register-intake.js +188 -0
  20. package/dist/register-intake.js.map +1 -0
  21. package/dist/register-intake.test.d.ts +2 -0
  22. package/dist/register-intake.test.d.ts.map +1 -0
  23. package/dist/register-intake.test.js +108 -0
  24. package/dist/register-intake.test.js.map +1 -0
  25. package/dist/register-subreddit-assets.js +1 -1
  26. package/dist/register-subreddit-assets.js.map +1 -1
  27. package/package.json +3 -3
  28. package/skills/integrity.json +16 -15
  29. package/skills/manifest.json +1 -1
  30. package/skills/reddit-content-rewrite/SKILL.md +1 -1
  31. package/skills/reddit-content-rewrite/prompts.md +2 -2
  32. package/skills/reddit-content-rewrite/sop-reference.md +18 -123
  33. package/skills/reddit-ext-post-audit/references/ext-post-audit.md +6 -7
  34. package/skills/reddit-matrix.lock.json +3 -3
  35. package/skills/reddit-voc-volume/SKILL.md +13 -9
  36. package/skills/reddit-voc-volume/references/arctic-shift.md +1 -1
  37. package/skills/reddit-voc-volume/requirements.txt +1 -4
  38. package/skills/reddit-voc-volume/scripts/reddit_voc_volume.py +22 -234
  39. package/skills/reddit-voc-volume/scripts/setup_env.sh +3 -40
  40. package/skills/reddit-voc-volume/services/firecrawl/examples/o1_web_crawler/o1_web_crawler.py +152 -152
  41. package/skills/reddit-voc-volume/tests/test_links_fallback.py +7 -7
  42. package/skills/reddit-voc-volume/tests/test_no_direct_reddit.py +315 -0
  43. package/skills/social-hub-admin/SKILL.md +25 -0
@@ -1,19 +1,19 @@
1
1
  {
2
2
  "version": 1,
3
3
  "algorithm": "sha256",
4
- "fileCount": 1657,
4
+ "fileCount": 1658,
5
5
  "files": {
6
6
  "README.md": "5246d4ae2712e3e656b101041929183d7ae7f8ea487dacf5854187826ab7c335",
7
- "manifest.json": "f470227ddcda7c66342429a7b22b573fc438c86e1571aee8894fa8e256851209",
7
+ "manifest.json": "8ff022d58e5f9b2490d2d7c7a73d0495993c025fdaf6085c80e429b385f1b795",
8
8
  "reddit-answers-research/SKILL.md": "8936215363b5b222f4010fd18349cb2c56b473ce659bfeb21116ad5448faa640",
9
9
  "reddit-answers-research/references/browser-playbook.md": "a8f61d3d43ca93d46dadc8a092a515ddcd32df12fb1d08d334cce2e02709d915",
10
10
  "reddit-answers-research/references/report-template.md": "9aa9acf555ba8b2ca503bdbdf5750a5f53c66e19989bf6807fa6200c7317e306",
11
11
  "reddit-brand-risk-response/SKILL.md": "590ff3254f3c027bd300f422ef5f9c36b05ef0e1cc470655f5705855911b54bf",
12
12
  "reddit-brand-risk-response/agents/openai.yaml": "00aff3fc6333d4a99b8bb51c282a02f5a10d67bf1279bbdf6e5bd51384e30c67",
13
- "reddit-content-rewrite/SKILL.md": "5fc998f119e94d82e51779043e9df765de514824eee343384f91d0eb7310bbcd",
13
+ "reddit-content-rewrite/SKILL.md": "7f7e98ca336eda259ad6cd01a36a85dcd6ad2ab40c4895e0df843eab1e0ab4e7",
14
14
  "reddit-content-rewrite/matrix-contract.md": "6af594450dc0f900070ae33cc6b9e437bca86e9500475d26b6f97ffba9b9db64",
15
- "reddit-content-rewrite/prompts.md": "b2f7195bd6a484c7fca3832948fc05d766c6411338021bf64a4fbe09989eed27",
16
- "reddit-content-rewrite/sop-reference.md": "dec597ddbc448211dd6c40bd0c087a703b734c315bbc5e9aac9cfb8d0b53fc4e",
15
+ "reddit-content-rewrite/prompts.md": "0eb54fb4ca346843b6a7cbac43e3176da40a08dd36b0c35b1fdb55468a8275f3",
16
+ "reddit-content-rewrite/sop-reference.md": "3640269dca6bab003f405f14f7e311fce5b495d5b045ff5ab64914432737c7ea",
17
17
  "reddit-content-writing/SKILL.md": "9ed5571500faa3511c0caf29845ef279cf7106ca236c2b749a3457eceb2f0d1b",
18
18
  "reddit-content-writing/references/comp-mention-strategy.md": "c6855848468379ee3a5618307a82f4ae08263ff397cbd66772f00a9b4411aa58",
19
19
  "reddit-content-writing/references/pgc-writing-strategy.md": "63cc15a7734eb0f00e5854f0d6dbffe51db23262c281ea963bef9afa0c92ebe5",
@@ -25,8 +25,8 @@
25
25
  "reddit-delivery-check/SKILL.md": "7a645cadecfc6f6224a5fe963c6027bd5e1700d6b29a57fef13784a028806b65",
26
26
  "reddit-delivery-check/references/phase5-delivery.md": "50abd9f6d1a433d52d915221aca17f4f279d9de62190442437c9b92056efcd8a",
27
27
  "reddit-ext-post-audit/SKILL.md": "3cd4310d810eabb58c64116aafa6e373a2da49dc5dfaeaea96f3d1c8af629341",
28
- "reddit-ext-post-audit/references/ext-post-audit.md": "0d2fc69ca38b84520409cf866284803ceacbceb82dcdea0df3ed52ad8183a2b6",
29
- "reddit-matrix.lock.json": "5e76c65a6236c9455d6af8b423647ab3f2094127f1b9fc3e5c5fd808175796c4",
28
+ "reddit-ext-post-audit/references/ext-post-audit.md": "c1f3dfc838f2645d259ea185117e68813315ba2f15e13f3805f9125f0e50fe54",
29
+ "reddit-matrix.lock.json": "0ac0b9e2ae27508fed6dcd36257d5f9de55d2aea31b4613b9dbe258a22d2e921",
30
30
  "reddit-monthly-iteration/SKILL.md": "cb13d1bd821c3361c3bc557beedd78f17d6278cdfbe4dd171d1a6d3b1aa19069",
31
31
  "reddit-monthly-iteration/references/monthly-iteration.md": "fcaf88824e1f7cf80a446919edbcb3685954d31c5606d53836e00589e9524524",
32
32
  "reddit-phase-brief/SKILL.md": "7b4ba2b0aab929ef01c6b07ccbc390f744e08a1acc03d04a969d296a77c2f8f8",
@@ -65,14 +65,14 @@
65
65
  "reddit-subreddit-compliance/SKILL.md": "12333387bf618e3b1304f5b21a32712a3101c80bcf3daac18754b0bff4129cd5",
66
66
  "reddit-subreddit-compliance/matrix-contract.md": "94cc3eab9133354c58283b4f11f72fc3fdd6e95b9b40b6d250dda86581e452ce",
67
67
  "reddit-subreddit-compliance/references/output-templates.md": "589f44c9544c72e72dcfe8c1a06ec67690214964d0394c652781e469fb9b2fe1",
68
- "reddit-voc-volume/SKILL.md": "edbe500db0397240867a8d7a44b1bb973dcb6865a8b82ee5ba98ce43f973db87",
68
+ "reddit-voc-volume/SKILL.md": "bca757c89b75ebc37e83f40087eafed9d068f133be6e403ebb86e45acc04c75f",
69
69
  "reddit-voc-volume/matrix-contract.md": "5676c3a847c35062e8432538e0beb98015dfae4a8144da9d437080211a384b11",
70
- "reddit-voc-volume/references/arctic-shift.md": "c4cec5a64b72e9d528a085d92330833afd175a673310c63968d3b0d4b60f4131",
70
+ "reddit-voc-volume/references/arctic-shift.md": "3a302d39c702e61ad633602bc5ca8ab901d4a6b1bc8b77e5ede5ce7da797bf96",
71
71
  "reddit-voc-volume/references/browser-fallback.md": "aa68e38b2fb3026034b8df0e2fcfa950f23b6b235b23df66f68062771f1531c9",
72
72
  "reddit-voc-volume/references/hub-first.md": "36d178bc848ab2a507afdb1feacdf22e67ae775b8d221d50cb700ee2d088d547",
73
- "reddit-voc-volume/requirements.txt": "91f21d1e6a42dc29db733a5914288ba3f74f3d65d33d49a966fdb60eebd435cc",
74
- "reddit-voc-volume/scripts/reddit_voc_volume.py": "daf5df32c632b139c2944748b2b31610bd42ba2a578c8aa6a16659e674d4ecda",
75
- "reddit-voc-volume/scripts/setup_env.sh": "2e9de90f1a8985953d161beda490c34b4cb5867a2d2d217766d97fd6fe373ec4",
73
+ "reddit-voc-volume/requirements.txt": "43b1afb7a184c45af13a495f32ff3966b83d91f0726c2fc6827d760086ffae61",
74
+ "reddit-voc-volume/scripts/reddit_voc_volume.py": "0864fc03b7f8e3edcdd782768f5831347c3a86235d34cc3760295b99b2cbe88d",
75
+ "reddit-voc-volume/scripts/setup_env.sh": "da02fd1ac7d914602a321a34ba403dfea30078e94df5f7b466464c0502f81c30",
76
76
  "reddit-voc-volume/scripts/setup_firecrawl_service.py": "8d25d38761d9db169bf403a49afdc7892bc5df09910d6d44a073082fbc29967c",
77
77
  "reddit-voc-volume/services/firecrawl/.gitattributes": "1a1dbe176bc233b499d35a57db7513f2941c99ab9759f177830c9149be99005b",
78
78
  "reddit-voc-volume/services/firecrawl/.github/CODEOWNERS": "e9035efad8c4d98efb06728ba1efce400e61c4a0e399d085c8001c6f887a875c",
@@ -1581,7 +1581,7 @@
1581
1581
  "reddit-voc-volume/services/firecrawl/examples/mistral-small-3.1-crawler/mistral-small-3.1-crawler.py": "15e19b60b1a8df3d92f41c280f73584b770612bda8b473f1eb575513776782a0",
1582
1582
  "reddit-voc-volume/services/firecrawl/examples/mistral-small-3.1-extractor/mistral-small-3.1-extractor.py": "b61acfd6a3c95d6a4261aa941d347f6b4a500b89f7897cab4633beb0a2416ba2",
1583
1583
  "reddit-voc-volume/services/firecrawl/examples/o1_job_recommender/o1_job_recommender.py": "bc5f5e477a994ee7dd33636a1158c33875aeee6ef98434e0bd14cc8bc25717eb",
1584
- "reddit-voc-volume/services/firecrawl/examples/o1_web_crawler/o1_web_crawler.py": "aaa56279d8184f519baa45473062502fa316b4e2388265d54cafa62e5cbf2b77",
1584
+ "reddit-voc-volume/services/firecrawl/examples/o1_web_crawler/o1_web_crawler.py": "6280ebd5d8bd25f72e6da1d81fa230ca01b3af23e74a4d1c83a0f5183e66d827",
1585
1585
  "reddit-voc-volume/services/firecrawl/examples/o1_web_extractor/o1_web_extractor.py": "fcd9558a391add78cd3132cccc30496fbe1bcf24c7dd0f506fc01635aa5eece7",
1586
1586
  "reddit-voc-volume/services/firecrawl/examples/o3-mini-deal-finder/o3-mini-deal-finder.py": "b0319c65a20e06f5d55f614553c6abbba60f761d0271600b826ab7c3242a5bbc",
1587
1587
  "reddit-voc-volume/services/firecrawl/examples/o3-mini_company_researcher/o3-mini_company_researcher.py": "8aada7f6813e6e39993fdf5b9bedd5bda16015e03e3d851ca5912b4de9b6829c",
@@ -1633,9 +1633,10 @@
1633
1633
  "reddit-voc-volume/services/firecrawl/img/firecrawl_logo_v1.png": "40b85912f49f4a1b45f42b85bbb39150fb7c0823c1c4ecadaa82860a988fa884",
1634
1634
  "reddit-voc-volume/services/firecrawl/img/open-source-cloud.png": "3d49d98b06dc91e829c9ea2410ad10aaddc0b8b7d7e2a133e061daaff6429895",
1635
1635
  "reddit-voc-volume/tests/test_archived_comments.py": "81fd6da65498f5cca81a10bae28bd6a9164efee1be4545dcab8d99984780a54e",
1636
- "reddit-voc-volume/tests/test_links_fallback.py": "0b6756cbef92567c680fe56525f89ca791502d6173414f833b50e305ef56c65a",
1636
+ "reddit-voc-volume/tests/test_links_fallback.py": "0f9e91e4f7721d6c8f63dc2e98f20d0aeaa82d497a780054ae0096150ac8d861",
1637
+ "reddit-voc-volume/tests/test_no_direct_reddit.py": "5f6764a92f0579eb3322ffcdf29db5351a4d5c38278ab923a1439b5e0a9be45a",
1637
1638
  "social-hub-accounts/SKILL.md": "096f7969f572a0cecbf244d814ba43422b8b556a98b751dc1ece7f9066864e4d",
1638
- "social-hub-admin/SKILL.md": "bce961e34268c736df5bc92e5b9edfdd98393d19dc2122f388112e4250e1102d",
1639
+ "social-hub-admin/SKILL.md": "e227a5d73a113a596231fc6fcaf53df39b10f597361d5e1849576167ed4fa48e",
1639
1640
  "social-hub-calendar-directives/SKILL.md": "27f82cd33c14bc6a51282f59560930f1600d48cb7df1a308505c457b2777ad6f",
1640
1641
  "social-hub-calendar-jobs/SKILL.md": "b79287c9e2dcb541518d5930c5fbf54fe81d17034a0406ca77cd2266afcbf943",
1641
1642
  "social-hub-cli/SKILL.md": "17211c1347c1e985aec132247c050ccaeb126234ef211d33ee873a8394caed2e",
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 1,
3
3
  "package": "social-ops-hub",
4
- "cliVersion": "0.3.47",
4
+ "cliVersion": "0.3.49",
5
5
  "repository": "social-ops-hub",
6
6
  "publish": {
7
7
  "registry": "https://skill.sh",
@@ -312,7 +312,7 @@ ExplicitStructureSpec:
312
312
  **Subreddit 信息获取优先级(不要乱写抓取脚本)**
313
313
 
314
314
  1. 优先使用用户提供的 subreddit 规则、热门帖链接、截图、已有样本或具体发帖要求
315
- 2. 如果用户要求“参考真实样本 / 抓一下 / 看这个板块风格”,按 [sop-reference.md](sop-reference.md) 的“Reddit 样本采集流程”执行;帖子级采样优先用 `/reddit-voc-volume`,评论采样才使用 SOP 中的 `curl_cffi + 完整请求头 + cookie` 低频流程
315
+ 2. 如果用户要求“参考真实样本 / 抓一下 / 看这个板块风格”,按 [sop-reference.md](sop-reference.md) 的“Reddit 样本采集流程”执行;帖子级采样优先用 `/reddit-voc-volume`,评论采样用 `reddit-voc-volume comments`(Arctic 历史评论),当下证据走 Hub-First 或 `social-hub scrape`
316
316
  3. 如果只是普通改写任务,且没有明确要求抓样本,不要临时编写新爬虫、不要并发抓取、不要绕过 403/429、不要抓私密或登录墙内容
317
317
  4. 如果板块规则可能决定能不能发,但没有足够信息,先问用户补充规则/热门帖样本,或在输出前给一句简短 Note 说明假设
318
318
 
@@ -228,8 +228,8 @@ baseline 是分布证据,不是归一化目标:不要求内容向样本中
228
228
  - 只有用户明确要求"参考真实样本 / 抓一下 / 看这个板块风格"时,才按
229
229
  `sop-reference.md` 的 Reddit 样本采集流程取样。该文件已清理为纯操作流程,
230
230
  其 legacy 评分维度、语料锚点与成品示例帖已在 v2.12.25 删除,不要凭记忆重建
231
- - 帖子级采样优先用 `/reddit-voc-volume`;评论级采样才使用 SOP 中的
232
- `curl_cffi + 完整请求头 + cookie` 低频流程
231
+ - 帖子级采样优先用 `/reddit-voc-volume`;评论级采样用
232
+ `reddit-voc-volume comments`(Arctic 历史评论),当下证据走 Hub-First 或 `social-hub scrape`
233
233
  - 普通改写任务不要临时写新爬虫、不要并发抓取、不要绕过 403/429、
234
234
  不要抓私密或登录墙内容
235
235
  - 板块规则要求补充事实性上下文(specs、routine、地区、报价明细、时间跨度等)
@@ -125,130 +125,25 @@ py -3 $VocScript subreddit `
125
125
  受控值一律取 `../reddit-strategy-shared/references/content-diversity-contract.md`
126
126
  的枚举,不要自造标签——换标签的伪差异是明确禁止项。
127
127
 
128
- ### 评论样本:用 curl_cffi + 完整请求头 + cookie
129
-
130
- `reddit-voc-volume` 默认只返回帖子级字段,不返回评论正文。评论样本需要对公开 permalink 的 `.json` 端点做低频读取。
131
-
132
- 必须使用:
133
-
134
- - `curl_cffi.requests.Session(impersonate="chrome131")`
135
- - 完整 Chrome 请求头
136
- - 浏览器 cookie(`browser_cookie3` 或 `REDDIT_COOKIES_JSON`)
137
- - 先 warm `https://www.reddit.com/`
138
- - 每个帖子请求之间 sleep 2–6 秒
139
- - 遇 403/429 立即停止,不要扩量
140
-
141
- 可复用脚本:
142
-
143
- ```python
144
- import importlib.util
145
- import json
146
- import time
147
- from pathlib import Path
148
-
149
- from curl_cffi import requests
150
-
151
- voc_script = Path.home() / ".cursor/skills/reddit-voc-volume/scripts/reddit_voc_volume.py"
152
- spec = importlib.util.spec_from_file_location("reddit_voc_volume", voc_script)
153
- rv = importlib.util.module_from_spec(spec)
154
- spec.loader.exec_module(rv)
155
-
156
- UA = (
157
- "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 "
158
- "(KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36"
159
- )
160
-
161
- HEADERS = {
162
- "User-Agent": UA,
163
- "Accept": "application/json, text/plain, */*",
164
- "Accept-Language": "en-US,en;q=0.9",
165
- "Accept-Encoding": "gzip, deflate, br, zstd",
166
- "Referer": "https://www.reddit.com/",
167
- "Origin": "https://www.reddit.com",
168
- "Connection": "keep-alive",
169
- "DNT": "1",
170
- "Sec-CH-UA": '"Google Chrome";v="131", "Chromium";v="131", "Not_A Brand";v="24"',
171
- "Sec-CH-UA-Mobile": "?0",
172
- "Sec-CH-UA-Platform": '"macOS"',
173
- "Sec-Fetch-Dest": "empty",
174
- "Sec-Fetch-Mode": "cors",
175
- "Sec-Fetch-Site": "same-origin",
176
- "Priority": "u=1, i",
177
- }
178
-
179
- def comment_json_url(permalink: str) -> str:
180
- return permalink.rstrip("/") + ".json?raw_json=1&limit=20&sort=top&threaded=true"
181
-
182
- def walk_comments(children, out, depth=0):
183
- for child in children:
184
- if child.get("kind") != "t1":
185
- continue
186
- data = child.get("data") or {}
187
- body = (data.get("body") or "").strip()
188
- if body and body not in ("[deleted]", "[removed]"):
189
- out.append({
190
- "body": body[:1000],
191
- "score": data.get("score"),
192
- "depth": depth,
193
- "author": data.get("author"),
194
- "permalink": "https://www.reddit.com" + (data.get("permalink") or ""),
195
- })
196
- replies = data.get("replies")
197
- if isinstance(replies, dict):
198
- walk_comments(((replies.get("data") or {}).get("children") or []), out, depth + 1)
199
-
200
- store = rv.CookieStore.get()
201
- cookies = store.cookies
202
- proxies = rv._proxies_dict()
203
- session = requests.Session(impersonate=rv.IMPERSONATE)
204
-
205
- # Warm same-origin session. Cookie is required for many public comment JSON pages.
206
- session.get(
207
- "https://www.reddit.com/",
208
- headers=HEADERS,
209
- cookies=cookies or None,
210
- proxies=proxies or None,
211
- timeout=30,
212
- )
213
-
214
- permalinks = [
215
- # 填入本次要采样的公开帖 permalink;不要在本文件里固化真实帖子标题
216
- "<https://www.reddit.com/r/<subreddit>/comments/<id>/<slug>/>",
217
- ]
218
-
219
- samples = []
220
- for permalink in permalinks:
221
- headers = dict(HEADERS)
222
- headers["Referer"] = permalink
223
- resp = session.get(
224
- comment_json_url(permalink),
225
- headers=headers,
226
- cookies=cookies or None,
227
- proxies=proxies or None,
228
- timeout=30,
229
- )
230
- if resp.status_code in (403, 429):
231
- break
232
- resp.raise_for_status()
233
- data = resp.json()
234
- post = (((data[0].get("data") or {}).get("children") or [{}])[0].get("data") or {})
235
- comments = []
236
- if len(data) > 1:
237
- walk_comments((data[1].get("data") or {}).get("children") or [], comments)
238
- samples.append({
239
- "post_title": post.get("title"),
240
- "subreddit": post.get("subreddit"),
241
- "url": permalink,
242
- "comments": comments[:12],
243
- })
244
- time.sleep(2.5)
245
-
246
- Path("/tmp/reddit_comment_samples.json").write_text(
247
- json.dumps(samples, ensure_ascii=False, indent=2),
248
- encoding="utf-8",
249
- )
128
+ ### 评论样本:历史评论走 Arctic,当下证据走 Hub
129
+
130
+ `reddit-voc-volume` 的 `links` / `keyword` 默认只返回帖子级字段,不返回评论正文。评论样本按下面路径取,
131
+ **不要自写 reddit.com `.json` 抓取脚本**(`curl_cffi` / cookie / 指纹伪装均已移除;`.json` 对住宅代理同样 403):
132
+
133
+ - 历史评论 / 评论树:`reddit-voc-volume comments <帖子 URL 或 ID>`,直连 Arctic Shift 归档,正文不截断,
134
+ 默认 tree,另有 `--source search`(`--body` / `--author` / `--after` / `--before` / `--parent-id`)
135
+ 与 `--ids` 批查。归档评论 score 非实时,只做分布统计,不当实时数据用。
136
+ - 当下证据(刚发布、Arctic 尚未收录的帖子):走 Hub-First(`reddit-voc-volume` 的 Hub 派发),
137
+ 或用 `social-hub scrape` 抓公开渲染页;本机 Firecrawl 作为再下一级。
138
+ - `comments` 子命令没有 `--sleep-sec`;多帖采样时,两次 `comments` 调用之间手动等待至少 2 秒(脚本常量 `ARCTIC_MIN_SLEEP_SEC`)。任何一步遇 403/429/验证码立即停止,不要扩量。
139
+
140
+ ```bash
141
+ VOC=~/.cursor/skills/reddit-voc-volume/scripts/reddit_voc_volume.py
142
+ python3 "$VOC" comments "https://www.reddit.com/r/<subreddit>/comments/<id>/<slug>/" --pretty
250
143
  ```
251
144
 
145
+ 输出 JSON 的评论条目按「评论功能」做分类计数(见下节),不落盘原文库。
146
+
252
147
  ### 评论样本提炼维度
253
148
 
254
149
  不要把评论样本整段塞进模板。按“评论功能”提炼:
@@ -272,7 +167,7 @@ Path("/tmp/reddit_comment_samples.json").write_text(
272
167
 
273
168
  - 只读公开帖子和公开评论。
274
169
  - 不尝试绕过私密版、登录墙、验证码或 403/429。
275
- - Cookie 只用于减少公开页误判,不输出 cookie 值。
170
+ - 不使用 cookie 或登录态;不直连 reddit.com。
276
171
  - 单次采样控制在少量请求;不要并发刷评论页。
277
172
  - 采样结果仅用于分布统计与 `SampleSetID` baseline manifest,不用于复制原文,
278
173
  也不用于提炼跨板块统一风格。
@@ -36,30 +36,29 @@ Step 6 ── EPA-5:淘汰行补充备选 URL → 重新从 EPA-0 开始
36
36
  **执行:** 从执行表中提取当批全部外部评论行的 Reddit URL,调用 `reddit-voc-volume` skill 的 `links` 模式:
37
37
 
38
38
  ```bash
39
- # macOS 可选:Anker 仓库包装脚本(自动 REDDIT_USE_BROWSER_COOKIES=1)
40
- # <Anker项目根>/Tools/reddit-voc/run_reddit_voc.sh links "URL1" "URL2" --pretty
41
-
42
- # 推荐:直接调用本 skill 脚本(须 export REDDIT_USE_BROWSER_COOKIES=1)
43
- export REDDIT_USE_BROWSER_COOKIES=1
39
+ # 直接调用本 skill 脚本;不需要 cookie 或任何浏览器环境变量。
40
+ # 显式加 --fallback auto:Arctic 未命中时依次尝试 Social Hub 渲染页、本机 Firecrawl。
44
41
  python3 ~/.cursor/skills/reddit-voc-volume/scripts/reddit_voc_volume.py links \
45
42
  "https://www.reddit.com/r/.../comments/xxx/..." \
46
43
  "https://www.reddit.com/r/.../comments/yyy/..." \
44
+ --fallback auto \
47
45
  --pretty
48
46
  ```
49
47
 
50
48
  Windows PowerShell:
51
49
 
52
50
  ```powershell
53
- $env:REDDIT_USE_BROWSER_COOKIES = "1"
54
51
  $SkillsRoot = Join-Path $HOME ".cursor\skills"
55
52
  $VocScript = Join-Path $SkillsRoot "reddit-voc-volume\scripts\reddit_voc_volume.py"
56
53
  py -3 $VocScript links `
57
54
  "https://www.reddit.com/r/.../comments/xxx/..." `
58
55
  "https://www.reddit.com/r/.../comments/yyy/..." `
56
+ --fallback auto `
59
57
  --pretty
60
58
  ```
61
59
 
62
- > **Cookie 自检:** `request_identity.used_cookies` 须为 true;JSON 连续 403/429 时读已安装 `reddit-voc-volume/references/browser-fallback.md`。
60
+ > **取数自检:** 脚本自 v2.12.28 起不再直连 reddit.com,也不读 cookie;`request_identity`(含 `used_cookies`、`fetch_mode`)只是兼容字段,`used_cookies` 恒为 false,**不能**拿来判定成败。改查:顶层 `ok` 为 true、`errors` 为空。
61
+ > 注意区分两层来源:顶层 `provenance` 是「采集编排来源」(`links` 模式下恒为 `emergency_local`,不能据此判断数据从哪来);**具体数据来源**看每条 `items[].source_fetch`:`arctic_shift` 表示 Arctic 归档命中,`social_hub_scrape` / `firecrawl` 表示 Arctic 未命中、改走渲染页证据(`item_type` 为 `firecrawl_page`)。若未加 `--fallback auto` 且 Arctic 未命中、结果为空或 `errors` 非空,加该参数重跑。Arctic 与渲染页都取不到时,读已安装 `reddit-voc-volume/references/browser-fallback.md`。
63
62
 
64
63
  **从返回 JSON 提取以下字段(每条 URL 对应一个 item):**
65
64
 
@@ -22,13 +22,13 @@
22
22
  "contentSha256": "08023a5dfa6cc2f3ffc3f1a551479c645ddcfc8cc775f88cd2d245c067829482"
23
23
  },
24
24
  "reddit-content-rewrite": {
25
- "contentSha256": "2f9dfdbb2410d060f755860b57ebc7c6776f4df343990029a8770855ecd33005"
25
+ "contentSha256": "b42bfea525bd11646d6c15ae081d00137c114835611d01b77354698d4b05f00e"
26
26
  },
27
27
  "reddit-delivery-check": {
28
28
  "contentSha256": "9231ff9ae5d950bc2fb87e45bee05e793b3ff9c37bee45e8444059a8b698e4a9"
29
29
  },
30
30
  "reddit-voc-volume": {
31
- "contentSha256": "7b068ab2fb50627978ec54bea3c76d12333b5438dd40f16204d1982ae5e9d95c"
31
+ "contentSha256": "f6b81203fb6892d367ec95f2e29caa21cad657559636f59248975a604353e725"
32
32
  },
33
33
  "reddit-brand-risk-response": {
34
34
  "contentSha256": "dbba80345ebe68818a25e7604dfaa6951c6bf0e4d785d5013be7a06b22ec5b7c"
@@ -43,7 +43,7 @@
43
43
  "contentSha256": "808659c48e546e8ce35e32ec42c68d35e3f843ec41d4974ea8eabd1da1dac7ce"
44
44
  },
45
45
  "reddit-ext-post-audit": {
46
- "contentSha256": "7ebe1b407c1897a6ba7620c6ae6ec16d206b3a7b0be3d1d30618705d58492214"
46
+ "contentSha256": "f14b469768ebf1dd2687b4e9c26f66fd141889b45710e3adee7b015ebdf35f64"
47
47
  }
48
48
  }
49
49
  }
@@ -47,7 +47,7 @@ description: |
47
47
 
48
48
 
49
49
  Python 3.10+;网络可访问 **arctic-shift.photon-reddit.com**(历史/评论/版规/wiki/about)与 Social Hub / 本机 Firecrawl(渲染页证据);建议配置 HTTPS_PROXY。
50
- **本机不直连 reddit.com**:渲染页由 Hub / Firecrawl 代为访问。`curl`、`curl_cffi`、`browser_cookie3` 与 `--via-curl` 均为 v2.12.28 前的遗留物,当前代码路径用不到(见下节「请求身份」)。
50
+ **本机不直连 reddit.com**:渲染页由 Hub / Firecrawl 代为访问。脚本只依赖 Python 标准库,不需要 `curl`、`curl_cffi`、`browser_cookie3`;v2.12.28 前的这些直连实现的直连实现已删除;`--via-curl` 仅作为废弃空参数保留一个发布周期(见下节「请求身份」)。
51
51
 
52
52
  ## 何时用 / 不用
53
53
 
@@ -400,10 +400,12 @@ v2.12.23 沿用 v2.12.12 引入的安全默认采样:`limit=10 / sleep=6`,
400
400
  渲染页证据走 Social Hub / Firecrawl。**2026-09-18 实测:`.json` 对住宅代理同样 403**,
401
401
  Reddit 侧封控已不是「换个指纹/加 cookie 就能过」的问题,别再把它当可选通道。
402
402
 
403
- 遗留物盘点:`RedditHttpClient` / `CookieStore` 仍有定义,但主流程不再实例化客户端,也不会读取浏览器 cookie;
404
- `--via-curl` 是保留的空开关;`fetch_via_curl_cffi` / `http_get_json_via_curl` 只有定义没有调用。
405
- `requirements.txt` 的 `curl_cffi`、`browser_cookie3` 当前路径用不到。输出信封里的
406
- `request_identity.*` 是兼容字段,**不表示真的打过 reddit.com**。
403
+ 遗留代码已删除:`RedditHttpClient` / `CookieStore` / `http_get_json_via_curl` / `fetch_via_curl_cffi` 与
404
+ `curl_cffi`、`browser_cookie3` 依赖均不复存在,`--via-curl`(keyword / subreddit / stickies / links)只剩废弃空参数:传入只向 stderr 打 `DEPRECATED` 提示,不影响取数与退出码,**下一版移除**,请勿再传。
405
+ 输出信封里的 `request_identity` 仍保留以兼容下游:`used_cookies` 恒为 `false`、`cookie_source` 恒为 `null`、
406
+ `cookie_cache_reused` 恒为 `false`、`impersonation` 恒为 `null`,`fetch_mode` 目前恒为 `"none"`
407
+ (脚本没有直连 reddit.com 的取数方式可记录);`proxy_used` 反映是否解析到 HTTPS 代理。
408
+ 这些字段**不表示真的打过 reddit.com**。浏览器兜底由 agent 手工回填时才会写 `fetch_mode: "browser_fallback"`。
407
409
 
408
410
  `links` 模式四种目标现在全部走 Arctic:帖子 permalink → `arctic_post_by_permalink`,
409
411
  about / rules / wiki → 对应的 `arctic_*_as_reddit_payload`;取不到才按 `--fallback` 走 Hub / Firecrawl 渲染页。
@@ -473,10 +475,12 @@ Social Hub / Firecrawl 渲染页。
473
475
  "rate_limited": false
474
476
  },
475
477
  "request_identity": {
476
- "fetch_mode": "curl_cffi",
477
- "used_cookies": true,
478
- "cookie_source": "browser",
479
- "impersonation": "chrome131",
478
+ "user_agent_kind": "chrome",
479
+ "fetch_mode": "none",
480
+ "used_cookies": false,
481
+ "cookie_source": null,
482
+ "cookie_cache_reused": false,
483
+ "impersonation": null,
480
484
  "proxy_used": true
481
485
  },
482
486
  "notes": [],
@@ -15,7 +15,7 @@ Pushshift 停摆后的接续者。**无需 auth**,免费公开服务,作者
15
15
  v2.12.26 修掉正文截断后,baseline 卡的长度维度只接受未截断全文。但多数网络
16
16
  环境下 reddit.com 的 `.json` 直采已被拦截(实测本机:`curl (56) CONNECT tunnel
17
17
  failed 403`,去掉代理直连亦为 `403 Blocked`)。Arctic Shift 不走 reddit.com,
18
- 不需要 cookie / curl_cffi 伪装,且**正文不截断**。
18
+ 不需要 cookie 或指纹伪装,且**正文不截断**。
19
19
 
20
20
  ## 覆盖范围(实测,非文档转述)
21
21
 
@@ -1,5 +1,2 @@
1
1
  # Reddit VOC volume — Python dependencies
2
- # 以下两项仅供未调用的旧 Reddit HTTP 函数使用。主流程不实例化旧客户端,
3
- # 不读取浏览器 cookie;不安装也不影响当前模式。
4
- curl_cffi>=0.7.0
5
- browser_cookie3>=0.19.0
2
+ # 无第三方 Python 依赖:脚本只用标准库(Arctic / Social Hub / Firecrawl 均走 urllib 或 CLI)。