ソースを参照

修:设了「提取满 N 个」之后,uid 解析阶段一个都换不到

现象(用户 03:17 那次,limit=3):
  [idflow] 开始解析数字 uid:3 个
  [resolve] 收到停止,已换 0/3 个        ← 第一个都还没开始就说"收到停止"
  [idflow] uid 解析完成:成功 0 / 失败 0

根因:shouldStop() 里含 limitReached()
  shouldStop() = limitReached() || timeUp()
  limitReached() 是**抓取阶段**的条件("收够了别再往外抓"),
  而解析 uid 是**收尾工作**,恰恰在抓满之后才做
  → 传 shouldStop 进去等于一进去就自杀。

  同一次运行里 limit 还是被**深度展开**填满的(第 2、3 个在展开阶段收的),
  所以现象更隐蔽:抓取看起来"正常结束",只是 uid 全丢。

  上一轮测的是 limit=0,所以没暴露 —— 测试盲区。

修
- resolvePhase 传给 resolveAll 的 shouldStop 改成只传 timeUp:
  抓满上限 ≠ 放弃收尾;用户主动停止靠 StopSignal 从 wait.tick 抛出,不需轮询;
  时长护栏仍生效
- resolveAll 里 "收到停止" 改成 "到达时长上限" —— 原来那句把"跑太久"和
  "用户点了停止"混为一谈,这次就是被它带偏了一轮

验证(limit=2 + 输入 3 个)
  resolved=2 / unresolved=0 / mapFile 生成
  [resolve] beautifulsoul78869 → 254801657882882048(via html)
  [resolve] ttbeauties6 → 7666124051215025169(via html)
  warnings: 已提取满 2 个,按设置停止
  message: 完成:提取 2 个 ID(已生成 uid 映射)

通则:**"停止"在不同阶段含义不同**。抓取阶段的"够了"与收尾阶段的"必须做完"
是相反的要求;共用一个 shouldStop() 就是把它们混在一起。
收尾阶段只该继承外部强制条件(用户叫停、总时长),不该继承业务完成条件(达到目标数量)。
梦境 1 週間 前
親
コミット
e7a2645f33
3 ファイル変更、39 行追加、5 行削除
  1. 20 3
      tiktok-auto/dist/tiktok-auto.js
  2. 15 1
      tiktok-auto/src/idflow.js
  3. 4 1
      tiktok-auto/src/resolve.js

+ 20 - 3
tiktok-auto/dist/tiktok-auto.js

@@ -1,5 +1,5 @@
 /*! tiktok-auto v1.0.0
- *  built 2026-10-20T09:16:16.854Z
+ *  built 2026-10-20T10:29:07.437Z
  *  modules: logger, bridge, config, wait, layout, ui, popups, tiktok, player, comment, flow, parse, uidset, filters, profile, idsource, resolve, idflow, main
  *  由 tools/build.js 自动生成 —— 请不要直接编辑本文件,改 src/ 后重新构建。
  */
@@ -5890,7 +5890,10 @@ TikTokAuto.resolve = (function () {
 
         for (var i = 0; i < total; i += 1) {
             if (settings.shouldStop && settings.shouldStop()) {
-                log.warn('resolve', '收到停止,已换 ' + map.length + '/' + total + ' 个');
+                /* 注意措辞:这里的 shouldStop 只反映**时长护栏**,
+                 * 不含"提取上限已到"(那个属于抓取阶段,不该阻止收尾)。
+                 * 早先写成"收到停止",把"跑太久"和"用户点了停止"混为一谈,排查时很误导。 */
+                log.warn('resolve', '到达时长上限,已换 ' + map.length + '/' + total + ' 个');
                 return { ok: true, map: map, failed: failed, stopped: true };
             }
             var name = usernames[i];
@@ -6158,7 +6161,21 @@ TikTokAuto.idflow = (function () {
 
             log.step('idflow', '开始解析数字 uid:' + names.length + ' 个(每个约 2~3 秒)');
             var result = TikTokAuto.resolve.resolveAll(names, {
-                shouldStop: shouldStop,
+                /**
+                 * ★ 这里**故意不传 shouldStop()**。
+                 *
+                 * `shouldStop()` 里含 `limitReached()` —— 那是**抓取阶段**的停止条件:
+                 * "已经收够这么多个了,别再往外抓"。而解析 uid 是**收尾工作**,
+                 * 恰恰是在抓满之后才需要做。
+                 *
+                 * 早先直接传 shouldStop(),于是设了「提取满 3 个」的用户:
+                 * 抓满 3 个 → limitReached() 一直为真 → 解析阶段第一句就被判"收到停止"
+                 * → 一个 uid 都换不到(实测 3 个全丢,日志只有一行"收到停止,已换 0/3")。
+                 *
+                 * 只保留时长护栏:用户主动停止靠 StopSignal 从 `wait.tick` 抛出,
+                 * 不需要在这里轮询。
+                 */
+                shouldStop: timeUp,
                 onProgress: function (done, total) {
                     progress('解析 uid ' + done + '/' + total, target.extracted);
                 }

+ 15 - 1
tiktok-auto/src/idflow.js

@@ -211,7 +211,21 @@ TikTokAuto.idflow = (function () {
 
             log.step('idflow', '开始解析数字 uid:' + names.length + ' 个(每个约 2~3 秒)');
             var result = TikTokAuto.resolve.resolveAll(names, {
-                shouldStop: shouldStop,
+                /**
+                 * ★ 这里**故意不传 shouldStop()**。
+                 *
+                 * `shouldStop()` 里含 `limitReached()` —— 那是**抓取阶段**的停止条件:
+                 * "已经收够这么多个了,别再往外抓"。而解析 uid 是**收尾工作**,
+                 * 恰恰是在抓满之后才需要做。
+                 *
+                 * 早先直接传 shouldStop(),于是设了「提取满 3 个」的用户:
+                 * 抓满 3 个 → limitReached() 一直为真 → 解析阶段第一句就被判"收到停止"
+                 * → 一个 uid 都换不到(实测 3 个全丢,日志只有一行"收到停止,已换 0/3")。
+                 *
+                 * 只保留时长护栏:用户主动停止靠 StopSignal 从 `wait.tick` 抛出,
+                 * 不需要在这里轮询。
+                 */
+                shouldStop: timeUp,
                 onProgress: function (done, total) {
                     progress('解析 uid ' + done + '/' + total, target.extracted);
                 }

+ 4 - 1
tiktok-auto/src/resolve.js

@@ -346,7 +346,10 @@ TikTokAuto.resolve = (function () {
 
         for (var i = 0; i < total; i += 1) {
             if (settings.shouldStop && settings.shouldStop()) {
-                log.warn('resolve', '收到停止,已换 ' + map.length + '/' + total + ' 个');
+                /* 注意措辞:这里的 shouldStop 只反映**时长护栏**,
+                 * 不含"提取上限已到"(那个属于抓取阶段,不该阻止收尾)。
+                 * 早先写成"收到停止",把"跑太久"和"用户点了停止"混为一谈,排查时很误导。 */
+                log.warn('resolve', '到达时长上限,已换 ' + map.length + '/' + total + ' 个');
                 return { ok: true, map: map, failed: failed, stopped: true };
             }
             var name = usernames[i];