@jangts/agent-core 0.3.5 → 0.3.6
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 +21 -0
- package/README.md +28 -26
- package/development/docs/api/README.en.md +2 -0
- package/development/docs/api/README.md +2 -0
- package/development/docs/api/observability.en.md +37 -11
- package/development/docs/api/observability.md +64 -11
- package/development/docs/api/reference.en.md +469 -348
- package/development/docs/api/reference.md +193 -137
- package/development/docs/api/types.en.md +1 -0
- package/development/docs/api/types.md +1 -0
- package/development/docs/api/workflow-views.en.md +64 -0
- package/development/docs/api/workflow-views.md +78 -0
- package/development/docs/api/workflow.en.md +6 -2
- package/development/docs/api/workflow.md +6 -2
- package/development/skills/agent-core-app/SKILL.md +12 -0
- package/dist/cjs/capabilities/invocation.js +21 -1
- package/dist/cjs/capabilities/tool-runtime.js +8 -1
- package/dist/cjs/capabilities/tools.js +12 -17
- package/dist/cjs/diagnostics/index.js +51 -3
- package/dist/cjs/diagnostics/native-sub-flow.js +106 -0
- package/dist/cjs/diagnostics/sub-flow.js +278 -32
- package/dist/cjs/execution/engine.js +3 -2
- package/dist/cjs/execution/events.js +5 -5
- package/dist/cjs/execution/reporting.js +18 -28
- package/dist/cjs/execution/workflow-chain.js +211 -0
- package/dist/cjs/execution/workflow-graph.js +72 -0
- package/dist/cjs/execution/workflow.js +34 -6
- package/dist/cjs/kits/aggregation.js +17 -14
- package/dist/cjs/kits/answering/checks.js +2 -1
- package/dist/cjs/kits/answering/flow.js +24 -21
- package/dist/cjs/kits/answering/tasks.js +25 -20
- package/dist/cjs/kits/delivery.js +36 -24
- package/dist/cjs/kits/knowledge/catalog.js +33 -30
- package/dist/cjs/kits/policies.js +3 -2
- package/dist/cjs/kits/presentation/outputs.js +2 -1
- package/dist/cjs/kits/retrieval.js +7 -1
- package/dist/cjs/kits/tools.js +1 -0
- package/dist/cjs/model/decision-retry.js +2 -1
- package/dist/cjs/model/runner.js +20 -5
- package/dist/cjs/structs/execution/workflow-views.js +2 -0
- package/dist/cjs/support/context/nodes.js +48 -45
- package/dist/cjs/support/context/processing.js +6 -3
- package/dist/cjs/utils/invocation.js +1 -0
- package/dist/esm/capabilities/invocation.js +21 -1
- package/dist/esm/capabilities/tool-runtime.js +8 -1
- package/dist/esm/capabilities/tools.js +12 -17
- package/dist/esm/diagnostics/index.d.ts +1 -0
- package/dist/esm/diagnostics/index.js +48 -2
- package/dist/esm/diagnostics/native-sub-flow.d.ts +94 -0
- package/dist/esm/diagnostics/native-sub-flow.js +101 -0
- package/dist/esm/diagnostics/sub-flow.d.ts +56 -4
- package/dist/esm/diagnostics/sub-flow.js +271 -32
- package/dist/esm/execution/engine.d.ts +1 -0
- package/dist/esm/execution/engine.js +3 -2
- package/dist/esm/execution/events.js +5 -5
- package/dist/esm/execution/reporting.d.ts +6 -12
- package/dist/esm/execution/reporting.js +19 -29
- package/dist/esm/execution/workflow-chain.d.ts +3 -0
- package/dist/esm/execution/workflow-chain.js +208 -0
- package/dist/esm/execution/workflow-graph.d.ts +7 -0
- package/dist/esm/execution/workflow-graph.js +68 -0
- package/dist/esm/execution/workflow.d.ts +6 -0
- package/dist/esm/execution/workflow.js +34 -6
- package/dist/esm/kits/aggregation.d.ts +1 -1
- package/dist/esm/kits/aggregation.js +17 -14
- package/dist/esm/kits/answering/checks.js +2 -1
- package/dist/esm/kits/answering/flow.js +24 -21
- package/dist/esm/kits/answering/tasks.js +25 -20
- package/dist/esm/kits/delivery.d.ts +0 -9
- package/dist/esm/kits/delivery.js +36 -24
- package/dist/esm/kits/knowledge/catalog.js +33 -30
- package/dist/esm/kits/policies.d.ts +1 -1
- package/dist/esm/kits/policies.js +3 -2
- package/dist/esm/kits/presentation/outputs.js +2 -1
- package/dist/esm/kits/retrieval.js +7 -1
- package/dist/esm/kits/tools.js +1 -0
- package/dist/esm/model/decision-retry.d.ts +2 -0
- package/dist/esm/model/decision-retry.js +2 -1
- package/dist/esm/model/runner.d.ts +2 -0
- package/dist/esm/model/runner.js +20 -5
- package/dist/esm/structs/capabilities/invocation.d.ts +2 -0
- package/dist/esm/structs/capabilities/tools.d.ts +7 -3
- package/dist/esm/structs/common.d.ts +2 -0
- package/dist/esm/structs/debug.d.ts +36 -20
- package/dist/esm/structs/execution/workflow-views.d.ts +123 -0
- package/dist/esm/structs/execution/workflow-views.js +1 -0
- package/dist/esm/structs/execution/workflow.d.ts +4 -3
- package/dist/esm/structs/index.d.ts +1 -0
- package/dist/esm/structs/model/runtime.d.ts +2 -0
- package/dist/esm/support/context/nodes.js +48 -45
- package/dist/esm/support/context/processing.js +6 -3
- package/dist/esm/utils/invocation.d.ts +1 -0
- package/dist/esm/utils/invocation.js +1 -0
- package/package.json +1 -1
- package/dist/cjs/utils/debug.js +0 -30
- package/dist/esm/utils/debug.d.ts +0 -27
- package/dist/esm/utils/debug.js +0 -27
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { WorkflowChainSource } from './workflow-views.js';
|
|
1
2
|
/**
|
|
2
3
|
* Workflow contract: a state graph whose nodes report their own use of model and tools.
|
|
3
4
|
*
|
|
@@ -66,8 +67,6 @@ export interface WorkflowNodeReport {
|
|
|
66
67
|
readonly usedModel?: boolean;
|
|
67
68
|
/** App-defined progress detail; collected only when content logging is enabled. */
|
|
68
69
|
readonly payload?: unknown;
|
|
69
|
-
/** Logger owned by this visit, used to report sub-steps. */
|
|
70
|
-
readonly subs?: import('../debug.js').SubFlowLogger;
|
|
71
70
|
}
|
|
72
71
|
/** One node of the graph. */
|
|
73
72
|
export type WorkflowNode<State, Result, Runtime = undefined> = {
|
|
@@ -94,7 +93,7 @@ export type WorkflowNode<State, Result, Runtime = undefined> = {
|
|
|
94
93
|
readonly requires?: readonly (keyof State & string)[];
|
|
95
94
|
/** State keys this node is expected to produce; validated after `run`. */
|
|
96
95
|
readonly provides?: readonly (keyof State & string)[];
|
|
97
|
-
/** Candidate successors, evaluated in order. */
|
|
96
|
+
/** Candidate successors, evaluated in order. A getter must be pure; registration reads it once. */
|
|
98
97
|
readonly routes: readonly WorkflowRoute<State, Result, Runtime>[];
|
|
99
98
|
/** Return only changed fields. Core commits them after cancellation and output checks. */
|
|
100
99
|
readonly run?: (state: Readonly<State>, context: WorkflowContext<Runtime>) => void | Partial<State> | Promise<void | Partial<State>>;
|
|
@@ -103,6 +102,8 @@ export type WorkflowNode<State, Result, Runtime = undefined> = {
|
|
|
103
102
|
export type AgentWorkflowDefinition<State, Result, Runtime = undefined> = {
|
|
104
103
|
/** Stable workflow id, also reported in every event. */
|
|
105
104
|
readonly id: string;
|
|
105
|
+
/** App-owned authorized diagnostic reader; no global run storage is installed. */
|
|
106
|
+
readonly chainSource?: WorkflowChainSource;
|
|
106
107
|
/** Definition revision; lets hosts distinguish executions of different graph versions. */
|
|
107
108
|
readonly revision?: string;
|
|
108
109
|
readonly nodes: readonly WorkflowNode<State, Result, Runtime>[];
|
|
@@ -175,6 +175,8 @@ export type ModelRunnerOptions<Transports extends readonly ModelTransportDefinit
|
|
|
175
175
|
} & ModelRunnerSettings;
|
|
176
176
|
/** One model call request. The input shape selects prompt mode or message mode. */
|
|
177
177
|
export type ModelCallRequest<Transport = string> = {
|
|
178
|
+
/** Record this call in the supplied logger; omission adds no sub-flow record. */
|
|
179
|
+
readonly logger?: import('../debug.js').SubFlowLogger;
|
|
178
180
|
/** Additional cancellation can shorten, never replace, the Runner lifetime. */
|
|
179
181
|
readonly signal?: AbortSignal;
|
|
180
182
|
/** Parent observation scope for this invocation; never changes execution budget or signal. */
|
|
@@ -9,6 +9,7 @@
|
|
|
9
9
|
* Main exports: `createContextProcessingNode`, `createContextSelectionNode`,
|
|
10
10
|
* `createContextReductionNode` and their result/definition types.
|
|
11
11
|
*/
|
|
12
|
+
import { nativeSubFlowAsync } from '../../diagnostics/native-sub-flow.js';
|
|
12
13
|
import { beginContextProcessing, finishContextProcessing, chooseSteps, applyReduction, needsReduction, watermarks, validateReductionTargets, contextPolicyCatalog, validateContextPolicy, } from './processing.js';
|
|
13
14
|
import { modelRunnerDefaults } from '../../model/defaults.js';
|
|
14
15
|
import { synchronous } from '../../utils/synchronous.js';
|
|
@@ -124,53 +125,55 @@ function contextNode(definition, execute) {
|
|
|
124
125
|
onErrorRouteId: definition.onErrorRouteId,
|
|
125
126
|
routes: definition.routes,
|
|
126
127
|
async run(state, context) {
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
diagnostics: context.diagnostics,
|
|
149
|
-
compressors,
|
|
150
|
-
selectors,
|
|
151
|
-
// Read lazily so handlers see the live budget rather than the value at preparation.
|
|
152
|
-
remainingCalls: () => prepared.remainingCalls,
|
|
153
|
-
callModel: (options) => context.model.invoke({
|
|
154
|
-
...options,
|
|
155
|
-
modelId: options.modelId ?? prepared.modelId,
|
|
128
|
+
return nativeSubFlowAsync(context, 'context', definition.id, async () => {
|
|
129
|
+
// The node timeout is an additional bound; parent cancellation still wins.
|
|
130
|
+
const signal = combineSignals(context.signal, AbortSignal.timeout(timeoutMs));
|
|
131
|
+
const prepared = selectPrepared
|
|
132
|
+
? selectPrepared(state, context)
|
|
133
|
+
: context.model.prepare(typeof request === 'function' ? request(state, context) : request);
|
|
134
|
+
const input = synchronous(plan(state, context), 'Context plans must be synchronous');
|
|
135
|
+
// An empty measurement reports the allowance left after transport, instruction and schema
|
|
136
|
+
// overhead, so processing must fit inside whichever limit is tighter.
|
|
137
|
+
const overhead = prepared.measure([]);
|
|
138
|
+
const fullLimit = Math.min(input.maxInputChars, overhead.maxInputChars);
|
|
139
|
+
const bodyLimit = fullLimit;
|
|
140
|
+
breakWhile(bodyLimit < 1, 'No input capacity for context');
|
|
141
|
+
const work = beginContextProcessing({
|
|
142
|
+
fragments: input.fragments,
|
|
143
|
+
additionalMessages: input.additionalMessages,
|
|
144
|
+
originalFragments: input.originalFragments,
|
|
145
|
+
mutableFragmentIds: input.mutableFragmentIds,
|
|
146
|
+
maxInputChars: bodyLimit,
|
|
147
|
+
}, policy, {
|
|
148
|
+
stageId: prepared.stageId,
|
|
156
149
|
signal,
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
150
|
+
diagnostics: context.diagnostics,
|
|
151
|
+
compressors,
|
|
152
|
+
selectors,
|
|
153
|
+
// Read lazily so handlers see the live budget rather than the value at preparation.
|
|
154
|
+
remainingCalls: () => prepared.remainingCalls,
|
|
155
|
+
callModel: (options) => context.model.invoke({
|
|
156
|
+
...options,
|
|
157
|
+
modelId: options.modelId ?? prepared.modelId,
|
|
158
|
+
signal,
|
|
159
|
+
}),
|
|
160
|
+
...(overhead.counterId
|
|
161
|
+
? {
|
|
162
|
+
tokenBudget: {
|
|
163
|
+
counterId: overhead.counterId,
|
|
164
|
+
inputLimit: overhead.inputTokenLimit,
|
|
165
|
+
measure: (messages) => prepared.measure(messages).inputTokens,
|
|
166
|
+
},
|
|
167
|
+
}
|
|
168
|
+
: {}),
|
|
169
|
+
});
|
|
170
|
+
context.report({ payload: { phase: 'processing', fragmentCount: input.fragments.length } });
|
|
171
|
+
const result = await execute(work, prepared, fullLimit, state, context);
|
|
172
|
+
// Never report or commit a result produced after cancellation.
|
|
173
|
+
signal.throwIfAborted();
|
|
174
|
+
context.report({ payload: { phase: 'processed', report: work.report } });
|
|
175
|
+
return synchronous(update(result, state), 'Context node updates must be synchronous');
|
|
167
176
|
});
|
|
168
|
-
context.report({ payload: { phase: 'processing', fragmentCount: input.fragments.length } });
|
|
169
|
-
const result = await execute(work, prepared, fullLimit, state, context);
|
|
170
|
-
// Never report or commit a result produced after cancellation.
|
|
171
|
-
signal.throwIfAborted();
|
|
172
|
-
context.report({ payload: { phase: 'processed', report: work.report } });
|
|
173
|
-
return synchronous(update(result, state), 'Context node updates must be synchronous');
|
|
174
177
|
},
|
|
175
178
|
};
|
|
176
179
|
}
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
* `finishContextProcessing` (staged runs), the policy/reduction catalogs and the individual
|
|
12
12
|
* validation, measurement and reduction helpers used by workflow nodes.
|
|
13
13
|
*/
|
|
14
|
+
import { nativeSubFlowAsync } from '../../diagnostics/native-sub-flow.js';
|
|
14
15
|
import { snapshotFragment, snapshotMessage } from './snapshot.js';
|
|
15
16
|
import { auditContextChange as audit } from '../../context/audit.js';
|
|
16
17
|
import { historyGroups, validateRecentHistory } from './history.js';
|
|
@@ -595,7 +596,9 @@ export function finishContextProcessing(state) {
|
|
|
595
596
|
* @throws {BudgetError} When a handler exhausts its call allowance.
|
|
596
597
|
*/
|
|
597
598
|
export async function processContext(plan, policy, ports) {
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
599
|
+
return nativeSubFlowAsync(ports, 'context', policy.mode, async () => {
|
|
600
|
+
const state = beginContextProcessing(plan, policy, ports);
|
|
601
|
+
await contextPolicyCatalog[policy.mode].run(state);
|
|
602
|
+
return finishContextProcessing(state);
|
|
603
|
+
});
|
|
601
604
|
}
|
|
@@ -38,6 +38,7 @@ export declare function invocationResult<Value, Metadata extends InvocationMetad
|
|
|
38
38
|
* @throws TypeError When the arity or the request shape is invalid.
|
|
39
39
|
*/
|
|
40
40
|
export declare function toolInvocation(request: import('../structs/capabilities/tools.js').ToolInvocationRequest, arity: number): {
|
|
41
|
+
logger: import("../index.js").SubFlowLogger | undefined;
|
|
41
42
|
toolId: string;
|
|
42
43
|
input: unknown;
|
|
43
44
|
diagnostics: import("../index.js").DiagnosticContext | undefined;
|
package/package.json
CHANGED
package/dist/cjs/utils/debug.js
DELETED
|
@@ -1,30 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.captureSubSteps = captureSubSteps;
|
|
4
|
-
const sub_flow_js_1 = require("../diagnostics/sub-flow.js");
|
|
5
|
-
const synchronous_js_1 = require("./synchronous.js");
|
|
6
|
-
/**
|
|
7
|
-
* Read the current sub-step log of one execution visit.
|
|
8
|
-
*
|
|
9
|
-
* A missing reader or a logger that yields nothing produces the empty shape, which
|
|
10
|
-
* lets callers spread the result unconditionally. Failures are reported as one
|
|
11
|
-
* dropped step instead of propagating, because diagnostics must not break execution.
|
|
12
|
-
*
|
|
13
|
-
* @param read - Getter for the current logger; omitted when the caller has no logger.
|
|
14
|
-
* @param identity - Diagnostic identity copied onto each captured step.
|
|
15
|
-
* @returns Frozen `subSteps`, the number of dropped steps and whether the log was truncated.
|
|
16
|
-
*/
|
|
17
|
-
function captureSubSteps(read, identity) {
|
|
18
|
-
const empty = { subSteps: Object.freeze([]), subStepsDropped: 0, subStepsTruncated: false };
|
|
19
|
-
if (!read)
|
|
20
|
-
return empty;
|
|
21
|
-
try {
|
|
22
|
-
const logger = (0, synchronous_js_1.synchronous)(read(), 'Debug steps must be synchronous');
|
|
23
|
-
return logger === undefined
|
|
24
|
-
? empty
|
|
25
|
-
: { ...empty, subSteps: (0, sub_flow_js_1.readSubFlowLogger)(logger, undefined, identity) };
|
|
26
|
-
}
|
|
27
|
-
catch {
|
|
28
|
-
return { ...empty, subStepsDropped: 1 };
|
|
29
|
-
}
|
|
30
|
-
}
|
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Adapter between App-supplied debug loggers and the diagnostics pipeline.
|
|
3
|
-
*
|
|
4
|
-
* Sub-flow loggers are mutable, execution-owned objects. This module reads one at the
|
|
5
|
-
* moment a diagnostic fact is built and converts it into a frozen array of steps, so
|
|
6
|
-
* persisted observations never retain a live logger.
|
|
7
|
-
*
|
|
8
|
-
* Exports: `captureSubSteps`.
|
|
9
|
-
*/
|
|
10
|
-
import type { SubFlowLogger } from '../structs/debug.js';
|
|
11
|
-
import type { DiagnosticIdentity } from '../structs/diagnostics.js';
|
|
12
|
-
/**
|
|
13
|
-
* Read the current sub-step log of one execution visit.
|
|
14
|
-
*
|
|
15
|
-
* A missing reader or a logger that yields nothing produces the empty shape, which
|
|
16
|
-
* lets callers spread the result unconditionally. Failures are reported as one
|
|
17
|
-
* dropped step instead of propagating, because diagnostics must not break execution.
|
|
18
|
-
*
|
|
19
|
-
* @param read - Getter for the current logger; omitted when the caller has no logger.
|
|
20
|
-
* @param identity - Diagnostic identity copied onto each captured step.
|
|
21
|
-
* @returns Frozen `subSteps`, the number of dropped steps and whether the log was truncated.
|
|
22
|
-
*/
|
|
23
|
-
export declare function captureSubSteps(read: (() => SubFlowLogger | undefined) | undefined, identity?: Readonly<DiagnosticIdentity>): {
|
|
24
|
-
subSteps: readonly Readonly<import("../index.js").RecordedSubStep>[];
|
|
25
|
-
subStepsDropped: number;
|
|
26
|
-
subStepsTruncated: boolean;
|
|
27
|
-
};
|
package/dist/esm/utils/debug.js
DELETED
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
import { readSubFlowLogger } from '../diagnostics/sub-flow.js';
|
|
2
|
-
import { synchronous } from './synchronous.js';
|
|
3
|
-
/**
|
|
4
|
-
* Read the current sub-step log of one execution visit.
|
|
5
|
-
*
|
|
6
|
-
* A missing reader or a logger that yields nothing produces the empty shape, which
|
|
7
|
-
* lets callers spread the result unconditionally. Failures are reported as one
|
|
8
|
-
* dropped step instead of propagating, because diagnostics must not break execution.
|
|
9
|
-
*
|
|
10
|
-
* @param read - Getter for the current logger; omitted when the caller has no logger.
|
|
11
|
-
* @param identity - Diagnostic identity copied onto each captured step.
|
|
12
|
-
* @returns Frozen `subSteps`, the number of dropped steps and whether the log was truncated.
|
|
13
|
-
*/
|
|
14
|
-
export function captureSubSteps(read, identity) {
|
|
15
|
-
const empty = { subSteps: Object.freeze([]), subStepsDropped: 0, subStepsTruncated: false };
|
|
16
|
-
if (!read)
|
|
17
|
-
return empty;
|
|
18
|
-
try {
|
|
19
|
-
const logger = synchronous(read(), 'Debug steps must be synchronous');
|
|
20
|
-
return logger === undefined
|
|
21
|
-
? empty
|
|
22
|
-
: { ...empty, subSteps: readSubFlowLogger(logger, undefined, identity) };
|
|
23
|
-
}
|
|
24
|
-
catch {
|
|
25
|
-
return { ...empty, subStepsDropped: 1 };
|
|
26
|
-
}
|
|
27
|
-
}
|