@jini-ai/core 0.6.22 → 0.6.23
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/CHANGELOG.md +4 -0
- package/dist/approval.d.ts +15 -0
- package/dist/approval.js +20 -6
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/teardown.d.ts +30 -0
- package/dist/teardown.js +43 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
package/dist/approval.d.ts
CHANGED
|
@@ -35,6 +35,17 @@ export interface RememberedApprovalPort {
|
|
|
35
35
|
confirmer: HumanConfirmer;
|
|
36
36
|
}): Promise<void>;
|
|
37
37
|
}
|
|
38
|
+
/** Host-owned view/version snapshot captured before asking, then carried into the approved
|
|
39
|
+
* effect. The host validates it at the effect boundary; this port grants no authorization. */
|
|
40
|
+
export interface ApprovalContextPort {
|
|
41
|
+
capture(required: {
|
|
42
|
+
ctx: ToolExecutionContext;
|
|
43
|
+
}): Promise<unknown>;
|
|
44
|
+
prepare(required: {
|
|
45
|
+
ctx: ToolExecutionContext;
|
|
46
|
+
snapshot: unknown;
|
|
47
|
+
}): ToolExecutionContext;
|
|
48
|
+
}
|
|
38
49
|
export interface ApprovalSteps<TPrepared, TDescription> {
|
|
39
50
|
prepare(required: {
|
|
40
51
|
ctx: ToolExecutionContext;
|
|
@@ -153,7 +164,10 @@ export declare function createApprovalProposalStore<TDescription>({ responseTool
|
|
|
153
164
|
};
|
|
154
165
|
/** Apply a host classification through the same handler owner used by domain plans.
|
|
155
166
|
* A host description's string `rememberKey` opts into reusable grants; descriptions remain opaque.
|
|
167
|
+
* Optional context is captured only for asking actions and prepared only after approval.
|
|
156
168
|
* @returns The registration with one approval handler; authorization policy is preserved.
|
|
169
|
+
* @complexity O(input bytes) snapshot plus bounded injected ports; no retained cross-call state.
|
|
170
|
+
* @overallScore 100
|
|
157
171
|
*/
|
|
158
172
|
export declare function applyApprovalPolicy<TDescription>({ registration, classify, asks, describe, askHuman, notConfirmed }: {
|
|
159
173
|
registration: ToolRegistration;
|
|
@@ -171,5 +185,6 @@ export declare function applyApprovalPolicy<TDescription>({ registration, classi
|
|
|
171
185
|
notConfirmed: ApprovalSteps<string, TDescription>['notConfirmed'];
|
|
172
186
|
}, optional?: {
|
|
173
187
|
remembered?: RememberedApprovalPort;
|
|
188
|
+
context?: ApprovalContextPort;
|
|
174
189
|
}): ToolRegistration;
|
|
175
190
|
//# sourceMappingURL=approval.d.ts.map
|
package/dist/approval.js
CHANGED
|
@@ -249,20 +249,34 @@ export function createApprovalProposalStore({ responseTool, messages }, { create
|
|
|
249
249
|
}
|
|
250
250
|
/** Apply a host classification through the same handler owner used by domain plans.
|
|
251
251
|
* A host description's string `rememberKey` opts into reusable grants; descriptions remain opaque.
|
|
252
|
+
* Optional context is captured only for asking actions and prepared only after approval.
|
|
252
253
|
* @returns The registration with one approval handler; authorization policy is preserved.
|
|
254
|
+
* @complexity O(input bytes) snapshot plus bounded injected ports; no retained cross-call state.
|
|
255
|
+
* @overallScore 100
|
|
253
256
|
*/
|
|
254
257
|
export function applyApprovalPolicy({ registration, classify, asks, describe, askHuman, notConfirmed }, optional = {}) {
|
|
255
258
|
return { ...registration, handler: createApprovalHandler({
|
|
256
|
-
prepare: async ({ ctx }) =>
|
|
259
|
+
prepare: async ({ ctx }) => {
|
|
260
|
+
const actionClass = classify({ input: ctx.input });
|
|
261
|
+
const ask = asks({ class: actionClass });
|
|
262
|
+
if (!ask || !optional.context)
|
|
263
|
+
return { actionClass, ask };
|
|
264
|
+
return { actionClass, ask, snapshot: await optional.context.capture({ ctx }) };
|
|
265
|
+
},
|
|
257
266
|
describe: async ({ ctx, prepared }) => {
|
|
258
|
-
const
|
|
259
|
-
const description = await describe({ ctx, class: prepared });
|
|
267
|
+
const description = await describe({ ctx, class: prepared.actionClass });
|
|
260
268
|
const candidate = { value: description };
|
|
261
|
-
return { ask, description, ...(isNonArrayRecord(candidate) && typeof candidate.value.rememberKey === 'string'
|
|
269
|
+
return { ask: prepared.ask, description, ...(isNonArrayRecord(candidate) && typeof candidate.value.rememberKey === 'string'
|
|
262
270
|
? { rememberKey: candidate.value.rememberKey } : {}) };
|
|
263
271
|
},
|
|
264
|
-
askHuman,
|
|
265
|
-
|
|
272
|
+
askHuman,
|
|
273
|
+
notConfirmed: ({ reason, prepared }) => notConfirmed({ reason, prepared: prepared?.actionClass }),
|
|
274
|
+
run: ({ ctx, prepared }, options) => {
|
|
275
|
+
if (!prepared.ask || !optional.context)
|
|
276
|
+
return registration.handler(ctx, options);
|
|
277
|
+
const executionContext = optional.context.prepare({ ctx, snapshot: prepared.snapshot });
|
|
278
|
+
return registration.handler(executionContext, options);
|
|
279
|
+
},
|
|
266
280
|
}, optional) };
|
|
267
281
|
}
|
|
268
282
|
//# sourceMappingURL=approval.js.map
|
package/dist/index.d.ts
CHANGED
|
@@ -8,6 +8,7 @@ export type { PackDisposalFailure } from './pack-lifecycle.js';
|
|
|
8
8
|
export { disposePacks, registerPackTools } from './pack-lifecycle.js';
|
|
9
9
|
export * from './redact.js';
|
|
10
10
|
export * from './user-facing-error.js';
|
|
11
|
+
export { onTeardown, runTeardownSteps, type TeardownHost, type TeardownStep } from './teardown.js';
|
|
11
12
|
export * from './api-token-auth.js';
|
|
12
13
|
export * from './origin-validation.js';
|
|
13
14
|
export * from './principal.js';
|
package/dist/index.js
CHANGED
|
@@ -6,6 +6,7 @@ export { createDaemon } from './daemon.js';
|
|
|
6
6
|
export { disposePacks, registerPackTools } from './pack-lifecycle.js';
|
|
7
7
|
export * from './redact.js';
|
|
8
8
|
export * from './user-facing-error.js';
|
|
9
|
+
export { onTeardown, runTeardownSteps } from './teardown.js';
|
|
9
10
|
export * from './api-token-auth.js';
|
|
10
11
|
export * from './origin-validation.js';
|
|
11
12
|
export * from './principal.js';
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/** A cleanup step may be synchronous or asynchronous; failures are reported after all steps run. */
|
|
2
|
+
export type TeardownStep = () => unknown;
|
|
3
|
+
/** Injected lifecycle registration; core has no dependency on a particular test runner or host. */
|
|
4
|
+
export interface TeardownHost {
|
|
5
|
+
after(fn: () => unknown): void;
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* Attempt every step in reverse registration order. Preserve a single failure's identity;
|
|
9
|
+
* report several as an AggregateError only after attempting the remaining cleanup.
|
|
10
|
+
* @param requiredArgs Steps owned by one lifecycle context; the input array is not mutated.
|
|
11
|
+
* @returns Resolves after cleanup, or rejects with the collected failure(s).
|
|
12
|
+
* @complexity O(n) time and space for n registered steps, excluding each step's own work.
|
|
13
|
+
* @example await runTeardownSteps({ steps: [closeDatabase, closeServer] });
|
|
14
|
+
*/
|
|
15
|
+
export declare function runTeardownSteps({ steps }: {
|
|
16
|
+
steps: readonly TeardownStep[];
|
|
17
|
+
}, _options?: {}): Promise<void>;
|
|
18
|
+
/**
|
|
19
|
+
* Queue a step on the host's single cleanup hook. Hosts that stop at the first throwing hook
|
|
20
|
+
* still attempt every registered resource cleanup before this hook reports a failure.
|
|
21
|
+
* @param requiredArgs Lifecycle host and a step to run when that host finishes.
|
|
22
|
+
* @returns Nothing; registers one hook on first use, then appends to that host's queue.
|
|
23
|
+
* @complexity O(1) registration; cleanup is O(n) time/space for n registered steps.
|
|
24
|
+
* @example onTeardown({ t: context, step: closeServer });
|
|
25
|
+
*/
|
|
26
|
+
export declare function onTeardown({ t, step }: {
|
|
27
|
+
t: TeardownHost;
|
|
28
|
+
step: TeardownStep;
|
|
29
|
+
}, _options?: {}): void;
|
|
30
|
+
//# sourceMappingURL=teardown.d.ts.map
|
package/dist/teardown.js
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
const queues = new WeakMap();
|
|
2
|
+
/**
|
|
3
|
+
* Attempt every step in reverse registration order. Preserve a single failure's identity;
|
|
4
|
+
* report several as an AggregateError only after attempting the remaining cleanup.
|
|
5
|
+
* @param requiredArgs Steps owned by one lifecycle context; the input array is not mutated.
|
|
6
|
+
* @returns Resolves after cleanup, or rejects with the collected failure(s).
|
|
7
|
+
* @complexity O(n) time and space for n registered steps, excluding each step's own work.
|
|
8
|
+
* @example await runTeardownSteps({ steps: [closeDatabase, closeServer] });
|
|
9
|
+
*/
|
|
10
|
+
export async function runTeardownSteps({ steps }, _options = {}) {
|
|
11
|
+
const failures = [];
|
|
12
|
+
for (const step of [...steps].reverse()) {
|
|
13
|
+
try {
|
|
14
|
+
await step();
|
|
15
|
+
}
|
|
16
|
+
catch (error) {
|
|
17
|
+
failures.push(error);
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
if (failures.length === 1)
|
|
21
|
+
throw failures[0];
|
|
22
|
+
if (failures.length > 1)
|
|
23
|
+
throw new AggregateError(failures, "test teardown failed", { cause: failures[0] });
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Queue a step on the host's single cleanup hook. Hosts that stop at the first throwing hook
|
|
27
|
+
* still attempt every registered resource cleanup before this hook reports a failure.
|
|
28
|
+
* @param requiredArgs Lifecycle host and a step to run when that host finishes.
|
|
29
|
+
* @returns Nothing; registers one hook on first use, then appends to that host's queue.
|
|
30
|
+
* @complexity O(1) registration; cleanup is O(n) time/space for n registered steps.
|
|
31
|
+
* @example onTeardown({ t: context, step: closeServer });
|
|
32
|
+
*/
|
|
33
|
+
export function onTeardown({ t, step }, _options = {}) {
|
|
34
|
+
const queued = queues.get(t);
|
|
35
|
+
if (queued) {
|
|
36
|
+
queued.push(step);
|
|
37
|
+
return;
|
|
38
|
+
}
|
|
39
|
+
const steps = [step];
|
|
40
|
+
queues.set(t, steps);
|
|
41
|
+
t.after(() => runTeardownSteps({ steps }));
|
|
42
|
+
}
|
|
43
|
+
//# sourceMappingURL=teardown.js.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jini-ai/core",
|
|
3
|
-
"version": "0.6.
|
|
3
|
+
"version": "0.6.23",
|
|
4
4
|
"description": "The Jini kernel: typed DI tokens, pack composition and lifecycle, the tool registry, redaction, and origin/API-token auth primitives. Zero dependencies.",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"repository": {
|