peertable 0.8.37 → 0.8.39
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/package.json +1 -1
- package/room/client.mjs +1 -1
- package/skill/scripts/wakeup-bridge.mjs +21 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "peertable",
|
|
3
|
-
"version": "0.8.
|
|
3
|
+
"version": "0.8.39",
|
|
4
4
|
"description": "A round table of peer agents. No orchestrator at the head. Turn Claude Code, Codex, and Grok sessions into a team of equal, long-lived peers.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
package/room/client.mjs
CHANGED
|
@@ -14,7 +14,7 @@ import { boundedRecent, boundedUnread } from './message-bounds.mjs'
|
|
|
14
14
|
|
|
15
15
|
// client.mjs 側のハードコード版数。package.json の version と一致していることを
|
|
16
16
|
// diagnostics の version_consistency が見る(2 つの版数源の drift 検出。決定45)
|
|
17
|
-
const MCP_VERSION = '0.8.
|
|
17
|
+
const MCP_VERSION = '0.8.39'
|
|
18
18
|
const PKG_ROOT = join(dirname(fileURLToPath(import.meta.url)), '..')
|
|
19
19
|
|
|
20
20
|
const USAGE = `usage:
|
|
@@ -174,15 +174,23 @@ const postedReceipts = new Map() // `${seq}:${recipient}` -> `${result}:${reason
|
|
|
174
174
|
// failed / seat_unavailable の初回だけ、親宛DMを1通送る——親宛DMは parent-watch が起こすので
|
|
175
175
|
// 既存の通知経路にそのまま乗り、この bridge 自身は親へ配達しないため再帰しない。
|
|
176
176
|
const notifiedFailures = new Set() // `${seq}:${recipient}`(delivered への回復で解除し、再failで再通知)
|
|
177
|
+
const failureStreaks = new Map() // `${seq}:${recipient}` -> 連続失敗数
|
|
177
178
|
async function notifyParentOfFailure(seq, recipient, result, reason) {
|
|
178
179
|
if (!parentName) return
|
|
179
180
|
const key = `${seq}:${recipient}`
|
|
180
181
|
if (result === 'delivered') {
|
|
181
182
|
notifiedFailures.delete(key)
|
|
183
|
+
failureStreaks.delete(key)
|
|
182
184
|
return
|
|
183
185
|
}
|
|
184
186
|
// not_a_delivery_target は「そもそもTUI配達対象でない」平常応答であって失敗ではない
|
|
185
187
|
if (reason === 'not_a_delivery_target') return
|
|
188
|
+
// 1回目の失敗は通知しない。数秒後の再試行で自己回復する一過性(paste競合等)が
|
|
189
|
+
// 毎回親を起こしてノイズになった(実被弾 2026-08-30)。実害のある失敗は次周期で
|
|
190
|
+
// 2回目に達するので、検知は数秒遅れるだけで漏れない。
|
|
191
|
+
const streak = (failureStreaks.get(key) ?? 0) + 1
|
|
192
|
+
failureStreaks.set(key, streak)
|
|
193
|
+
if (streak < 2) return
|
|
186
194
|
if (notifiedFailures.has(key)) return
|
|
187
195
|
try {
|
|
188
196
|
const res = await fetch(`${url}/api/${encodeURIComponent(room)}/messages`, {
|
|
@@ -486,7 +494,19 @@ async function wake(seat, msgs) {
|
|
|
486
494
|
} else {
|
|
487
495
|
await run('tmux', tmuxArgv(['send-keys', '-t', observation.target, 'C-u'], { socket: observation.socket }))
|
|
488
496
|
await sleep(100)
|
|
489
|
-
|
|
497
|
+
// 素打ち(send-keys -l)は長文で連続keystrokeとして届き、TUIのpaste burst検知を
|
|
498
|
+
// 半端な状態に落として composer が submit 不能に固まる形を繰り返した(実被弾
|
|
499
|
+
// 2026-08-29: Codex席が同日3回、掃除も効かない入力破損)。正規の bracketed paste
|
|
500
|
+
// (load-buffer→paste-buffer -p)で「1回の貼り付け」として届ける。
|
|
501
|
+
const pasteBuf = `wakeup-${process.pid}-${Date.now()}`
|
|
502
|
+
const pasteFile = join(proj, '.team', `wakeup-paste-${process.pid}.txt`)
|
|
503
|
+
writeFileSync(pasteFile, text)
|
|
504
|
+
try {
|
|
505
|
+
await run('tmux', tmuxArgv(['load-buffer', '-b', pasteBuf, pasteFile], { socket: observation.socket }))
|
|
506
|
+
await run('tmux', tmuxArgv(['paste-buffer', '-p', '-d', '-b', pasteBuf, '-t', observation.target], { socket: observation.socket }))
|
|
507
|
+
} finally {
|
|
508
|
+
try { unlinkSync(pasteFile) } catch { /* 一時fileの掃除失敗は配達判定に影響しない */ }
|
|
509
|
+
}
|
|
490
510
|
await sleep(750)
|
|
491
511
|
await run('tmux', tmuxArgv(['send-keys', '-t', observation.target, 'Enter'], { socket: observation.socket }))
|
|
492
512
|
}
|