commonswarm 0.1.33 → 0.1.34
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/cswarm.cjs +132 -112
- package/package.json +1 -1
package/cswarm.cjs
CHANGED
|
@@ -33068,7 +33068,7 @@ function parseV2Record(row) {
|
|
|
33068
33068
|
throw new Error("stored listener effect is malformed");
|
|
33069
33069
|
}
|
|
33070
33070
|
if (signalKind2 === "note") {
|
|
33071
|
-
if (typeof row.commandId !== "string" || row.commandId !== "" || row.state !== "observed" || row.promptAttempts !== 0 || row.postAttempts !== 0 || row.replyBody !== null || row.replyTruncated !== false || row.replySignalId !== null || row.failureCode !== null) {
|
|
33071
|
+
if (typeof row.commandId !== "string" || row.commandId !== "" || row.state !== "observed" && row.state !== "routed_main" || row.promptAttempts !== 0 || row.postAttempts !== 0 || row.replyBody !== null || row.replyTruncated !== false || row.replySignalId !== null || row.failureCode !== null) {
|
|
33072
33072
|
throw new Error("stored listener effect is malformed");
|
|
33073
33073
|
}
|
|
33074
33074
|
} else if (row.state === "routed_main") {
|
|
@@ -33137,11 +33137,11 @@ function newObservedNoteRecord(input) {
|
|
|
33137
33137
|
updatedAt: input.updatedAt
|
|
33138
33138
|
};
|
|
33139
33139
|
}
|
|
33140
|
-
function
|
|
33140
|
+
function newRoutedMainRecord(input) {
|
|
33141
33141
|
const base = newObservedNoteRecord(input);
|
|
33142
33142
|
return {
|
|
33143
33143
|
...base,
|
|
33144
|
-
signalKind:
|
|
33144
|
+
signalKind: input.signalKind,
|
|
33145
33145
|
state: "routed_main"
|
|
33146
33146
|
};
|
|
33147
33147
|
}
|
|
@@ -35076,8 +35076,8 @@ var FilePendingMainQueue = class {
|
|
|
35076
35076
|
}
|
|
35077
35077
|
};
|
|
35078
35078
|
function pendingMainEntry(signal, principalId, provenance, now, options = {}) {
|
|
35079
|
-
if (signal.kind !== "ask") {
|
|
35080
|
-
throw new Error("only directed asks can enter the pending-for-main queue");
|
|
35079
|
+
if (signal.kind !== "ask" && signal.kind !== "note") {
|
|
35080
|
+
throw new Error("only directed asks and notes can enter the pending-for-main queue");
|
|
35081
35081
|
}
|
|
35082
35082
|
return parseEntry({
|
|
35083
35083
|
signalId: signal.id,
|
|
@@ -35085,6 +35085,7 @@ function pendingMainEntry(signal, principalId, provenance, now, options = {}) {
|
|
|
35085
35085
|
principalId,
|
|
35086
35086
|
fromId: signal.from,
|
|
35087
35087
|
fromKind: signal.from_kind,
|
|
35088
|
+
kind: signal.kind,
|
|
35088
35089
|
senderName: provenance.senderName,
|
|
35089
35090
|
body: signal.body,
|
|
35090
35091
|
createdAt: signal.created_at,
|
|
@@ -35182,7 +35183,7 @@ function ackForTerminalEffect(record, now) {
|
|
|
35182
35183
|
if (record.state === "observed" && record.signalKind === "note") {
|
|
35183
35184
|
return { outcome: "observed", lastErrorCode: null };
|
|
35184
35185
|
}
|
|
35185
|
-
if (record.state === "routed_main"
|
|
35186
|
+
if (record.state === "routed_main") {
|
|
35186
35187
|
return { outcome: "queued", lastErrorCode: null };
|
|
35187
35188
|
}
|
|
35188
35189
|
if (record.state === "expired" && record.signalKind === "ask" && Date.parse(record.askUntil) <= now()) {
|
|
@@ -35204,7 +35205,7 @@ function ackForTerminalEffect(record, now) {
|
|
|
35204
35205
|
return { outcome: "failed_terminal", lastErrorCode: "local_effect_failed" };
|
|
35205
35206
|
}
|
|
35206
35207
|
function isAckableTerminalEffect(record, now) {
|
|
35207
|
-
return record.state === "done" && record.signalKind === "ask" && !!record.replySignalId || record.state === "observed" && record.signalKind === "note" || record.state === "routed_main"
|
|
35208
|
+
return record.state === "done" && record.signalKind === "ask" && !!record.replySignalId || record.state === "observed" && record.signalKind === "note" || record.state === "routed_main" || record.state === "expired" && record.signalKind === "ask" && Date.parse(record.askUntil) <= now() || record.state === "failed" && record.signalKind === "ask";
|
|
35208
35209
|
}
|
|
35209
35210
|
function effectPhaseBudget(record) {
|
|
35210
35211
|
if (record === null || record.state === "received" || record.state === "prompting") {
|
|
@@ -35215,6 +35216,9 @@ function effectPhaseBudget(record) {
|
|
|
35215
35216
|
}
|
|
35216
35217
|
return LISTENER_ACK_ONLY_MINIMUM_MS;
|
|
35217
35218
|
}
|
|
35219
|
+
function observedNoteNeedsMainRoute(record, routeMode, deferOverChars) {
|
|
35220
|
+
return record?.state === "observed" && record.signalKind === "note" && decideListenerRoute(routeMode, deferOverChars, record.askBody.length) === "main";
|
|
35221
|
+
}
|
|
35218
35222
|
function verifyPreparedAckEffect(record, active, now) {
|
|
35219
35223
|
if (record === null || record.signalId !== active.signalId || active.ack === null) {
|
|
35220
35224
|
throw new Error("prepared delivery ACK has no matching terminal effect");
|
|
@@ -35450,7 +35454,11 @@ async function runListenerRuntime(options) {
|
|
|
35450
35454
|
...options.resolveSenderProvenance === void 0 ? {} : { resolveSenderProvenance: options.resolveSenderProvenance },
|
|
35451
35455
|
isCredentialFailure: isCredentialLoss
|
|
35452
35456
|
});
|
|
35453
|
-
const
|
|
35457
|
+
const routeSignalToMain = async (signal) => {
|
|
35458
|
+
if (signal.kind !== "ask" && signal.kind !== "note") {
|
|
35459
|
+
throw new Error("only directed asks and notes can route to the main session");
|
|
35460
|
+
}
|
|
35461
|
+
const signalKind2 = signal.kind;
|
|
35454
35462
|
let provenance = {
|
|
35455
35463
|
senderName: null,
|
|
35456
35464
|
operatorId: null,
|
|
@@ -35480,13 +35488,19 @@ async function runListenerRuntime(options) {
|
|
|
35480
35488
|
});
|
|
35481
35489
|
const existing = await options.store.read(signal.id);
|
|
35482
35490
|
if (existing !== null) {
|
|
35483
|
-
if (!sameEffectSignal(existing, signal)
|
|
35484
|
-
throw new Error("stored listener effect does not match the main-routed
|
|
35491
|
+
if (!sameEffectSignal(existing, signal)) {
|
|
35492
|
+
throw new Error("stored listener effect does not match the main-routed message");
|
|
35493
|
+
}
|
|
35494
|
+
if (existing.state === "routed_main") {
|
|
35495
|
+
return existing;
|
|
35496
|
+
}
|
|
35497
|
+
if (!(existing.signalKind === "note" && existing.state === "observed")) {
|
|
35498
|
+
throw new Error("stored listener effect does not match the main-routed message");
|
|
35485
35499
|
}
|
|
35486
|
-
return existing;
|
|
35487
35500
|
}
|
|
35488
|
-
await options.store.write(
|
|
35501
|
+
await options.store.write(newRoutedMainRecord({
|
|
35489
35502
|
signalId: signal.id,
|
|
35503
|
+
signalKind: signalKind2,
|
|
35490
35504
|
body: signal.body,
|
|
35491
35505
|
until: signal.until,
|
|
35492
35506
|
senderOwnerRelation: signal.sender_owner_relation ?? "unknown",
|
|
@@ -35494,7 +35508,7 @@ async function runListenerRuntime(options) {
|
|
|
35494
35508
|
}));
|
|
35495
35509
|
const persisted = await options.store.read(signal.id);
|
|
35496
35510
|
if (persisted === null || !sameEffectSignal(persisted, signal) || persisted.state !== "routed_main") {
|
|
35497
|
-
throw new Error("main-routed
|
|
35511
|
+
throw new Error("main-routed message effect could not be verified");
|
|
35498
35512
|
}
|
|
35499
35513
|
return persisted;
|
|
35500
35514
|
};
|
|
@@ -35716,7 +35730,20 @@ async function runListenerRuntime(options) {
|
|
|
35716
35730
|
const recovery = currentJournalRecord?.active ?? null;
|
|
35717
35731
|
if (recovery?.phase === "ack_pending") {
|
|
35718
35732
|
const horizon = Date.parse(recovery.leasedUntil) + LISTENER_DELIVERY_SAFETY_MARGIN_MS;
|
|
35719
|
-
|
|
35733
|
+
let preparedNeedsMainRoute = false;
|
|
35734
|
+
if (recovery.signalId !== null) {
|
|
35735
|
+
try {
|
|
35736
|
+
preparedNeedsMainRoute = observedNoteNeedsMainRoute(
|
|
35737
|
+
await options.store.read(recovery.signalId),
|
|
35738
|
+
routeMode,
|
|
35739
|
+
deferOverChars
|
|
35740
|
+
);
|
|
35741
|
+
} catch (error) {
|
|
35742
|
+
stop = { reason: "fatal", error: asError2(error) };
|
|
35743
|
+
break;
|
|
35744
|
+
}
|
|
35745
|
+
}
|
|
35746
|
+
if (page.capabilities.deliveryAck && now() < horizon && !preparedNeedsMainRoute) {
|
|
35720
35747
|
const ackStop = await sendPreparedAck(recovery);
|
|
35721
35748
|
if (ackStop !== null) {
|
|
35722
35749
|
stop = ackStop;
|
|
@@ -35755,7 +35782,7 @@ async function runListenerRuntime(options) {
|
|
|
35755
35782
|
terminal = null;
|
|
35756
35783
|
}
|
|
35757
35784
|
}
|
|
35758
|
-
if (terminal !== null && sameRecoveredEffect(recovery, terminal) && isAckableTerminalEffect(terminal, now)) {
|
|
35785
|
+
if (terminal !== null && sameRecoveredEffect(recovery, terminal) && !observedNoteNeedsMainRoute(terminal, routeMode, deferOverChars) && isAckableTerminalEffect(terminal, now)) {
|
|
35759
35786
|
try {
|
|
35760
35787
|
const mapped = ackForTerminalEffect(terminal, now);
|
|
35761
35788
|
await options.deliveryJournal.prepareAck({
|
|
@@ -35949,7 +35976,33 @@ async function runListenerRuntime(options) {
|
|
|
35949
35976
|
if (existing !== null && !sameEffectSignal(existing, signal)) {
|
|
35950
35977
|
throw new Error("stored listener effect does not match the authoritative delivery");
|
|
35951
35978
|
}
|
|
35952
|
-
if (signal.kind
|
|
35979
|
+
if (signal.kind !== "ask" && signal.kind !== "note") {
|
|
35980
|
+
throw new Error("claimed delivery has an unsupported signal kind");
|
|
35981
|
+
}
|
|
35982
|
+
const decision = decideListenerRoute(
|
|
35983
|
+
routeMode,
|
|
35984
|
+
deferOverChars,
|
|
35985
|
+
signal.body.length
|
|
35986
|
+
);
|
|
35987
|
+
options.onEvent?.({
|
|
35988
|
+
type: "routing_decision",
|
|
35989
|
+
signalId: signal.id,
|
|
35990
|
+
routeMode,
|
|
35991
|
+
decision,
|
|
35992
|
+
threshold: deferOverChars,
|
|
35993
|
+
bodyLength: signal.body.length,
|
|
35994
|
+
ts: eventTime(now)
|
|
35995
|
+
});
|
|
35996
|
+
if (decision === "main") {
|
|
35997
|
+
terminal = await routeSignalToMain(signal);
|
|
35998
|
+
options.onEvent?.({
|
|
35999
|
+
type: "effect",
|
|
36000
|
+
signalId: signal.id,
|
|
36001
|
+
status: "routed_main",
|
|
36002
|
+
failureCode: null,
|
|
36003
|
+
ts: eventTime(now)
|
|
36004
|
+
});
|
|
36005
|
+
} else if (signal.kind === "note") {
|
|
35953
36006
|
if (existing === null) {
|
|
35954
36007
|
await options.store.write(newObservedNoteRecord({
|
|
35955
36008
|
signalId: signal.id,
|
|
@@ -35970,85 +36023,58 @@ async function runListenerRuntime(options) {
|
|
|
35970
36023
|
failureCode: null,
|
|
35971
36024
|
ts: eventTime(now)
|
|
35972
36025
|
});
|
|
35973
|
-
} else
|
|
35974
|
-
|
|
35975
|
-
|
|
35976
|
-
|
|
35977
|
-
signal
|
|
35978
|
-
|
|
35979
|
-
|
|
35980
|
-
|
|
35981
|
-
|
|
35982
|
-
|
|
35983
|
-
|
|
35984
|
-
|
|
35985
|
-
|
|
35986
|
-
|
|
35987
|
-
|
|
35988
|
-
|
|
35989
|
-
|
|
36026
|
+
} else {
|
|
36027
|
+
let processAttempt = 0;
|
|
36028
|
+
while (terminal === null) {
|
|
36029
|
+
const before = await options.store.read(signal.id);
|
|
36030
|
+
if (before !== null && !sameEffectSignal(before, signal)) {
|
|
36031
|
+
throw new Error("stored listener effect does not match the authoritative delivery");
|
|
36032
|
+
}
|
|
36033
|
+
const requiredBudget = effectPhaseBudget(before);
|
|
36034
|
+
if (leasedUntilMs <= now() + requiredBudget) {
|
|
36035
|
+
await sleep2(
|
|
36036
|
+
Math.max(
|
|
36037
|
+
0,
|
|
36038
|
+
leasedUntilMs + LISTENER_DELIVERY_SAFETY_MARGIN_MS - now()
|
|
36039
|
+
),
|
|
36040
|
+
abort
|
|
36041
|
+
);
|
|
36042
|
+
if (abort?.aborted) {
|
|
36043
|
+
stop = { reason: "cancelled" };
|
|
36044
|
+
break;
|
|
36045
|
+
}
|
|
36046
|
+
if (now() >= leasedUntilMs + LISTENER_DELIVERY_SAFETY_MARGIN_MS) {
|
|
36047
|
+
await journal.clearActive(eventTime(now));
|
|
36048
|
+
after = null;
|
|
36049
|
+
}
|
|
36050
|
+
break;
|
|
36051
|
+
}
|
|
36052
|
+
const processed = await engine.process(signal);
|
|
36053
|
+
const effect = "record" in processed ? processed.record : null;
|
|
35990
36054
|
options.onEvent?.({
|
|
35991
36055
|
type: "effect",
|
|
35992
36056
|
signalId: signal.id,
|
|
35993
|
-
status:
|
|
35994
|
-
failureCode: null,
|
|
36057
|
+
status: processed.status,
|
|
36058
|
+
failureCode: effect?.failureCode ?? null,
|
|
35995
36059
|
ts: eventTime(now)
|
|
35996
36060
|
});
|
|
35997
|
-
|
|
35998
|
-
|
|
35999
|
-
|
|
36000
|
-
|
|
36001
|
-
|
|
36002
|
-
|
|
36003
|
-
|
|
36004
|
-
|
|
36005
|
-
|
|
36006
|
-
|
|
36007
|
-
|
|
36008
|
-
0,
|
|
36009
|
-
leasedUntilMs + LISTENER_DELIVERY_SAFETY_MARGIN_MS - now()
|
|
36010
|
-
),
|
|
36011
|
-
abort
|
|
36012
|
-
);
|
|
36013
|
-
if (abort?.aborted) {
|
|
36014
|
-
stop = { reason: "cancelled" };
|
|
36015
|
-
break;
|
|
36016
|
-
}
|
|
36017
|
-
if (now() >= leasedUntilMs + LISTENER_DELIVERY_SAFETY_MARGIN_MS) {
|
|
36018
|
-
await journal.clearActive(eventTime(now));
|
|
36019
|
-
after = null;
|
|
36020
|
-
}
|
|
36061
|
+
if (processed.status === "ignored") {
|
|
36062
|
+
throw new Error("claimed delivery was ignored by the listener engine");
|
|
36063
|
+
}
|
|
36064
|
+
if (processed.status === "retry_pending") {
|
|
36065
|
+
processAttempt += 1;
|
|
36066
|
+
await sleep2(
|
|
36067
|
+
deliveryRetryDelay(processAttempt, null, random),
|
|
36068
|
+
abort
|
|
36069
|
+
);
|
|
36070
|
+
if (abort?.aborted) {
|
|
36071
|
+
stop = { reason: "cancelled" };
|
|
36021
36072
|
break;
|
|
36022
36073
|
}
|
|
36023
|
-
|
|
36024
|
-
const effect = "record" in processed ? processed.record : null;
|
|
36025
|
-
options.onEvent?.({
|
|
36026
|
-
type: "effect",
|
|
36027
|
-
signalId: signal.id,
|
|
36028
|
-
status: processed.status,
|
|
36029
|
-
failureCode: effect?.failureCode ?? null,
|
|
36030
|
-
ts: eventTime(now)
|
|
36031
|
-
});
|
|
36032
|
-
if (processed.status === "ignored") {
|
|
36033
|
-
throw new Error("claimed delivery was ignored by the listener engine");
|
|
36034
|
-
}
|
|
36035
|
-
if (processed.status === "retry_pending") {
|
|
36036
|
-
processAttempt += 1;
|
|
36037
|
-
await sleep2(
|
|
36038
|
-
deliveryRetryDelay(processAttempt, null, random),
|
|
36039
|
-
abort
|
|
36040
|
-
);
|
|
36041
|
-
if (abort?.aborted) {
|
|
36042
|
-
stop = { reason: "cancelled" };
|
|
36043
|
-
break;
|
|
36044
|
-
}
|
|
36045
|
-
continue;
|
|
36046
|
-
}
|
|
36047
|
-
terminal = processed.record;
|
|
36074
|
+
continue;
|
|
36048
36075
|
}
|
|
36076
|
+
terminal = processed.record;
|
|
36049
36077
|
}
|
|
36050
|
-
} else {
|
|
36051
|
-
throw new Error("claimed delivery has an unsupported signal kind");
|
|
36052
36078
|
}
|
|
36053
36079
|
} catch (error) {
|
|
36054
36080
|
if (abort?.aborted) {
|
|
@@ -36097,24 +36123,7 @@ async function runListenerRuntime(options) {
|
|
|
36097
36123
|
stop = { reason: "cancelled" };
|
|
36098
36124
|
break;
|
|
36099
36125
|
}
|
|
36100
|
-
if (signal.kind
|
|
36101
|
-
try {
|
|
36102
|
-
await readOrReplaceUnreadableEffect(options.store, signal, now);
|
|
36103
|
-
const record2 = await observeFallbackNote(options.store, signal, now);
|
|
36104
|
-
options.onEvent?.({
|
|
36105
|
-
type: "effect",
|
|
36106
|
-
signalId: signal.id,
|
|
36107
|
-
status: "observed",
|
|
36108
|
-
failureCode: record2.failureCode,
|
|
36109
|
-
ts: eventTime(now)
|
|
36110
|
-
});
|
|
36111
|
-
} catch (error) {
|
|
36112
|
-
stop = { reason: "fatal", error: asError2(error) };
|
|
36113
|
-
break;
|
|
36114
|
-
}
|
|
36115
|
-
continue;
|
|
36116
|
-
}
|
|
36117
|
-
if (signal.kind !== "ask") continue;
|
|
36126
|
+
if (signal.kind !== "ask" && signal.kind !== "note") continue;
|
|
36118
36127
|
let result;
|
|
36119
36128
|
try {
|
|
36120
36129
|
await readOrReplaceUnreadableEffect(options.store, signal, now);
|
|
@@ -36133,7 +36142,7 @@ async function runListenerRuntime(options) {
|
|
|
36133
36142
|
ts: eventTime(now)
|
|
36134
36143
|
});
|
|
36135
36144
|
if (decision === "main") {
|
|
36136
|
-
|
|
36145
|
+
await routeSignalToMain(signal);
|
|
36137
36146
|
options.onEvent?.({
|
|
36138
36147
|
type: "effect",
|
|
36139
36148
|
signalId: signal.id,
|
|
@@ -36143,6 +36152,17 @@ async function runListenerRuntime(options) {
|
|
|
36143
36152
|
});
|
|
36144
36153
|
continue;
|
|
36145
36154
|
}
|
|
36155
|
+
if (signal.kind === "note") {
|
|
36156
|
+
const record2 = await observeFallbackNote(options.store, signal, now);
|
|
36157
|
+
options.onEvent?.({
|
|
36158
|
+
type: "effect",
|
|
36159
|
+
signalId: signal.id,
|
|
36160
|
+
status: "observed",
|
|
36161
|
+
failureCode: record2.failureCode,
|
|
36162
|
+
ts: eventTime(now)
|
|
36163
|
+
});
|
|
36164
|
+
continue;
|
|
36165
|
+
}
|
|
36146
36166
|
result = await engine.process(signal);
|
|
36147
36167
|
} catch (error) {
|
|
36148
36168
|
if (abort?.aborted) {
|
|
@@ -38620,8 +38640,8 @@ var ACCEPTED_AGENT_CREDENTIAL_MESSAGES = [
|
|
|
38620
38640
|
AGENT_CREDENTIAL_MESSAGE_D088
|
|
38621
38641
|
];
|
|
38622
38642
|
function packageVersion() {
|
|
38623
|
-
if ("0.1.
|
|
38624
|
-
return "0.1.
|
|
38643
|
+
if ("0.1.34".length > 0) {
|
|
38644
|
+
return "0.1.34";
|
|
38625
38645
|
}
|
|
38626
38646
|
try {
|
|
38627
38647
|
const value = JSON.parse(
|
|
@@ -38820,11 +38840,11 @@ TTL); a turn that lands just before a rotation can be clamped to the ~5m
|
|
|
38820
38840
|
renewal lead, and if it times out there, durable delivery retries it on the
|
|
38821
38841
|
fresh credential.
|
|
38822
38842
|
|
|
38823
|
-
listen start --route worker|main|split chooses where directed
|
|
38824
|
-
is the unchanged default. main queues every ask for the interactive session.
|
|
38825
|
-
split queues
|
|
38826
|
-
1..10000 and an equal-length
|
|
38827
|
-
to surface queued
|
|
38843
|
+
listen start --route worker|main|split chooses where directed messages go. worker
|
|
38844
|
+
is the unchanged default. main queues every ask or note for the interactive session.
|
|
38845
|
+
split queues messages whose body is longer than --defer-over <chars>; the bound is
|
|
38846
|
+
1..10000 and an equal-length message stays on the worker path. Run cswarm hook check
|
|
38847
|
+
to surface queued messages. hook check has its own 3s ceiling, exits 0 on every
|
|
38828
38848
|
outcome, and skips network checks made within --cooldown seconds (default 30).
|
|
38829
38849
|
hook install claude prints the UserPromptSubmit JSON by default and changes the
|
|
38830
38850
|
project's .claude/settings.json only with --write; uninstall also requires --write.
|