baxian 2.0.2 → 2.0.4
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.
- package/README.md +2 -2
- package/README.zh-CN.md +3 -3
- package/dist/agent/bootstrap.js +4 -4
- package/dist/agent/branch.d.ts.map +1 -1
- package/dist/agent/branch.js +0 -7
- package/dist/agent/branch.js.map +1 -1
- package/dist/agent/detect/region.d.ts.map +1 -1
- package/dist/agent/detect/region.js +0 -3
- package/dist/agent/detect/region.js.map +1 -1
- package/dist/agent/dispatch-reconciler.d.ts +2 -0
- package/dist/agent/dispatch-reconciler.d.ts.map +1 -1
- package/dist/agent/dispatch-reconciler.js +48 -55
- package/dist/agent/dispatch-reconciler.js.map +1 -1
- package/dist/agent/lineage.d.ts.map +1 -1
- package/dist/agent/lineage.js +0 -9
- package/dist/agent/lineage.js.map +1 -1
- package/dist/agent/manager.d.ts +42 -8
- package/dist/agent/manager.d.ts.map +1 -1
- package/dist/agent/manager.js +717 -375
- package/dist/agent/manager.js.map +1 -1
- package/dist/agent/net-exec.d.ts.map +1 -1
- package/dist/agent/net-exec.js +0 -5
- package/dist/agent/net-exec.js.map +1 -1
- package/dist/agent/pane-streamer-manager.d.ts.map +1 -1
- package/dist/agent/pane-streamer-manager.js +0 -36
- package/dist/agent/pane-streamer-manager.js.map +1 -1
- package/dist/agent/pane-streamer.d.ts +6 -0
- package/dist/agent/pane-streamer.d.ts.map +1 -1
- package/dist/agent/pane-streamer.js +126 -83
- package/dist/agent/pane-streamer.js.map +1 -1
- package/dist/agent/phase-signal-watcher.d.ts.map +1 -1
- package/dist/agent/phase-signal-watcher.js +2 -77
- package/dist/agent/phase-signal-watcher.js.map +1 -1
- package/dist/agent/phase-signal.d.ts +0 -1
- package/dist/agent/phase-signal.d.ts.map +1 -1
- package/dist/agent/phase-signal.js +0 -17
- package/dist/agent/phase-signal.js.map +1 -1
- package/dist/agent/preflight.d.ts.map +1 -1
- package/dist/agent/preflight.js +0 -18
- package/dist/agent/preflight.js.map +1 -1
- package/dist/agent/prompt.d.ts.map +1 -1
- package/dist/agent/prompt.js +0 -1
- package/dist/agent/prompt.js.map +1 -1
- package/dist/agent/repo-store.d.ts.map +1 -1
- package/dist/agent/repo-store.js +0 -38
- package/dist/agent/repo-store.js.map +1 -1
- package/dist/agent/runner.d.ts.map +1 -1
- package/dist/agent/runner.js +0 -2
- package/dist/agent/runner.js.map +1 -1
- package/dist/agent/tmux-install.js +0 -1
- package/dist/agent/tmux-install.js.map +1 -1
- package/dist/agent/tmux-probe-poller.d.ts.map +1 -1
- package/dist/agent/tmux-probe-poller.js +4 -11
- package/dist/agent/tmux-probe-poller.js.map +1 -1
- package/dist/agent/tmux.d.ts.map +1 -1
- package/dist/agent/tmux.js +0 -86
- package/dist/agent/tmux.js.map +1 -1
- package/dist/agent/vt-visible-text.d.ts +46 -1
- package/dist/agent/vt-visible-text.d.ts.map +1 -1
- package/dist/agent/vt-visible-text.js +639 -63
- package/dist/agent/vt-visible-text.js.map +1 -1
- package/dist/api/agents.d.ts.map +1 -1
- package/dist/api/agents.js +3 -49
- package/dist/api/agents.js.map +1 -1
- package/dist/api/config.d.ts.map +1 -1
- package/dist/api/config.js +10 -59
- package/dist/api/config.js.map +1 -1
- package/dist/api/hosts.d.ts.map +1 -1
- package/dist/api/hosts.js +8 -63
- package/dist/api/hosts.js.map +1 -1
- package/dist/api/platform-guard.d.ts.map +1 -1
- package/dist/api/platform-guard.js +2 -3
- package/dist/api/platform-guard.js.map +1 -1
- package/dist/api/probe.d.ts.map +1 -1
- package/dist/api/probe.js +0 -1
- package/dist/api/probe.js.map +1 -1
- package/dist/api/projects.d.ts.map +1 -1
- package/dist/api/projects.js +15 -28
- package/dist/api/projects.js.map +1 -1
- package/dist/api/tasks.d.ts.map +1 -1
- package/dist/api/tasks.js +94 -58
- package/dist/api/tasks.js.map +1 -1
- package/dist/app.d.ts +2 -2
- package/dist/app.d.ts.map +1 -1
- package/dist/app.js +0 -6
- package/dist/app.js.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +6 -31
- package/dist/cli.js.map +1 -1
- package/dist/config/hot-reload.d.ts.map +1 -1
- package/dist/config/hot-reload.js +0 -4
- package/dist/config/hot-reload.js.map +1 -1
- package/dist/config/loader.d.ts.map +1 -1
- package/dist/config/loader.js +6 -29
- package/dist/config/loader.js.map +1 -1
- package/dist/config/normalizer.d.ts.map +1 -1
- package/dist/config/normalizer.js +0 -19
- package/dist/config/normalizer.js.map +1 -1
- package/dist/config/validator.d.ts.map +1 -1
- package/dist/config/validator.js +31 -229
- package/dist/config/validator.js.map +1 -1
- package/dist/event/handlers.d.ts.map +1 -1
- package/dist/event/handlers.js +3 -11
- package/dist/event/handlers.js.map +1 -1
- package/dist/event/log.js +0 -2
- package/dist/event/log.js.map +1 -1
- package/dist/event/ws.d.ts.map +1 -1
- package/dist/event/ws.js +3 -3
- package/dist/event/ws.js.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +5 -46
- package/dist/index.js.map +1 -1
- package/dist/platform/body-digest.d.ts.map +1 -1
- package/dist/platform/body-digest.js +0 -4
- package/dist/platform/body-digest.js.map +1 -1
- package/dist/platform/command-renderer.d.ts.map +1 -1
- package/dist/platform/command-renderer.js +0 -3
- package/dist/platform/command-renderer.js.map +1 -1
- package/dist/platform/comment-cursor.d.ts.map +1 -1
- package/dist/platform/comment-cursor.js +0 -21
- package/dist/platform/comment-cursor.js.map +1 -1
- package/dist/platform/driver-spec.d.ts.map +1 -1
- package/dist/platform/driver-spec.js +1 -42
- package/dist/platform/driver-spec.js.map +1 -1
- package/dist/platform/feedback.d.ts +5 -1
- package/dist/platform/feedback.d.ts.map +1 -1
- package/dist/platform/feedback.js +7 -1
- package/dist/platform/feedback.js.map +1 -1
- package/dist/platform/field-mapper.d.ts.map +1 -1
- package/dist/platform/field-mapper.js +3 -11
- package/dist/platform/field-mapper.js.map +1 -1
- package/dist/platform/git-driver.d.ts.map +1 -1
- package/dist/platform/git-driver.js +0 -20
- package/dist/platform/git-driver.js.map +1 -1
- package/dist/platform/manifest.d.ts.map +1 -1
- package/dist/platform/manifest.js +0 -3
- package/dist/platform/manifest.js.map +1 -1
- package/dist/platform/markers.d.ts.map +1 -1
- package/dist/platform/markers.js +0 -19
- package/dist/platform/markers.js.map +1 -1
- package/dist/platform/platform-poller.d.ts +5 -1
- package/dist/platform/platform-poller.d.ts.map +1 -1
- package/dist/platform/platform-poller.js +8 -49
- package/dist/platform/platform-poller.js.map +1 -1
- package/dist/platform/plugin-registry.d.ts.map +1 -1
- package/dist/platform/plugin-registry.js +1 -12
- package/dist/platform/plugin-registry.js.map +1 -1
- package/dist/platform/pr-conversation-cache.d.ts +12 -7
- package/dist/platform/pr-conversation-cache.d.ts.map +1 -1
- package/dist/platform/pr-conversation-cache.js +60 -40
- package/dist/platform/pr-conversation-cache.js.map +1 -1
- package/dist/platform/preflight-exec.d.ts.map +1 -1
- package/dist/platform/preflight-exec.js +0 -9
- package/dist/platform/preflight-exec.js.map +1 -1
- package/dist/platform/response-parser.d.ts.map +1 -1
- package/dist/platform/response-parser.js +0 -4
- package/dist/platform/response-parser.js.map +1 -1
- package/dist/platform/review-timeline.d.ts +17 -2
- package/dist/platform/review-timeline.d.ts.map +1 -1
- package/dist/platform/review-timeline.js +93 -106
- package/dist/platform/review-timeline.js.map +1 -1
- package/dist/platform/row-schema.d.ts.map +1 -1
- package/dist/platform/row-schema.js +0 -11
- package/dist/platform/row-schema.js.map +1 -1
- package/dist/platform/startup.d.ts.map +1 -1
- package/dist/platform/startup.js +1 -12
- package/dist/platform/startup.js.map +1 -1
- package/dist/platform/types.d.ts.map +1 -1
- package/dist/platform/types.js +0 -5
- package/dist/platform/types.js.map +1 -1
- package/dist/platform/verdict-engine.d.ts.map +1 -1
- package/dist/platform/verdict-engine.js +0 -15
- package/dist/platform/verdict-engine.js.map +1 -1
- package/dist/shared/concurrency.d.ts.map +1 -1
- package/dist/shared/concurrency.js +0 -2
- package/dist/shared/concurrency.js.map +1 -1
- package/dist/shared/constants.d.ts +0 -2
- package/dist/shared/constants.d.ts.map +1 -1
- package/dist/shared/constants.js +0 -3
- package/dist/shared/constants.js.map +1 -1
- package/dist/shared/git-url.d.ts.map +1 -1
- package/dist/shared/git-url.js +0 -9
- package/dist/shared/git-url.js.map +1 -1
- package/dist/shared/types.d.ts +31 -12
- package/dist/shared/types.d.ts.map +1 -1
- package/dist/shared/types.js +14 -0
- package/dist/shared/types.js.map +1 -1
- package/dist/skill/registry.d.ts.map +1 -1
- package/dist/skill/registry.js +0 -5
- package/dist/skill/registry.js.map +1 -1
- package/dist/skills/baxian-signals/SKILL.md +0 -6
- package/dist/state/agent-store.d.ts.map +1 -1
- package/dist/state/agent-store.js +0 -6
- package/dist/state/agent-store.js.map +1 -1
- package/dist/state/error-record-store.d.ts.map +1 -1
- package/dist/state/error-record-store.js +0 -5
- package/dist/state/error-record-store.js.map +1 -1
- package/dist/state/init.d.ts.map +1 -1
- package/dist/state/init.js +0 -1
- package/dist/state/init.js.map +1 -1
- package/dist/state/lock.d.ts.map +1 -1
- package/dist/state/lock.js +0 -1
- package/dist/state/lock.js.map +1 -1
- package/dist/state/snapshot.d.ts +0 -1
- package/dist/state/snapshot.d.ts.map +1 -1
- package/dist/state/snapshot.js +0 -13
- package/dist/state/snapshot.js.map +1 -1
- package/dist/state/task-store.d.ts.map +1 -1
- package/dist/state/task-store.js +96 -11
- package/dist/state/task-store.js.map +1 -1
- package/dist/terminal/attach.d.ts.map +1 -1
- package/dist/terminal/attach.js +0 -4
- package/dist/terminal/attach.js.map +1 -1
- package/dist/terminal/stream-ws.js +0 -5
- package/dist/terminal/stream-ws.js.map +1 -1
- package/dist/web/assets/index-CzVzThuT.js +15 -0
- package/dist/web/assets/{index-BS2adAfI.css → index-Rmp4wT_5.css} +1 -1
- package/dist/web/index.html +2 -2
- package/package.json +1 -1
- package/dist/agent/root-agent-runtime.d.ts +0 -80
- package/dist/agent/root-agent-runtime.d.ts.map +0 -1
- package/dist/agent/root-agent-runtime.js +0 -637
- package/dist/agent/root-agent-runtime.js.map +0 -1
- package/dist/agent/root-recovery-coordinator.d.ts +0 -124
- package/dist/agent/root-recovery-coordinator.d.ts.map +0 -1
- package/dist/agent/root-recovery-coordinator.js +0 -1557
- package/dist/agent/root-recovery-coordinator.js.map +0 -1
- package/dist/state/root-recovery-store.d.ts +0 -107
- package/dist/state/root-recovery-store.d.ts.map +0 -1
- package/dist/state/root-recovery-store.js +0 -400
- package/dist/state/root-recovery-store.js.map +0 -1
- package/dist/web/assets/index-BKiM0MSM.js +0 -15
|
@@ -1,17 +1,15 @@
|
|
|
1
|
-
export const PR_CONVERSATION_CACHE_TTL_MS = 60_000;
|
|
2
|
-
// 限流结果必须服务端共享退避:只靠客户端计时挡不住刷新、第二个浏览器与重复 mount,
|
|
3
|
-
// 而限流期间继续打平台可能导致集成被封禁(GitHub 明示)。
|
|
4
1
|
export const PR_CONVERSATION_RATE_LIMIT_TTL_MS = 60_000;
|
|
5
|
-
// 窗口过期后仍记住连击一段时间:立即遗忘会让每次重试都从 60s 起,指数增长永不生效。
|
|
6
2
|
const RATE_LIMIT_STRIKE_MEMORY_MS = 10 * 60_000;
|
|
7
|
-
// 与 poller 的限流退避同上限:无封顶的 2^n 会在连续五六次后把端点锁死数小时,
|
|
8
|
-
// 平台早已恢复也无法自愈(进入长窗口后连重建都不再发生,计数也就永不清零)。
|
|
9
3
|
const RATE_LIMIT_MAX_WAIT_MS = 900_000;
|
|
10
4
|
export const PR_CONVERSATION_CACHE_MAX_ENTRIES = 64;
|
|
11
5
|
export const PR_CONVERSATION_CACHE_MAX_PAYLOAD_BYTES = 2 * 1024 * 1024;
|
|
12
6
|
export const PR_CONVERSATION_CACHE_MAX_TOTAL_BYTES = 16 * 1024 * 1024;
|
|
13
|
-
|
|
14
|
-
|
|
7
|
+
export function closedUnmergedAnchorSlot(task) {
|
|
8
|
+
const anchor = task.closedUnmergedAnchor;
|
|
9
|
+
if (anchor === undefined)
|
|
10
|
+
return '';
|
|
11
|
+
return `${anchor.generation}/${anchor.cleared === true ? 'reopened' : 'closed'}`;
|
|
12
|
+
}
|
|
15
13
|
export function prReviewCacheRevision(task, repoKey) {
|
|
16
14
|
return [
|
|
17
15
|
task.reviewRound,
|
|
@@ -21,11 +19,11 @@ export function prReviewCacheRevision(task, repoKey) {
|
|
|
21
19
|
task.prFeedbackReceivedAt ?? '',
|
|
22
20
|
task.prNumber ?? '',
|
|
23
21
|
task.reviewConversationUpdatedAt ?? '',
|
|
22
|
+
closedUnmergedAnchorSlot(task),
|
|
24
23
|
repoKey,
|
|
25
24
|
].join(':');
|
|
26
25
|
}
|
|
27
26
|
export class PrConversationCache {
|
|
28
|
-
ttlMs;
|
|
29
27
|
maxEntries;
|
|
30
28
|
maxPayloadBytes;
|
|
31
29
|
maxTotalBytes;
|
|
@@ -33,22 +31,43 @@ export class PrConversationCache {
|
|
|
33
31
|
entries = new Map();
|
|
34
32
|
rateLimited = new Map();
|
|
35
33
|
inflight = new Map();
|
|
34
|
+
// put() 建立的 conversationTime 下限:任务快照早于最后一次 poller 写入的 build 不得落盘
|
|
35
|
+
putFloors = new Map();
|
|
36
36
|
totalBytes = 0;
|
|
37
37
|
constructor(opts = {}) {
|
|
38
|
-
this.ttlMs = opts.ttlMs ?? PR_CONVERSATION_CACHE_TTL_MS;
|
|
39
38
|
this.maxEntries = opts.maxEntries ?? PR_CONVERSATION_CACHE_MAX_ENTRIES;
|
|
40
39
|
this.maxPayloadBytes = opts.maxPayloadBytes ?? PR_CONVERSATION_CACHE_MAX_PAYLOAD_BYTES;
|
|
41
40
|
this.maxTotalBytes = opts.maxTotalBytes ?? PR_CONVERSATION_CACHE_MAX_TOTAL_BYTES;
|
|
42
41
|
this.now = opts.now ?? Date.now;
|
|
43
42
|
}
|
|
44
|
-
async get(key, revision, build) {
|
|
45
|
-
this.
|
|
43
|
+
async get(key, revision, build, conversationTime = '') {
|
|
44
|
+
this.sweepRateLimited();
|
|
46
45
|
const entry = this.entries.get(key);
|
|
47
|
-
if (entry && entry.revision === revision
|
|
48
|
-
return entry
|
|
46
|
+
if (entry && entry.revision === revision) {
|
|
47
|
+
return this.stamped(entry);
|
|
49
48
|
}
|
|
50
|
-
|
|
51
|
-
|
|
49
|
+
return this.buildThrough(key, revision, build, conversationTime);
|
|
50
|
+
}
|
|
51
|
+
async force(key, revision, build, conversationTime = '') {
|
|
52
|
+
this.sweepRateLimited();
|
|
53
|
+
return this.buildThrough(key, revision, build, conversationTime);
|
|
54
|
+
}
|
|
55
|
+
put(key, revision, payload, conversationTime = '') {
|
|
56
|
+
if (payload.error !== undefined || payload.rateLimited === true)
|
|
57
|
+
return;
|
|
58
|
+
this.sweepRateLimited();
|
|
59
|
+
this.setPutFloor(key, conversationTime);
|
|
60
|
+
this.inflight.delete(key);
|
|
61
|
+
this.rateLimited.delete(key);
|
|
62
|
+
this.store(key, revision, payload);
|
|
63
|
+
}
|
|
64
|
+
stats() {
|
|
65
|
+
return {
|
|
66
|
+
entries: this.entries.size + this.rateLimited.size,
|
|
67
|
+
totalBytes: this.totalBytes + this.rateLimitedBytes(),
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
async buildThrough(key, revision, build, conversationTime) {
|
|
52
71
|
const throttled = this.rateLimited.get(key);
|
|
53
72
|
if (throttled !== undefined) {
|
|
54
73
|
if (this.now() < throttled.until) {
|
|
@@ -56,7 +75,6 @@ export class PrConversationCache {
|
|
|
56
75
|
? throttled.payload
|
|
57
76
|
: { items: [], error: throttled.payload.error ?? 'rate limited', rateLimited: true };
|
|
58
77
|
}
|
|
59
|
-
// 窗口已过:放行本次重建,但保留连击计数(并丢掉 payload 只留状态)供指数增长使用。
|
|
60
78
|
this.rateLimited.set(key, {
|
|
61
79
|
...throttled,
|
|
62
80
|
payload: { items: [], rateLimited: true },
|
|
@@ -67,7 +85,6 @@ export class PrConversationCache {
|
|
|
67
85
|
if (running && running.revision === revision) {
|
|
68
86
|
return running.promise;
|
|
69
87
|
}
|
|
70
|
-
// revision 不同:直接取代注册,旧构建继续跑但落定时不再拥有写入权。
|
|
71
88
|
const reg = { revision, promise: Promise.resolve({ items: [] }) };
|
|
72
89
|
reg.promise = (async () => {
|
|
73
90
|
try {
|
|
@@ -78,8 +95,12 @@ export class PrConversationCache {
|
|
|
78
95
|
this.noteRateLimited(key, revision, payload);
|
|
79
96
|
else {
|
|
80
97
|
this.rateLimited.delete(key);
|
|
81
|
-
if (!payload.error)
|
|
82
|
-
this.
|
|
98
|
+
if (!payload.error) {
|
|
99
|
+
if (!this.fencedByPut(key, conversationTime)) {
|
|
100
|
+
this.store(key, revision, payload);
|
|
101
|
+
}
|
|
102
|
+
return { ...payload, fetchedAt: new Date(this.now()).toISOString() };
|
|
103
|
+
}
|
|
83
104
|
}
|
|
84
105
|
}
|
|
85
106
|
return payload;
|
|
@@ -93,21 +114,24 @@ export class PrConversationCache {
|
|
|
93
114
|
this.inflight.set(key, reg);
|
|
94
115
|
return reg.promise;
|
|
95
116
|
}
|
|
96
|
-
|
|
97
|
-
return {
|
|
98
|
-
entries: this.entries.size + this.rateLimited.size,
|
|
99
|
-
totalBytes: this.totalBytes + this.rateLimitedBytes(),
|
|
100
|
-
};
|
|
117
|
+
stamped(entry) {
|
|
118
|
+
return { ...entry.payload, fetchedAt: new Date(entry.fetchedAt).toISOString() };
|
|
101
119
|
}
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
if (
|
|
108
|
-
|
|
120
|
+
setPutFloor(key, conversationTime) {
|
|
121
|
+
this.putFloors.delete(key);
|
|
122
|
+
this.putFloors.set(key, conversationTime);
|
|
123
|
+
while (this.putFloors.size > this.maxEntries) {
|
|
124
|
+
const oldest = this.putFloors.keys().next().value;
|
|
125
|
+
if (oldest === undefined)
|
|
126
|
+
break;
|
|
127
|
+
this.putFloors.delete(oldest);
|
|
109
128
|
}
|
|
110
|
-
|
|
129
|
+
}
|
|
130
|
+
fencedByPut(key, conversationTime) {
|
|
131
|
+
const floor = this.putFloors.get(key);
|
|
132
|
+
return floor !== undefined && conversationTime < floor;
|
|
133
|
+
}
|
|
134
|
+
sweepRateLimited() {
|
|
111
135
|
const now = this.now();
|
|
112
136
|
for (const [key, backoff] of this.rateLimited) {
|
|
113
137
|
if (now >= backoff.until + RATE_LIMIT_STRIKE_MEMORY_MS)
|
|
@@ -120,12 +144,9 @@ export class PrConversationCache {
|
|
|
120
144
|
this.rateLimited.delete(oldest);
|
|
121
145
|
}
|
|
122
146
|
}
|
|
123
|
-
// 连续限流按指数增长(60 / 120 / 240…),成功即清零——客户端计时保护不了其他客户端。
|
|
124
147
|
noteRateLimited(key, revision, payload) {
|
|
125
148
|
const strikes = (this.rateLimited.get(key)?.strikes ?? 0) + 1;
|
|
126
149
|
const wait = Math.min(PR_CONVERSATION_RATE_LIMIT_TTL_MS * 2 ** (strikes - 1), RATE_LIMIT_MAX_WAIT_MS);
|
|
127
|
-
// 超过单项上限的 payload 只留退避状态:限流条目与普通条目共用一份字节预算,
|
|
128
|
-
// 否则这张表能在 stats() 之外常驻上百 MiB。
|
|
129
150
|
const bytes = Buffer.byteLength(JSON.stringify(payload), 'utf8');
|
|
130
151
|
const kept = bytes > this.maxPayloadBytes
|
|
131
152
|
? { items: [], error: payload.error, rateLimited: true }
|
|
@@ -146,7 +167,6 @@ export class PrConversationCache {
|
|
|
146
167
|
total += backoff.payloadBytes;
|
|
147
168
|
return total;
|
|
148
169
|
}
|
|
149
|
-
// 退避表与普通条目共享总字节上限;淘汰只丢 payload、保留退避状态(连击计数不能因内存压力清零)。
|
|
150
170
|
enforceRateLimitBudget() {
|
|
151
171
|
while (this.rateLimited.size > this.maxEntries
|
|
152
172
|
|| this.totalBytes + this.rateLimitedBytes() > this.maxTotalBytes) {
|
|
@@ -169,18 +189,18 @@ export class PrConversationCache {
|
|
|
169
189
|
}
|
|
170
190
|
}
|
|
171
191
|
store(key, revision, payload) {
|
|
172
|
-
const
|
|
192
|
+
const { fetchedAt: _stale, ...bare } = payload;
|
|
193
|
+
const payloadBytes = Buffer.byteLength(JSON.stringify(bare), 'utf8');
|
|
173
194
|
if (payloadBytes > this.maxPayloadBytes) {
|
|
174
195
|
this.remove(key);
|
|
175
196
|
return;
|
|
176
197
|
}
|
|
177
198
|
this.remove(key);
|
|
178
|
-
this.entries.set(key, { revision, fetchedAt: this.now(), payloadBytes, payload });
|
|
199
|
+
this.entries.set(key, { revision, fetchedAt: this.now(), payloadBytes, payload: bare });
|
|
179
200
|
this.totalBytes += payloadBytes;
|
|
180
201
|
this.evict();
|
|
181
202
|
}
|
|
182
203
|
evict() {
|
|
183
|
-
// store() 先 delete 再 set,Map 插入序即 fetchedAt 非降序,队首即最旧。
|
|
184
204
|
while (this.entries.size > this.maxEntries || this.totalBytes > this.maxTotalBytes) {
|
|
185
205
|
const oldestKey = this.entries.keys().next().value;
|
|
186
206
|
if (oldestKey === undefined)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pr-conversation-cache.js","sourceRoot":"","sources":["../../src/platform/pr-conversation-cache.ts"],"names":[],"mappings":"AAEA,MAAM,CAAC,MAAM,
|
|
1
|
+
{"version":3,"file":"pr-conversation-cache.js","sourceRoot":"","sources":["../../src/platform/pr-conversation-cache.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"preflight-exec.d.ts","sourceRoot":"","sources":["../../src/platform/preflight-exec.ts"],"names":[],"mappings":"AAAA,OAAO,EAAmC,KAAK,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAE5F,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,GAAG,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,CAAC,EAAE,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,yBAAyB;IACxC,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,OAAO,CAAC;IACZ,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,MAAM,iBAAiB,GAAG,CAC9B,OAAO,EAAE,MAAM,KACZ,OAAO,CAAC;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"preflight-exec.d.ts","sourceRoot":"","sources":["../../src/platform/preflight-exec.ts"],"names":[],"mappings":"AAAA,OAAO,EAAmC,KAAK,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAE5F,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,GAAG,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,CAAC,EAAE,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,yBAAyB;IACxC,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,OAAO,CAAC;IACZ,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,MAAM,iBAAiB,GAAG,CAC9B,OAAO,EAAE,MAAM,KACZ,OAAO,CAAC;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;AA8BnE,wBAAsB,uBAAuB,CAC3C,IAAI,EAAE,iBAAiB,EACvB,KAAK,EAAE,SAAS,mBAAmB,EAAE,EACrC,GAAG,EAAE,aAAa,GAAG;IAAE,cAAc,EAAE,MAAM,CAAA;CAAE,EAC/C,SAAS,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,KAAK,IAAI,GACpD,OAAO,CAAC,yBAAyB,EAAE,CAAC,CA4BtC"}
|
|
@@ -1,10 +1,6 @@
|
|
|
1
1
|
import { renderCommand, renderFixMessage } from './command-renderer.js';
|
|
2
|
-
// 边界完整(前后不得再接数字/点/字母)排除 `2.40.0.1`、`2.40.0rc1`、`1.2.40.0`;
|
|
3
|
-
// 多候选一律拒绝——banner 里的日期(`built 2026.07.20`)与真实版本无法靠位置区分。
|
|
4
2
|
const VERSION_RE = /(?<![\w.])v?(\d+)\.(\d+)\.(\d+)(-[0-9A-Za-z.-]+)?(?![\w.])/g;
|
|
5
3
|
function parseVersion(text) {
|
|
6
|
-
// gh 的常规输出同时含 `gh version X` 与 release 链接里的 `vX`:同值重复是正常形态,
|
|
7
|
-
// 只有**不同**候选才是无法判定的歧义(banner 日期 + 真实版本)。
|
|
8
4
|
const distinct = new Map();
|
|
9
5
|
for (const m of text.matchAll(VERSION_RE)) {
|
|
10
6
|
const parsed = {
|
|
@@ -15,7 +11,6 @@ function parseVersion(text) {
|
|
|
15
11
|
}
|
|
16
12
|
return distinct.size === 1 ? [...distinct.values()][0] : undefined;
|
|
17
13
|
}
|
|
18
|
-
// semver §9:同核预发布版本低于正式版本;manifest 底线恒为正式版(x.y.z 强制)。
|
|
19
14
|
function versionBelow(actual, min) {
|
|
20
15
|
for (let i = 0; i < 3; i++) {
|
|
21
16
|
const a = actual.core[i];
|
|
@@ -25,9 +20,6 @@ function versionBelow(actual, min) {
|
|
|
25
20
|
}
|
|
26
21
|
return actual.prerelease && !min.prerelease;
|
|
27
22
|
}
|
|
28
|
-
// 两执行面共用;首败即止——后续步骤共享同一前置,连锁失败只会误导修复方向。
|
|
29
|
-
// 失败命令的原始输出只经 onFailure 交给调用方分类,绝不进返回值:结果直达
|
|
30
|
-
// /projects/:id/checks 响应,stdout/stderr 可能含凭据且缓冲上限达数十 MiB。
|
|
31
23
|
export async function runDriverPreflightSteps(exec, steps, ctx, onFailure) {
|
|
32
24
|
const results = [];
|
|
33
25
|
const minVersion = parseVersion(ctx.minToolVersion);
|
|
@@ -45,7 +37,6 @@ export async function runDriverPreflightSteps(exec, steps, ctx, onFailure) {
|
|
|
45
37
|
failed = true;
|
|
46
38
|
output = err instanceof Error ? err.message : String(err);
|
|
47
39
|
}
|
|
48
|
-
// 退出码只证明可执行;版本步骤(加载期强制恰一个)须按 manifest 底线比较,不可解析即失败。
|
|
49
40
|
if (!failed && step.versionCheck === true && minVersion !== undefined) {
|
|
50
41
|
const actual = parseVersion(output);
|
|
51
42
|
failed = actual === undefined || versionBelow(actual, minVersion);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"preflight-exec.js","sourceRoot":"","sources":["../../src/platform/preflight-exec.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,gBAAgB,EAAsB,MAAM,uBAAuB,CAAC;AAmB5F,
|
|
1
|
+
{"version":3,"file":"preflight-exec.js","sourceRoot":"","sources":["../../src/platform/preflight-exec.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"response-parser.d.ts","sourceRoot":"","sources":["../../src/platform/response-parser.ts"],"names":[],"mappings":"AAAA,qBAAa,kBAAmB,SAAQ,KAAK;gBAC/B,OAAO,EAAE,MAAM;CAI5B;AAED,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAOzD;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"response-parser.d.ts","sourceRoot":"","sources":["../../src/platform/response-parser.ts"],"names":[],"mappings":"AAAA,qBAAa,kBAAmB,SAAQ,KAAK;gBAC/B,OAAO,EAAE,MAAM;CAI5B;AAED,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAOzD;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,EAAE,CAmE5D"}
|
|
@@ -15,12 +15,8 @@ export function parseJsonResponse(stdout) {
|
|
|
15
15
|
}
|
|
16
16
|
export function parseJsonPagedPage(stdout) {
|
|
17
17
|
const s = stdout.trim();
|
|
18
|
-
// 平台的合法空列表恒输出字面 [];exit 0 + 空 stdout 是工具/管道损坏而非空页,
|
|
19
|
-
// 当空页会让整源以 ok 进完整性门、漏掉其中的 fail/反馈后照常裁决。
|
|
20
18
|
if (s === '')
|
|
21
19
|
throw new ResponseParseError('json-paged page has empty stdout (expected a JSON array, e.g. [])');
|
|
22
|
-
// 最常见形态是单个合并数组:整体 parse 命中即免掉逐字符分帧扫描;
|
|
23
|
-
// 失败才回退扫描器(gh --paginate 式的多数组拼接),错误语义与扫描路径一致。
|
|
24
20
|
try {
|
|
25
21
|
const whole = JSON.parse(s);
|
|
26
22
|
if (Array.isArray(whole))
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"response-parser.js","sourceRoot":"","sources":["../../src/platform/response-parser.ts"],"names":[],"mappings":"AAAA,MAAM,OAAO,kBAAmB,SAAQ,KAAK;IAC3C,YAAY,OAAe;QACzB,KAAK,CAAC,OAAO,CAAC,CAAC;QACf,IAAI,CAAC,IAAI,GAAG,oBAAoB,CAAC;IACnC,CAAC;CACF;AAED,MAAM,UAAU,iBAAiB,CAAC,MAAc;IAC9C,MAAM,CAAC,GAAG,MAAM,CAAC,IAAI,EAAE,CAAC;IACxB,IAAI,CAAC;QACH,OAAO,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;IACvB,CAAC;IAAC,OAAO,CAAC,EAAE,CAAC;QACX,MAAM,IAAI,kBAAkB,CAAC,0BAA0B,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACvG,CAAC;AACH,CAAC;AAED,MAAM,UAAU,kBAAkB,CAAC,MAAc;IAC/C,MAAM,CAAC,GAAG,MAAM,CAAC,IAAI,EAAE,CAAC;IACxB,
|
|
1
|
+
{"version":3,"file":"response-parser.js","sourceRoot":"","sources":["../../src/platform/response-parser.ts"],"names":[],"mappings":"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"}
|
|
@@ -7,10 +7,25 @@ export interface TimelineSourceReader {
|
|
|
7
7
|
prNumber: number;
|
|
8
8
|
}, projectPage?: (pageRows: NormalizedRow[]) => NormalizedRow[], shouldStop?: (pageRows: NormalizedRow[], page: number) => boolean): Promise<NormalizedRow[]>;
|
|
9
9
|
}
|
|
10
|
-
export
|
|
10
|
+
export interface TimelinePayload {
|
|
11
11
|
items: PrReviewItem[];
|
|
12
12
|
error?: string;
|
|
13
13
|
rateLimited?: boolean;
|
|
14
14
|
truncated?: boolean;
|
|
15
|
-
}
|
|
15
|
+
}
|
|
16
|
+
export declare class TimelineCollector {
|
|
17
|
+
private readonly buckets;
|
|
18
|
+
private readonly itemQuota;
|
|
19
|
+
private readonly byteQuota;
|
|
20
|
+
private readonly errors;
|
|
21
|
+
private rateLimitedFlag;
|
|
22
|
+
constructor(sources: readonly CommentSourceOp[]);
|
|
23
|
+
admitPage(source: CommentSourceOp, pageRows: readonly NormalizedRow[]): void;
|
|
24
|
+
overQuota(source: CommentSourceOp): boolean;
|
|
25
|
+
noteFailure(sourceKey: string, error: unknown): void;
|
|
26
|
+
get rateLimited(): boolean;
|
|
27
|
+
assemble(): TimelinePayload;
|
|
28
|
+
private bucket;
|
|
29
|
+
}
|
|
30
|
+
export declare function buildDriverReviewTimeline(driver: TimelineSourceReader, prNumber: number): Promise<TimelinePayload>;
|
|
16
31
|
//# sourceMappingURL=review-timeline.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"review-timeline.d.ts","sourceRoot":"","sources":["../../src/platform/review-timeline.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD,OAAO,EAAiB,KAAK,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAGpE,OAAO,KAAK,EAAE,YAAY,EAAoB,MAAM,oBAAoB,CAAC;AAEzE,MAAM,WAAW,oBAAoB;IACnC,QAAQ,CAAC,cAAc,EAAE,eAAe,EAAE,CAAC;IAC3C,gBAAgB,CACd,MAAM,EAAE,eAAe,EACvB,IAAI,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAA;KAAE,EAC1B,WAAW,CAAC,EAAE,CAAC,QAAQ,EAAE,aAAa,EAAE,KAAK,aAAa,EAAE,EAC5D,UAAU,CAAC,EAAE,CAAC,QAAQ,EAAE,aAAa,EAAE,EAAE,IAAI,EAAE,MAAM,KAAK,OAAO,GAChE,OAAO,CAAC,aAAa,EAAE,CAAC,CAAC;CAC7B;
|
|
1
|
+
{"version":3,"file":"review-timeline.d.ts","sourceRoot":"","sources":["../../src/platform/review-timeline.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD,OAAO,EAAiB,KAAK,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAGpE,OAAO,KAAK,EAAE,YAAY,EAAoB,MAAM,oBAAoB,CAAC;AAEzE,MAAM,WAAW,oBAAoB;IACnC,QAAQ,CAAC,cAAc,EAAE,eAAe,EAAE,CAAC;IAC3C,gBAAgB,CACd,MAAM,EAAE,eAAe,EACvB,IAAI,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAA;KAAE,EAC1B,WAAW,CAAC,EAAE,CAAC,QAAQ,EAAE,aAAa,EAAE,KAAK,aAAa,EAAE,EAC5D,UAAU,CAAC,EAAE,CAAC,QAAQ,EAAE,aAAa,EAAE,EAAE,IAAI,EAAE,MAAM,KAAK,OAAO,GAChE,OAAO,CAAC,aAAa,EAAE,CAAC,CAAC;CAC7B;AAkBD,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,YAAY,EAAE,CAAC;IACtB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB;AAUD,qBAAa,iBAAiB;IAC5B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAmC;IAC3D,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;IACnC,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;IACnC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAgB;IACvC,OAAO,CAAC,eAAe,CAAS;gBAEpB,OAAO,EAAE,SAAS,eAAe,EAAE;IAM/C,SAAS,CAAC,MAAM,EAAE,eAAe,EAAE,QAAQ,EAAE,SAAS,aAAa,EAAE,GAAG,IAAI;IAmB5E,SAAS,CAAC,MAAM,EAAE,eAAe,GAAG,OAAO;IAU3C,WAAW,CAAC,SAAS,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,GAAG,IAAI;IAQpD,IAAI,WAAW,IAAI,OAAO,CAEzB;IAED,QAAQ,IAAI,eAAe;IAgB3B,OAAO,CAAC,MAAM;CAcf;AAED,wBAAsB,yBAAyB,CAC7C,MAAM,EAAE,oBAAoB,EAC5B,QAAQ,EAAE,MAAM,GACf,OAAO,CAAC,eAAe,CAAC,CAuB1B"}
|
|
@@ -2,11 +2,7 @@ import { DriverOpError, safeDriverErrorText } from './git-driver.js';
|
|
|
2
2
|
import { versionTimeOf } from './row-schema.js';
|
|
3
3
|
import { classifyCommentSource, rowBodyDigest, rowTokens, stripBaxianMarkerLines } from './markers.js';
|
|
4
4
|
import { MAX_INLINE_CONTENT_BYTES } from '../shared/index.js';
|
|
5
|
-
// 聚合上界:单条 10 KiB 只限一行,三源 × 100 页 × 100 条可达数百 MiB。预算按源均分并在
|
|
6
|
-
// 分页循环内生效(driver 的 all/seen 因此同受硬界),避免靠前的源吃光额度让 reviews 源
|
|
7
|
-
// 的裁决行整体消失;计量按投影后 item 的完整序列化长度,不只是正文。
|
|
8
5
|
const TIMELINE_MAX_ITEMS = 2_000;
|
|
9
|
-
// 为 items 数组的逗号/方括号与外层 payload 包装预留 framing 余量,硬边界按完整序列化成立。
|
|
10
6
|
const TIMELINE_PAYLOAD_MAX_BYTES = 2 * 1024 * 1024;
|
|
11
7
|
const TIMELINE_FRAMING_RESERVE = 8 * 1024;
|
|
12
8
|
const TIMELINE_MAX_BYTES = TIMELINE_PAYLOAD_MAX_BYTES - TIMELINE_FRAMING_RESERVE;
|
|
@@ -15,125 +11,119 @@ const KIND_BY_CLASS = {
|
|
|
15
11
|
threaded: 'review-comment',
|
|
16
12
|
'top-level': 'issue-comment',
|
|
17
13
|
};
|
|
18
|
-
export
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
return true;
|
|
45
|
-
}
|
|
46
|
-
return false;
|
|
47
|
-
};
|
|
48
|
-
const seenRows = new Map();
|
|
49
|
-
const admit = (pageRows) => {
|
|
50
|
-
for (const row of pageRows) {
|
|
51
|
-
compactRowForTimeline(row);
|
|
52
|
-
if (row.system === true)
|
|
53
|
-
continue;
|
|
54
|
-
// 页内投影先于 runPaged 的跨页去重,重叠页会把同一行送来两次——身份键在此自查重。
|
|
55
|
-
const id = String(row.id);
|
|
56
|
-
const digest = String(row.bodyDigest ?? '');
|
|
57
|
-
if (seenRows.get(id) === digest)
|
|
58
|
-
continue;
|
|
59
|
-
seenRows.set(id, digest);
|
|
60
|
-
const entry = projectRow(source.key, kind, row);
|
|
61
|
-
const size = Buffer.byteLength(JSON.stringify(entry.item), 'utf8') + 1;
|
|
62
|
-
// 判定先于计入:单条本身超额时也必须丢弃,否则一条超大投影就能撑爆响应。
|
|
63
|
-
if (collected.length >= itemQuota || sourceBytes + size > byteQuota) {
|
|
64
|
-
markTruncated();
|
|
65
|
-
break;
|
|
66
|
-
}
|
|
67
|
-
sourceBytes += size;
|
|
68
|
-
collected.push(entry);
|
|
14
|
+
export class TimelineCollector {
|
|
15
|
+
buckets = new Map();
|
|
16
|
+
itemQuota;
|
|
17
|
+
byteQuota;
|
|
18
|
+
errors = [];
|
|
19
|
+
rateLimitedFlag = false;
|
|
20
|
+
constructor(sources) {
|
|
21
|
+
const sourceCount = Math.max(sources.length, 1);
|
|
22
|
+
this.itemQuota = Math.max(1, Math.floor(TIMELINE_MAX_ITEMS / sourceCount));
|
|
23
|
+
this.byteQuota = Math.max(1, Math.floor(TIMELINE_MAX_BYTES / sourceCount));
|
|
24
|
+
}
|
|
25
|
+
admitPage(source, pageRows) {
|
|
26
|
+
const bucket = this.bucket(source);
|
|
27
|
+
for (const row of pageRows) {
|
|
28
|
+
if (row.system === true)
|
|
29
|
+
continue;
|
|
30
|
+
const id = String(row.id);
|
|
31
|
+
const digest = rowBodyDigest(row);
|
|
32
|
+
if (bucket.seenRows.get(id) === digest)
|
|
33
|
+
continue;
|
|
34
|
+
bucket.seenRows.set(id, digest);
|
|
35
|
+
const entry = projectRow(source.key, bucket.kind, row);
|
|
36
|
+
const size = Buffer.byteLength(JSON.stringify(entry.item), 'utf8') + 1;
|
|
37
|
+
if (bucket.collected.length >= this.itemQuota || bucket.bytes + size > this.byteQuota) {
|
|
38
|
+
bucket.truncated = true;
|
|
39
|
+
break;
|
|
69
40
|
}
|
|
41
|
+
bucket.bytes += size;
|
|
42
|
+
bucket.collected.push(entry);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
overQuota(source) {
|
|
46
|
+
const bucket = this.bucket(source);
|
|
47
|
+
if (bucket.truncated)
|
|
48
|
+
return true;
|
|
49
|
+
if (bucket.collected.length >= this.itemQuota || bucket.bytes >= this.byteQuota) {
|
|
50
|
+
bucket.truncated = true;
|
|
51
|
+
return true;
|
|
52
|
+
}
|
|
53
|
+
return false;
|
|
54
|
+
}
|
|
55
|
+
noteFailure(sourceKey, error) {
|
|
56
|
+
this.errors.push(`${sourceKey}: ${safeDriverErrorText(error)}`);
|
|
57
|
+
this.buckets.delete(sourceKey);
|
|
58
|
+
if (error instanceof DriverOpError && error.info.errorClass === 'RATE_LIMIT') {
|
|
59
|
+
this.rateLimitedFlag = true;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
get rateLimited() {
|
|
63
|
+
return this.rateLimitedFlag;
|
|
64
|
+
}
|
|
65
|
+
assemble() {
|
|
66
|
+
const entries = [];
|
|
67
|
+
let truncated = false;
|
|
68
|
+
for (const bucket of this.buckets.values()) {
|
|
69
|
+
entries.push(...bucket.collected);
|
|
70
|
+
if (bucket.truncated)
|
|
71
|
+
truncated = true;
|
|
72
|
+
}
|
|
73
|
+
sortTimeline(entries);
|
|
74
|
+
return {
|
|
75
|
+
items: entries.map(e => e.item),
|
|
76
|
+
...(this.errors.length > 0 ? { error: this.errors.join('; ') } : {}),
|
|
77
|
+
...(this.rateLimitedFlag ? { rateLimited: true } : {}),
|
|
78
|
+
...(truncated ? { truncated: true } : {}),
|
|
70
79
|
};
|
|
80
|
+
}
|
|
81
|
+
bucket(source) {
|
|
82
|
+
let bucket = this.buckets.get(source.key);
|
|
83
|
+
if (!bucket) {
|
|
84
|
+
bucket = {
|
|
85
|
+
kind: KIND_BY_CLASS[classifyCommentSource(source)],
|
|
86
|
+
collected: [],
|
|
87
|
+
bytes: 0,
|
|
88
|
+
truncated: false,
|
|
89
|
+
seenRows: new Map(),
|
|
90
|
+
};
|
|
91
|
+
this.buckets.set(source.key, bucket);
|
|
92
|
+
}
|
|
93
|
+
return bucket;
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
export async function buildDriverReviewTimeline(driver, prNumber) {
|
|
97
|
+
const collector = new TimelineCollector(driver.commentSources);
|
|
98
|
+
for (const source of driver.commentSources) {
|
|
71
99
|
let pagedInline = false;
|
|
72
|
-
let rows;
|
|
73
100
|
try {
|
|
74
|
-
rows = await driver.runCommentSource(source, { prNumber }, pageRows => {
|
|
101
|
+
const rows = await driver.runCommentSource(source, { prNumber }, pageRows => {
|
|
75
102
|
pagedInline = true;
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
return pageRows.map(r => ({ id: r.id, bodyDigest: r.bodyDigest }));
|
|
80
|
-
}, () => overQuota());
|
|
81
|
-
// reader 未消费页内钩子时(projectPage 是可选契约)仍按同一预算收集,绝不静默空时间线。
|
|
103
|
+
collector.admitPage(source, pageRows);
|
|
104
|
+
return pageRows.map(r => ({ id: r.id, bodyDigest: rowBodyDigest(r) }));
|
|
105
|
+
}, () => collector.overQuota(source));
|
|
82
106
|
if (!pagedInline)
|
|
83
|
-
|
|
84
|
-
entries.push(...collected);
|
|
107
|
+
collector.admitPage(source, rows);
|
|
85
108
|
}
|
|
86
109
|
catch (err) {
|
|
87
110
|
console.warn(`[review-timeline] source ${source.key} failed:`, safeDriverErrorText(err));
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
// 绕过平台退避(GitHub 明示持续撞限流可致集成被禁用)。
|
|
91
|
-
if (err instanceof DriverOpError && err.info.errorClass === 'RATE_LIMIT') {
|
|
92
|
-
rateLimited = true;
|
|
111
|
+
collector.noteFailure(source.key, err);
|
|
112
|
+
if (collector.rateLimited)
|
|
93
113
|
break;
|
|
94
|
-
}
|
|
95
|
-
continue;
|
|
96
114
|
}
|
|
97
115
|
}
|
|
98
|
-
|
|
99
|
-
return {
|
|
100
|
-
items: entries.map(e => e.item),
|
|
101
|
-
...(errors.length > 0 ? { error: errors.join('; ') } : {}),
|
|
102
|
-
...(rateLimited ? { rateLimited: true } : {}),
|
|
103
|
-
...(truncated ? { truncated: true } : {}),
|
|
104
|
-
};
|
|
105
|
-
}
|
|
106
|
-
function compactRowForTimeline(row) {
|
|
107
|
-
const token = rowTokens(row)[0];
|
|
108
|
-
// 摘要必须在删正文前落到行上:瘦身分页行以它作指纹,缺失会让 runPaged 把「同 id 不同正文」
|
|
109
|
-
// 误判成完全相同的重复行(该形态的契约是拒绝本轮扫描、下轮重试)。
|
|
110
|
-
if (row.bodyDigest === undefined)
|
|
111
|
-
row.bodyDigest = rowBodyDigest(row);
|
|
112
|
-
const body = sizedBody(stripBaxianMarkerLines(typeof row.body === 'string' ? row.body : ''));
|
|
113
|
-
row.timelineToken = token;
|
|
114
|
-
row.timelineBody = body;
|
|
115
|
-
delete row.body;
|
|
116
|
-
}
|
|
117
|
-
function timelineStash(row) {
|
|
118
|
-
const stashed = row;
|
|
119
|
-
if (stashed.timelineBody !== undefined) {
|
|
120
|
-
return { timelineToken: stashed.timelineToken, timelineBody: stashed.timelineBody };
|
|
121
|
-
}
|
|
122
|
-
return {
|
|
123
|
-
timelineToken: rowTokens(row)[0],
|
|
124
|
-
timelineBody: sizedBody(stripBaxianMarkerLines(typeof row.body === 'string' ? row.body : '')),
|
|
125
|
-
};
|
|
116
|
+
return collector.assemble();
|
|
126
117
|
}
|
|
127
118
|
function projectRow(sourceKey, kind, row) {
|
|
128
119
|
const id = String(row.id);
|
|
129
|
-
const
|
|
120
|
+
const token = rowTokens(row)[0];
|
|
121
|
+
const timelineBody = sizedBody(stripBaxianMarkerLines(typeof row.body === 'string' ? row.body : ''));
|
|
130
122
|
const line = typeof row.line === 'number' ? row.line
|
|
131
123
|
: typeof row.originalLine === 'number' ? row.originalLine : undefined;
|
|
132
124
|
const createdAt = typeof row.createdAt === 'string' ? row.createdAt
|
|
133
125
|
: typeof row.updatedAt === 'string' ? row.updatedAt : undefined;
|
|
134
126
|
const threaded = kind === 'review-comment' && row.discussionId !== null && row.discussionId !== undefined;
|
|
135
|
-
// 回复身份只信显式 parentId 映射(时间/顺序推断在秒精度与仅 updatedAt 的合法源上都不成立);
|
|
136
|
-
// 未映射的源不标注,仅少一个回复徽标。
|
|
137
127
|
const isReply = row.parentId !== null && row.parentId !== undefined && String(row.parentId) !== String(row.id);
|
|
138
128
|
return {
|
|
139
129
|
item: {
|
|
@@ -171,10 +161,7 @@ function sizedBody(raw) {
|
|
|
171
161
|
cut--;
|
|
172
162
|
return { body: buf.subarray(0, cut).toString('utf8'), bodyTruncated: true };
|
|
173
163
|
}
|
|
174
|
-
// 数值 versionTime(updatedAt ?? createdAt)排序:编辑过的行(含后补 verdict token)按修订
|
|
175
|
-
// 时刻落位,RFC3339 任意 offset 也正确比较;同刻 review 排后,分轮不把随行评论溢进下一轮。
|
|
176
164
|
function sortTimeline(entries) {
|
|
177
|
-
// 同刻权重覆盖一切裁决载体(含降级评论):裁决闭轮,排前会把同轮评论挤进下一轮。
|
|
178
165
|
const rank = (e) => (e.item.kind === 'review' || e.item.verdict !== undefined ? 1 : 0);
|
|
179
166
|
entries.sort((a, b) => {
|
|
180
167
|
if (a.sortTime !== undefined && b.sortTime !== undefined) {
|