instar 1.3.524 → 1.3.526
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/dist/commands/server.d.ts.map +1 -1
- package/dist/commands/server.js +77 -5
- package/dist/commands/server.js.map +1 -1
- package/dist/config/ConfigDefaults.d.ts.map +1 -1
- package/dist/config/ConfigDefaults.js +23 -0
- package/dist/config/ConfigDefaults.js.map +1 -1
- package/dist/core/ConflictStore.d.ts +150 -0
- package/dist/core/ConflictStore.d.ts.map +1 -0
- package/dist/core/ConflictStore.js +247 -0
- package/dist/core/ConflictStore.js.map +1 -0
- package/dist/core/PostUpdateMigrator.d.ts +1 -0
- package/dist/core/PostUpdateMigrator.d.ts.map +1 -1
- package/dist/core/PostUpdateMigrator.js +116 -0
- package/dist/core/PostUpdateMigrator.js.map +1 -1
- package/dist/core/ReplicatedStoreReader.d.ts +83 -0
- package/dist/core/ReplicatedStoreReader.d.ts.map +1 -0
- package/dist/core/ReplicatedStoreReader.js +100 -0
- package/dist/core/ReplicatedStoreReader.js.map +1 -0
- package/dist/core/ReplicationBudget.d.ts +183 -0
- package/dist/core/ReplicationBudget.d.ts.map +1 -0
- package/dist/core/ReplicationBudget.js +253 -0
- package/dist/core/ReplicationBudget.js.map +1 -0
- package/dist/core/RollbackUnmerge.d.ts +134 -0
- package/dist/core/RollbackUnmerge.d.ts.map +1 -0
- package/dist/core/RollbackUnmerge.js +286 -0
- package/dist/core/RollbackUnmerge.js.map +1 -0
- package/dist/core/UnionReader.d.ts +161 -0
- package/dist/core/UnionReader.d.ts.map +1 -0
- package/dist/core/UnionReader.js +0 -0
- package/dist/core/UnionReader.js.map +1 -0
- package/dist/monitoring/ActiveWorkSilenceSentinel.d.ts +56 -2
- package/dist/monitoring/ActiveWorkSilenceSentinel.d.ts.map +1 -1
- package/dist/monitoring/ActiveWorkSilenceSentinel.js +174 -10
- package/dist/monitoring/ActiveWorkSilenceSentinel.js.map +1 -1
- package/dist/monitoring/PromiseBeacon.d.ts +48 -0
- package/dist/monitoring/PromiseBeacon.d.ts.map +1 -1
- package/dist/monitoring/PromiseBeacon.js +186 -41
- package/dist/monitoring/PromiseBeacon.js.map +1 -1
- package/dist/monitoring/SubagentTracker.d.ts +9 -0
- package/dist/monitoring/SubagentTracker.d.ts.map +1 -1
- package/dist/monitoring/SubagentTracker.js +11 -0
- package/dist/monitoring/SubagentTracker.js.map +1 -1
- package/dist/monitoring/sentinelWiring.d.ts +20 -1
- package/dist/monitoring/sentinelWiring.d.ts.map +1 -1
- package/dist/monitoring/sentinelWiring.js +26 -0
- package/dist/monitoring/sentinelWiring.js.map +1 -1
- package/dist/scaffold/templates.d.ts.map +1 -1
- package/dist/scaffold/templates.js +13 -0
- package/dist/scaffold/templates.js.map +1 -1
- package/dist/server/AgentServer.d.ts +7 -0
- package/dist/server/AgentServer.d.ts.map +1 -1
- package/dist/server/AgentServer.js +3 -0
- package/dist/server/AgentServer.js.map +1 -1
- package/dist/server/routes.d.ts +10 -0
- package/dist/server/routes.d.ts.map +1 -1
- package/dist/server/routes.js +67 -0
- package/dist/server/routes.js.map +1 -1
- package/package.json +1 -1
- package/src/data/builtin-manifest.json +64 -64
- package/src/scaffold/templates.ts +13 -0
- package/upgrades/1.3.525.md +32 -0
- package/upgrades/1.3.526.md +83 -0
- package/upgrades/side-effects/hlc-step4-5-union-rollback-bounds.md +148 -0
- package/upgrades/side-effects/honest-progress-messaging.md +150 -0
|
@@ -261,6 +261,7 @@ export class PostUpdateMigrator {
|
|
|
261
261
|
this.migrateCommitmentOwnerBackfill(result);
|
|
262
262
|
this.migrateMultiMachinePostureReviewDimension(result);
|
|
263
263
|
this.migrateConformanceGateAutoInvoke(result);
|
|
264
|
+
this.migrateHonestProgressMessagingDefaults(result);
|
|
264
265
|
return result;
|
|
265
266
|
}
|
|
266
267
|
// ── Standards-Conformance Gate auto-invocation (2026-06-12, topic 13481) ──
|
|
@@ -530,6 +531,81 @@ export class PostUpdateMigrator {
|
|
|
530
531
|
result.skipped.push('cartographer-dev-gate: no default-shaped false to strip (marker set)');
|
|
531
532
|
}
|
|
532
533
|
}
|
|
534
|
+
// ── HONEST-PROGRESS-MESSAGING D (Config surface + migration parity) ──
|
|
535
|
+
//
|
|
536
|
+
// The honest-messaging behavior reaches every agent via the monitors' code
|
|
537
|
+
// defaults already; this migration SURFACES the operator-tunable / rollback
|
|
538
|
+
// keys into a deployed agent's config.json so they are visible and settable,
|
|
539
|
+
// and logs which keys it backfilled (audit). Existence-checked + idempotent: a
|
|
540
|
+
// key the operator has explicitly set — including the rollback
|
|
541
|
+
// `suppressUnchangedHeartbeats: false` — is NEVER overwritten. Writes to the
|
|
542
|
+
// paths the runtime ACTUALLY reads: `monitoring.activeWorkSilenceSentinel.*`
|
|
543
|
+
// and TOP-LEVEL `promiseBeacon.*` (server.ts reads `config.promiseBeacon`, not
|
|
544
|
+
// `monitoring.promiseBeacon` — the spec prose's path was corrected against the
|
|
545
|
+
// real read site during the build).
|
|
546
|
+
migrateHonestProgressMessagingDefaults(result) {
|
|
547
|
+
const configPath = path.join(this.config.stateDir, 'config.json');
|
|
548
|
+
if (!fs.existsSync(configPath)) {
|
|
549
|
+
result.skipped.push('honest-progress-messaging-defaults: config.json not found');
|
|
550
|
+
return;
|
|
551
|
+
}
|
|
552
|
+
let config;
|
|
553
|
+
try {
|
|
554
|
+
config = JSON.parse(fs.readFileSync(configPath, 'utf-8'));
|
|
555
|
+
}
|
|
556
|
+
catch (err) {
|
|
557
|
+
result.errors.push(`honest-progress-messaging-defaults: config.json read failed: ${err instanceof Error ? err.message : String(err)}`);
|
|
558
|
+
return;
|
|
559
|
+
}
|
|
560
|
+
const migrations = (config._instar_migrations ?? []);
|
|
561
|
+
const marker = 'honest-progress-messaging-defaults';
|
|
562
|
+
if (migrations.some(m => m.startsWith(marker))) {
|
|
563
|
+
result.skipped.push('honest-progress-messaging-defaults: already migrated');
|
|
564
|
+
return;
|
|
565
|
+
}
|
|
566
|
+
// Ensure a nested object exists without clobbering operator settings.
|
|
567
|
+
const ensureObj = (parent, key) => {
|
|
568
|
+
const cur = parent[key];
|
|
569
|
+
if (cur && typeof cur === 'object' && !Array.isArray(cur))
|
|
570
|
+
return cur;
|
|
571
|
+
const fresh = {};
|
|
572
|
+
parent[key] = fresh;
|
|
573
|
+
return fresh;
|
|
574
|
+
};
|
|
575
|
+
// Set a key ONLY if absent (existence-checked) — operator overrides survive.
|
|
576
|
+
const backfilled = [];
|
|
577
|
+
const setIfAbsent = (obj, key, value, label) => {
|
|
578
|
+
if (!(key in obj)) {
|
|
579
|
+
obj[key] = value;
|
|
580
|
+
backfilled.push(label);
|
|
581
|
+
}
|
|
582
|
+
};
|
|
583
|
+
const monitoring = ensureObj(config, 'monitoring');
|
|
584
|
+
const silence = ensureObj(monitoring, 'activeWorkSilenceSentinel');
|
|
585
|
+
setIfAbsent(silence, 'silenceThresholdMs', 1_800_000, 'monitoring.activeWorkSilenceSentinel.silenceThresholdMs');
|
|
586
|
+
setIfAbsent(silence, 'activeWorkMaxFrozenIndicatorMs', 5_400_000, 'monitoring.activeWorkSilenceSentinel.activeWorkMaxFrozenIndicatorMs');
|
|
587
|
+
const beacon = ensureObj(config, 'promiseBeacon');
|
|
588
|
+
setIfAbsent(beacon, 'suppressUnchangedHeartbeats', true, 'promiseBeacon.suppressUnchangedHeartbeats');
|
|
589
|
+
setIfAbsent(beacon, 'beaconLivenessIntervalMs', 3_600_000, 'promiseBeacon.beaconLivenessIntervalMs');
|
|
590
|
+
setIfAbsent(beacon, 'turnFinishedCloseoutChecks', 3, 'promiseBeacon.turnFinishedCloseoutChecks');
|
|
591
|
+
// Record the marker even when nothing was backfilled, so it runs exactly once.
|
|
592
|
+
const now = new Date().toISOString();
|
|
593
|
+
migrations.push(`${marker}-${now}`);
|
|
594
|
+
config._instar_migrations = migrations;
|
|
595
|
+
try {
|
|
596
|
+
fs.writeFileSync(configPath, JSON.stringify(config, null, 2));
|
|
597
|
+
}
|
|
598
|
+
catch (err) {
|
|
599
|
+
result.errors.push(`honest-progress-messaging-defaults: config.json write failed: ${err instanceof Error ? err.message : String(err)}`);
|
|
600
|
+
return;
|
|
601
|
+
}
|
|
602
|
+
if (backfilled.length > 0) {
|
|
603
|
+
result.upgraded.push(`honest-progress-messaging-defaults: backfilled ${backfilled.join(', ')} (existence-checked — operator overrides preserved)`);
|
|
604
|
+
}
|
|
605
|
+
else {
|
|
606
|
+
result.skipped.push('honest-progress-messaging-defaults: all keys already present (marker set)');
|
|
607
|
+
}
|
|
608
|
+
}
|
|
533
609
|
/**
|
|
534
610
|
* Seed the interactive first-launch onboarding flags into every EXISTING
|
|
535
611
|
* claude-code subscription-pool config home (2026-06-09 incident, topic
|
|
@@ -4244,6 +4320,26 @@ A secret you give me on one machine — a Telegram token, an API key, a GitHub P
|
|
|
4244
4320
|
patched = true;
|
|
4245
4321
|
result.upgraded.push('CLAUDE.md: added secret-sync push-opt-in safety line');
|
|
4246
4322
|
}
|
|
4323
|
+
// One Memory (replicated stores) — multi-machine-replicated-store-foundation
|
|
4324
|
+
// §7. Deployed agents don't know certain stores now replicate with a no-clobber
|
|
4325
|
+
// union + operator-resolved conflicts + origin-tagged rollback, nor the three
|
|
4326
|
+
// /state/* routes. Append the section so an agent can answer "why do I have two
|
|
4327
|
+
// versions of preference X?" / "roll back machine Y's data". Idempotent via the
|
|
4328
|
+
// unique `/state/resolve-conflict` marker.
|
|
4329
|
+
if (!content.includes('/state/resolve-conflict') && !content.includes('One Memory (replicated stores)')) {
|
|
4330
|
+
const oneMemory = `
|
|
4331
|
+
### One Memory (replicated stores)
|
|
4332
|
+
|
|
4333
|
+
When enabled, certain stores (preferences, relationships) replicate across my machines so I have ONE memory, not one-per-machine. A read returns the UNION of every machine's copy, merged by a no-clobber rule: a normal sequential edit history resolves to the latest writer; but two machines that edited the SAME thing DURING A PARTITION (a genuine concurrent divergence) are NEVER silently overwritten. For a high-impact store (preferences, relationships) BOTH versions are preserved and the conflict is flagged for you to resolve; for a low-impact store the latest wins but the overwrite is flagged, never silent. A replicated record never clobbers a divergent local one — reach is not authority. Ships DARK behind \`multiMachine.stateSync.<store>\` (default false); a single-machine agent is a strict no-op.
|
|
4334
|
+
- See open conflicts: \`curl -H "Authorization: Bearer $AUTH" http://localhost:4042/state/conflicts\` → the unresolved divergences awaiting your call (each with a stable \`conflictId\` + the preserved versions).
|
|
4335
|
+
- Resolve one (YOUR authority — the foundation never picks a winner): \`curl -X POST -H "Authorization: Bearer $AUTH" http://localhost:4042/state/resolve-conflict -H 'Content-Type: application/json' -d '{"conflictId":"<id>","winnerOrigin":"<machine id>"}'\` (or supply a \`mergedVersion\` object). The chosen/merged record then replicates as normal.
|
|
4336
|
+
- Roll back a machine's data (un-merge): disabling \`multiMachine.stateSync.<store>\` for a peer atomically DROPS that origin's contribution — the union recomputes live, a key that was winning from the dropped machine reverts to the latest among the REMAINING machines (or to "no record"), any conflict that only existed because of it auto-resolves, and the dropped streams are quarantined-aside (reversible, auditable, never a destructive delete). View what's currently un-merged: \`curl -H "Authorization: Bearer $AUTH" http://localhost:4042/state/quarantine\`.
|
|
4337
|
+
- **When to use** (PROACTIVE — these are the triggers): the user asks "why do I have two versions of preference X?" → read open conflicts and present them for resolution. The user says "roll back machine Y's data / forget what the other machine learned" → un-merge that origin. Spec: \`docs/specs/multi-machine-replicated-store-foundation.md\` §7.
|
|
4338
|
+
`;
|
|
4339
|
+
content += '\n' + oneMemory;
|
|
4340
|
+
patched = true;
|
|
4341
|
+
result.upgraded.push('CLAUDE.md: added One Memory (replicated stores) section');
|
|
4342
|
+
}
|
|
4247
4343
|
// ContextWedgeSentinel — the 4th silently-stopped sentinel. Tells the agent
|
|
4248
4344
|
// about the transcript fast-fail wedges (thinking-block 400 + AUP-rejection
|
|
4249
4345
|
// loop) + that auto-recovery is opt-in. Without it, an agent asked "why did
|
|
@@ -5530,6 +5626,16 @@ Create worktrees for collaborator repos with \`instar worktree create <branch>\`
|
|
|
5530
5626
|
patched = true;
|
|
5531
5627
|
result.upgraded.push('CLAUDE.md: added Threadline Single-Negotiator section');
|
|
5532
5628
|
}
|
|
5629
|
+
// HONEST-PROGRESS-MESSAGING C (docs alignment) — the silent-freeze watchdog +
|
|
5630
|
+
// promise beacon are now honest (corroborate before claiming a freeze; silent
|
|
5631
|
+
// unless there's something true to say). Existing agents learn what they are,
|
|
5632
|
+
// their defaults, and how to tune/disable via this appended subsection (Agent
|
|
5633
|
+
// Awareness Standard). Content-sniff marker keeps it idempotent.
|
|
5634
|
+
if (!content.includes('Honest progress messaging (silent-freeze watchdog + promise beacon)')) {
|
|
5635
|
+
content += `\n### Honest progress messaging (silent-freeze watchdog + promise beacon)\n\nTwo background notifiers used to post frequent, falsely-confident noise because they judged "work" by whether the terminal *screen* repainted — a busy long task looks identical to a frozen one. Both are now honest. They are SIGNALS, never gates: they only decide whether to notify you, and every error path fails toward silence.\n- **Silent-freeze watchdog** (ActiveWorkSilenceSentinel): before claiming a session is stuck, it re-captures the LIVE frame and corroborates — if the frame still shows an active-work indicator (spinner / "esc to interrupt"), a sub-agent is live, or it's a clean idle prompt, it stays SILENT. It speaks only when genuinely wedged, and even then hedges ("…hasn't changed in N min and a nudge didn't wake it — it may be stuck, or on a long task I can't see into. Want me to check?"). Threshold raised 15m→30m; a 90m frozen-indicator backstop still surfaces a real mid-tool hang. Tune/disable: \`monitoring.activeWorkSilenceSentinel.enabled\` (off), \`.silenceThresholdMs\` (default 30m), \`.activeWorkMaxFrozenIndicatorMs\` (default 90m).\n- **Promise beacon** (the ⏳ heartbeats): the zero-information "still on it, no new output" filler is suppressed by default — it speaks only on genuine new progress, deadline pressure, a sparse once-per-60m liveness line, or a one-shot turn-finished close-out. Base cadence relaxed 10m→20m. Tune/disable: \`promiseBeacon.suppressUnchangedHeartbeats: false\` (restore the legacy every-tick heartbeat — the rollback lever), \`promiseBeacon.beaconLivenessIntervalMs\` (default 60m), \`promiseBeacon.turnFinishedCloseoutChecks\` (default 3).\n- **Doc correction:** the trio's escalations are NOT gated by \`monitoring.sentinelTelegramEscalation\` (that gate governs a different path); they route through the tone-gated \`/attention\` surface and are controlled by each sentinel's own \`enabled\` flag (both default true). Effectiveness is measurable in \`logs/sentinel-events.jsonl\` and the per-feature LLM-metrics surface (feature keys \`active-work-silence\`, \`promise-beacon\`). Spec: \`docs/specs/HONEST-PROGRESS-MESSAGING-SPEC.md\`.\n`;
|
|
5636
|
+
patched = true;
|
|
5637
|
+
result.upgraded.push('CLAUDE.md: added Honest progress messaging section');
|
|
5638
|
+
}
|
|
5533
5639
|
if (patched) {
|
|
5534
5640
|
try {
|
|
5535
5641
|
fs.writeFileSync(claudeMdPath, content);
|
|
@@ -5702,6 +5808,16 @@ Create worktrees for collaborator repos with \`instar worktree create <branch>\`
|
|
|
5702
5808
|
// Metrics precedent; each CLAUDE.md contains exactly one, so the other no-ops.
|
|
5703
5809
|
'**Links that survive machine boundaries (WS4.4',
|
|
5704
5810
|
'### Links that survive machine boundaries (WS4.4',
|
|
5811
|
+
// One Memory (replicated stores) — multi-machine-replicated-store-foundation
|
|
5812
|
+
// §7: framework-agnostic — a Codex/Gemini agent on a multi-machine pool must
|
|
5813
|
+
// know stores replicate with a no-clobber union + operator-resolved conflicts
|
|
5814
|
+
// (/state/conflicts, /state/resolve-conflict) + origin-tagged rollback
|
|
5815
|
+
// (/state/quarantine), so it answers "why two versions of preference X?" /
|
|
5816
|
+
// "roll back machine Y's data" instead of improvising a clobber. Two tail-
|
|
5817
|
+
// truncated variants cover both deployed forms (templates' bold block +
|
|
5818
|
+
// migrateClaudeMd's H3); each CLAUDE.md contains exactly one, so the other no-ops.
|
|
5819
|
+
'**One Memory (replicated stores)',
|
|
5820
|
+
'### One Memory (replicated stores)',
|
|
5705
5821
|
];
|
|
5706
5822
|
for (const shadowName of ['AGENTS.md', 'GEMINI.md']) {
|
|
5707
5823
|
const shadowPath = path.join(this.config.projectDir, shadowName);
|