impel-cli 0.20.10 → 0.20.12
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/RELEASE_NOTES.md +17 -0
- package/package.json +1 -1
- package/src/agents.js +3 -1
- package/src/nativeAgentTransport.js +34 -4
package/RELEASE_NOTES.md
CHANGED
|
@@ -1,5 +1,22 @@
|
|
|
1
1
|
# Release notes
|
|
2
2
|
|
|
3
|
+
## 0.20.12 — Internal admission retry
|
|
4
|
+
|
|
5
|
+
- Absorbs brief local run-allocation lock contention inside the transport
|
|
6
|
+
instead of returning a model-visible busy error.
|
|
7
|
+
- Keeps cancellation bounded while preserving the same single persisted
|
|
8
|
+
idempotency key and authoritative run identity.
|
|
9
|
+
- Prevents a transient concurrency collision from adding a second agent tool
|
|
10
|
+
call or wrapper inference turn.
|
|
11
|
+
|
|
12
|
+
## 0.20.11 — Managed profile upgrade compatibility
|
|
13
|
+
|
|
14
|
+
- Recognizes every discovery-root manifest from v2 through the current schema
|
|
15
|
+
when refreshing generated native agents.
|
|
16
|
+
- Preserves collision protection for files absent from the prior managed
|
|
17
|
+
manifest while allowing v8 profiles to regenerate onto v9.
|
|
18
|
+
- Adds a regression test for upgrading the immediately previous manifest.
|
|
19
|
+
|
|
3
20
|
## 0.20.10 — Direct-answer continuation surface
|
|
4
21
|
|
|
5
22
|
- Limits answer-only native agents to the exact answer and resume tools.
|
package/package.json
CHANGED
package/src/agents.js
CHANGED
|
@@ -949,7 +949,9 @@ export function syncAgentProfile({
|
|
|
949
949
|
throw new Error("generated native-agent destinations are not unique");
|
|
950
950
|
}
|
|
951
951
|
const priorFiles = new Set(prior?.files || []);
|
|
952
|
-
const priorUsesDiscoveryRoot =
|
|
952
|
+
const priorUsesDiscoveryRoot = Number.isInteger(prior?.version)
|
|
953
|
+
&& prior.version >= 2
|
|
954
|
+
&& prior.version <= MANAGED_AGENT_MANIFEST_VERSION;
|
|
953
955
|
|
|
954
956
|
// Native clients discover standalone definitions directly under `agents/`.
|
|
955
957
|
// Preflight every destination before writing so an unmanaged file with the
|
|
@@ -52,6 +52,8 @@ const DEFAULT_MAX_RESPONSE_BYTES = 2 * 1024 * 1024;
|
|
|
52
52
|
const DEFAULT_MAX_STATE_BYTES = 512 * 1024;
|
|
53
53
|
const DEFAULT_LOCK_LEASE_MS = 75_000;
|
|
54
54
|
const DEFAULT_ADMISSION_LEASE_MS = 10_000;
|
|
55
|
+
const DEFAULT_ADMISSION_RETRY_ATTEMPTS = 40;
|
|
56
|
+
const DEFAULT_ADMISSION_RETRY_INTERVAL_MS = 25;
|
|
55
57
|
const STATE_COMMIT_LEASE_MARGIN_MS = 5_000;
|
|
56
58
|
const CIBI_START_IN_PROGRESS_CODE = "eve_run_drain_start_in_progress";
|
|
57
59
|
const CIBI_START_IN_PROGRESS_MESSAGE = "The durable Eve drain workflow is still being enqueued; retry this idempotent start.";
|
|
@@ -167,6 +169,30 @@ function throwIfAborted(signal) {
|
|
|
167
169
|
if (signal?.aborted) throw abortError();
|
|
168
170
|
}
|
|
169
171
|
|
|
172
|
+
function abortableDelay(ms, signal) {
|
|
173
|
+
throwIfAborted(signal);
|
|
174
|
+
return new Promise((resolve, reject) => {
|
|
175
|
+
let settled = false;
|
|
176
|
+
let timeout = null;
|
|
177
|
+
const cleanup = () => signal?.removeEventListener("abort", onAbort);
|
|
178
|
+
const onAbort = () => {
|
|
179
|
+
if (settled) return;
|
|
180
|
+
settled = true;
|
|
181
|
+
clearTimeout(timeout);
|
|
182
|
+
cleanup();
|
|
183
|
+
reject(abortError());
|
|
184
|
+
};
|
|
185
|
+
timeout = setTimeout(() => {
|
|
186
|
+
if (settled) return;
|
|
187
|
+
settled = true;
|
|
188
|
+
cleanup();
|
|
189
|
+
resolve();
|
|
190
|
+
}, ms);
|
|
191
|
+
signal?.addEventListener("abort", onAbort, { once: true });
|
|
192
|
+
if (signal?.aborted) onAbort();
|
|
193
|
+
});
|
|
194
|
+
}
|
|
195
|
+
|
|
170
196
|
function boundedAttachmentSignal(parentSignal, timeoutMs) {
|
|
171
197
|
const controller = new AbortController();
|
|
172
198
|
let timedOut = false;
|
|
@@ -1660,11 +1686,15 @@ export class NativeAgentCompositeTransport {
|
|
|
1660
1686
|
};
|
|
1661
1687
|
}
|
|
1662
1688
|
|
|
1663
|
-
allocateState(startArguments, { startMode = "durable" } = {}) {
|
|
1689
|
+
async allocateState(startArguments, { startMode = "durable", signal } = {}) {
|
|
1664
1690
|
let admission = null;
|
|
1665
1691
|
try {
|
|
1666
1692
|
this.ensureRoots();
|
|
1667
|
-
|
|
1693
|
+
for (let attempt = 0; attempt < DEFAULT_ADMISSION_RETRY_ATTEMPTS; attempt += 1) {
|
|
1694
|
+
admission = this.acquireAdmissionLock();
|
|
1695
|
+
if (admission) break;
|
|
1696
|
+
await abortableDelay(DEFAULT_ADMISSION_RETRY_INTERVAL_MS, signal);
|
|
1697
|
+
}
|
|
1668
1698
|
if (!admission) {
|
|
1669
1699
|
throw new Error("native-agent run allocation is busy; retry without changing the request");
|
|
1670
1700
|
}
|
|
@@ -1726,7 +1756,7 @@ export class NativeAgentCompositeTransport {
|
|
|
1726
1756
|
...(args.context !== undefined ? { context: args.context } : {}),
|
|
1727
1757
|
contextKeys: args.contextKeys ?? [],
|
|
1728
1758
|
}, prepared.agent);
|
|
1729
|
-
state = this.allocateState(startArguments, { startMode: "answer" });
|
|
1759
|
+
state = await this.allocateState(startArguments, { startMode: "answer", signal: attachment.signal });
|
|
1730
1760
|
lock = this.acquireLock(state.invocationId);
|
|
1731
1761
|
if (!lock) return handleForState(state);
|
|
1732
1762
|
const result = await this.attach(state, prepared, {
|
|
@@ -1770,7 +1800,7 @@ export class NativeAgentCompositeTransport {
|
|
|
1770
1800
|
try {
|
|
1771
1801
|
const prepared = await this.prepareNewSession(attachment.signal);
|
|
1772
1802
|
const startArguments = this.normalizeRunArguments(args, prepared.agent);
|
|
1773
|
-
state = this.allocateState(startArguments);
|
|
1803
|
+
state = await this.allocateState(startArguments, { signal: attachment.signal });
|
|
1774
1804
|
// The durable identity and exact retry arguments exist before the first
|
|
1775
1805
|
// upstream byte is sent.
|
|
1776
1806
|
lock = this.acquireLock(state.invocationId);
|