@salesforce/sfdx-agent-harness-mastra 0.10.0 → 0.12.0
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/README.md +67 -21
- package/dist/default-model-config-factory.d.ts +2 -1
- package/dist/default-model-config-factory.js +8 -1
- package/dist/gen-sink.d.ts +23 -0
- package/dist/gen-sink.js +56 -0
- package/dist/index.d.ts +2 -2
- package/dist/index.js +1 -1
- package/dist/llmg-express-model-config-factory.d.ts +7 -5
- package/dist/llmg-express-model-config-factory.js +12 -5
- package/dist/mastra-event-adapter.d.ts +1 -1
- package/dist/mastra-event-adapter.js +6 -3
- package/dist/mastra-harness-factory.d.ts +19 -2
- package/dist/mastra-harness-factory.js +8 -4
- package/dist/mastra-harness.d.ts +154 -10
- package/dist/mastra-harness.js +407 -51
- package/dist/mastra-message-mapper.js +63 -1
- package/dist/mastra-stream-broker.d.ts +210 -0
- package/dist/mastra-stream-broker.js +563 -0
- package/dist/mcp-config-mapper.d.ts +4 -1
- package/dist/mcp-config-mapper.js +8 -2
- package/dist/model-config-factory.d.ts +13 -1
- package/dist/salesforce-llm-gateway.d.ts +20 -1
- package/dist/salesforce-llm-gateway.js +59 -10
- package/dist/tool-search.d.ts +0 -41
- package/dist/tool-search.js +0 -43
- package/package.json +4 -4
package/README.md
CHANGED
|
@@ -46,14 +46,15 @@ Linux and macOS release the handle eagerly; the retry options are no-ops on thos
|
|
|
46
46
|
|
|
47
47
|
### Core
|
|
48
48
|
|
|
49
|
-
| Export | Kind | Description
|
|
50
|
-
| ------------------------------------- | --------- |
|
|
51
|
-
| `MastraHarnessFactory` | class | `HarnessFactory` that produces a Mastra-backed `AgentHarness` bound to a storage root.
|
|
52
|
-
| `
|
|
53
|
-
| `
|
|
54
|
-
| `
|
|
55
|
-
| `
|
|
56
|
-
| `
|
|
49
|
+
| Export | Kind | Description |
|
|
50
|
+
| ------------------------------------- | --------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
51
|
+
| `MastraHarnessFactory` | class | `HarnessFactory` that produces a Mastra-backed `AgentHarness` bound to a storage root. |
|
|
52
|
+
| `MastraHarnessFactoryConfig` | interface | Configuration for `MastraHarnessFactory` (`modelConfigFactory?`, `toolApprovalTimeoutMs?`). |
|
|
53
|
+
| `MastraModelConfigFactory` | interface | Strategy for creating model configurations; injected into `MastraHarnessFactory`. |
|
|
54
|
+
| `ResolvedModelConfig` | type | Return type of `MastraModelConfigFactory.create()` — a `MastraModelConfig` plus a `validateFiles(files)` hook the harness calls for pre-flight multimodal (`image`/`file`) validation. |
|
|
55
|
+
| `DefaultMastraModelConfigFactory` | class | Default factory using the Salesforce LLM Gateway (`SalesforceMastraModelGateway`). |
|
|
56
|
+
| `LLMGExpressMastraModelConfigFactory` | class | Factory for LLM Gateway Express (API-key-authenticated, OpenAI-compatible endpoint). |
|
|
57
|
+
| `LLMGExpressConfig` | type | Configuration for `LLMGExpressMastraModelConfigFactory` (`apiKey`, `baseUrl`, `modelId`). |
|
|
57
58
|
|
|
58
59
|
### Extension surface
|
|
59
60
|
|
|
@@ -61,14 +62,16 @@ These types let consumers reach Mastra-specific features through the SDK's typed
|
|
|
61
62
|
`MastraAgentHarness` from `MastraHarnessFactory.create()`, so consumers usually don't reference these types explicitly —
|
|
62
63
|
they show up via inference at the call site.
|
|
63
64
|
|
|
64
|
-
| Export | Kind
|
|
65
|
-
| ------------------------ |
|
|
66
|
-
| `MastraAgentHarness` | type
|
|
67
|
-
| `MastraAgentConfig` | type
|
|
68
|
-
| `MastraToolSearchConfig` | type
|
|
69
|
-
| `
|
|
70
|
-
| `
|
|
71
|
-
|
|
65
|
+
| Export | Kind | Description |
|
|
66
|
+
| ------------------------ | ---- | ---------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
67
|
+
| `MastraAgentHarness` | type | Branded `AgentHarness` subtype; carries the Mastra-specific `extensions` namespace and the inferred config type. |
|
|
68
|
+
| `MastraAgentConfig` | type | `AgentConfig` extended with Mastra-only fields (currently `toolSearch`). Inferred at `manager.createAgent` automatically — annotation rarely needed. |
|
|
69
|
+
| `MastraToolSearchConfig` | type | Shape of `MastraAgentConfig.toolSearch` (`pool`, `alwaysActive`, `topK`, `ttl`). |
|
|
70
|
+
| `ToolSearchHandle` | type | Stable interface for the tool-search runtime: `id`, `getStateStats`, `clearState`, `clearAllState`, `cleanupNow`. Wraps Mastra's internal processor. |
|
|
71
|
+
| `SkillSearchHandle` | type | Stable interface for the skill-search runtime: `id` (Mastra's processor has no other public methods today; the harness owns lifecycle). |
|
|
72
|
+
|
|
73
|
+
The Mastra-specific accessors live on `manager.extensions.mastra` (`getToolSearchProcessor(agentId)`,
|
|
74
|
+
`getSkillSearchProcessor(agentId)`, `formatMcpToolName(serverName, toolName)`) and require no separate import.
|
|
72
75
|
|
|
73
76
|
#### Tool search
|
|
74
77
|
|
|
@@ -76,7 +79,7 @@ Hide a large tool catalog behind Mastra's `search_tools` / `load_tool` meta-tool
|
|
|
76
79
|
|
|
77
80
|
```ts
|
|
78
81
|
import { createAgentManager } from '@salesforce/sfdx-agent-sdk';
|
|
79
|
-
import { MastraHarnessFactory
|
|
82
|
+
import { MastraHarnessFactory } from '@salesforce/sfdx-agent-harness-mastra';
|
|
80
83
|
|
|
81
84
|
const manager = await createAgentManager(storageRoot, new MastraHarnessFactory());
|
|
82
85
|
|
|
@@ -86,7 +89,14 @@ const agent = await manager.createAgent(projectRoot, {
|
|
|
86
89
|
mcpServers: { sfdx: { type: 'stdio', command: 'npx', args: ['@salesforce/mcp'] } },
|
|
87
90
|
toolSearch: {
|
|
88
91
|
pool: '*', // or an explicit name list
|
|
89
|
-
alwaysActive: [
|
|
92
|
+
alwaysActive: [
|
|
93
|
+
'lookup_account',
|
|
94
|
+
// Build the Mastra-specific namespaced name for an MCP tool that hasn't
|
|
95
|
+
// been discovered yet. The output format is harness-specific
|
|
96
|
+
// (Mastra: `${server}_${tool}`); for cross-harness tool identification
|
|
97
|
+
// anywhere else, prefer the `(serverName, toolName)` pair on `McpToolInfo`.
|
|
98
|
+
manager.extensions.mastra.formatMcpToolName('sfdx', 'deploy_metadata'),
|
|
99
|
+
],
|
|
90
100
|
topK: 5, // advisory; defaults to Mastra's 5
|
|
91
101
|
ttl: 3_600_000, // ms; advisory; defaults to Mastra's 1h
|
|
92
102
|
},
|
|
@@ -151,19 +161,55 @@ for await (const event of result.eventStream) {
|
|
|
151
161
|
}
|
|
152
162
|
```
|
|
153
163
|
|
|
164
|
+
### Tool approval timeout
|
|
165
|
+
|
|
166
|
+
When `requireToolApproval: true` is set on a `chat()` call, the harness suspends the workflow on each
|
|
167
|
+
`tool-approval-request` and waits for the consumer to call `approveToolCall(...)` / `declineToolCall(...)` /
|
|
168
|
+
`submitToolResult(...)`. To bound how long a pending approval can wait — for example, when a UI process crashes or a
|
|
169
|
+
user walks away — the factory accepts a `toolApprovalTimeoutMs` option. It defaults to `600_000` (10 minutes) and
|
|
170
|
+
matches the `ClaudeHarnessFactoryConfig` knob of the same name.
|
|
171
|
+
|
|
172
|
+
```ts
|
|
173
|
+
const harnessFactory = new MastraHarnessFactory({
|
|
174
|
+
toolApprovalTimeoutMs: 60_000, // auto-deny pending approvals after 60s
|
|
175
|
+
});
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
When the timer fires, the harness aborts the suspended Mastra run, drops the `activeRuns` entry for the thread, and
|
|
179
|
+
yields a synthetic terminal pair on the active `eventStream`:
|
|
180
|
+
|
|
181
|
+
```ts
|
|
182
|
+
{ type: 'error', error: Error('Tool approval timed out after 60000ms.'), code: 'tool-approval-timeout' }
|
|
183
|
+
{ type: 'finish', finishReason: 'error' }
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
Subsequent `approveToolCall` / `declineToolCall` / `submitToolResult` calls for the timed-out tool reject with
|
|
187
|
+
`no active run found for thread "<id>"`. The granularity is per thread — each suspended `ActiveRun` arms its own timer
|
|
188
|
+
because Mastra suspends one tool approval at a time per thread; multi-tool turns get a fresh timer with each
|
|
189
|
+
continuation. To observe the timeout, keep iterating the `eventStream` past the `tool-approval-request` event so the
|
|
190
|
+
synthetic terminal pair lands in your loop:
|
|
191
|
+
|
|
192
|
+
```ts
|
|
193
|
+
for await (const event of result.eventStream) {
|
|
194
|
+
if (event.type === 'error' && event.code === 'tool-approval-timeout') {
|
|
195
|
+
// Pending approval was never answered.
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
```
|
|
199
|
+
|
|
154
200
|
### Using LLM Gateway Express
|
|
155
201
|
|
|
156
202
|
```ts
|
|
157
203
|
import { createAgentManager } from '@salesforce/sfdx-agent-sdk';
|
|
158
204
|
import { MastraHarnessFactory, LLMGExpressMastraModelConfigFactory } from '@salesforce/sfdx-agent-harness-mastra';
|
|
159
205
|
|
|
160
|
-
const harnessFactory = new MastraHarnessFactory(
|
|
161
|
-
new LLMGExpressMastraModelConfigFactory({
|
|
206
|
+
const harnessFactory = new MastraHarnessFactory({
|
|
207
|
+
modelConfigFactory: new LLMGExpressMastraModelConfigFactory({
|
|
162
208
|
apiKey: process.env.LLMG_EXPRESS_API_KEY!,
|
|
163
209
|
baseUrl: process.env.LLMG_EXPRESS_BASE_URL!,
|
|
164
210
|
modelId: 'claude-sonnet-4-20250514',
|
|
165
211
|
}),
|
|
166
|
-
);
|
|
212
|
+
});
|
|
167
213
|
|
|
168
214
|
const manager = await createAgentManager('/path/to/storage', harnessFactory);
|
|
169
215
|
```
|
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
import type
|
|
1
|
+
import { type LLMGatewayClient } from '@salesforce/llm-gateway-sdk';
|
|
2
2
|
import type { MastraModelConfigFactory, ResolvedModelConfig } from './model-config-factory.js';
|
|
3
3
|
/**
|
|
4
4
|
* Default model configuration factory that uses the Salesforce LLM Gateway.
|
|
5
5
|
*
|
|
6
6
|
* Wraps the LLMGatewayClient in a SalesforceMastraModelGateway and calls
|
|
7
7
|
* resolveLanguageModel() to produce the LanguageModelV2 that Mastra consumes.
|
|
8
|
+
* Captures the gateway model at creation time to provide multimodal validation.
|
|
8
9
|
*/
|
|
9
10
|
export declare class DefaultMastraModelConfigFactory implements MastraModelConfigFactory {
|
|
10
11
|
create(llmGatewayClient: LLMGatewayClient): ResolvedModelConfig;
|
|
@@ -2,17 +2,24 @@
|
|
|
2
2
|
* Copyright 2026, Salesforce, Inc. All rights reserved.
|
|
3
3
|
* See LICENSE.txt for license terms.
|
|
4
4
|
*/
|
|
5
|
+
import { validateMultimodalFiles } from '@salesforce/llm-gateway-sdk';
|
|
5
6
|
import { SalesforceMastraModelGateway } from './salesforce-llm-gateway.js';
|
|
6
7
|
/**
|
|
7
8
|
* Default model configuration factory that uses the Salesforce LLM Gateway.
|
|
8
9
|
*
|
|
9
10
|
* Wraps the LLMGatewayClient in a SalesforceMastraModelGateway and calls
|
|
10
11
|
* resolveLanguageModel() to produce the LanguageModelV2 that Mastra consumes.
|
|
12
|
+
* Captures the gateway model at creation time to provide multimodal validation.
|
|
11
13
|
*/
|
|
12
14
|
export class DefaultMastraModelConfigFactory {
|
|
13
15
|
create(llmGatewayClient) {
|
|
14
16
|
const agentGateway = new SalesforceMastraModelGateway(llmGatewayClient);
|
|
15
|
-
|
|
17
|
+
const model = agentGateway.resolveLanguageModel();
|
|
18
|
+
const gatewayModel = llmGatewayClient.getModel();
|
|
19
|
+
return {
|
|
20
|
+
model,
|
|
21
|
+
validateFiles: (files) => validateMultimodalFiles(files, gatewayModel),
|
|
22
|
+
};
|
|
16
23
|
}
|
|
17
24
|
}
|
|
18
25
|
//# sourceMappingURL=default-model-config-factory.js.map
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Buffered async generator wrapper used by `MastraStreamBroker` to deliver
|
|
3
|
+
* `ChatEvent`s to a consumer's `ChatStreamResult.eventStream`.
|
|
4
|
+
*
|
|
5
|
+
* The buffer holds events pushed before the consumer starts iterating, so the
|
|
6
|
+
* broker can begin populating the sink eagerly without coordinating with the
|
|
7
|
+
* consumer's `for await` loop. Events pushed after iteration starts unblock
|
|
8
|
+
* the awaiting consumer via an internal Promise waiter.
|
|
9
|
+
*
|
|
10
|
+
* Internal to `@salesforce/sfdx-agent-harness-mastra`; not part of the public
|
|
11
|
+
* harness surface. Mirrors the same primitive in `@salesforce/sfdx-agent-harness-claude`
|
|
12
|
+
* to keep each harness's broker self-contained without forcing a shared
|
|
13
|
+
* cross-package surface.
|
|
14
|
+
*/
|
|
15
|
+
export declare class GenSink<T> {
|
|
16
|
+
private readonly buffered;
|
|
17
|
+
private ended;
|
|
18
|
+
private waiter;
|
|
19
|
+
push(event: T): void;
|
|
20
|
+
end(): void;
|
|
21
|
+
generator(): AsyncGenerator<T, void>;
|
|
22
|
+
private wake;
|
|
23
|
+
}
|
package/dist/gen-sink.js
ADDED
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2026, Salesforce, Inc. All rights reserved.
|
|
3
|
+
* See LICENSE.txt for license terms.
|
|
4
|
+
*/
|
|
5
|
+
/**
|
|
6
|
+
* Buffered async generator wrapper used by `MastraStreamBroker` to deliver
|
|
7
|
+
* `ChatEvent`s to a consumer's `ChatStreamResult.eventStream`.
|
|
8
|
+
*
|
|
9
|
+
* The buffer holds events pushed before the consumer starts iterating, so the
|
|
10
|
+
* broker can begin populating the sink eagerly without coordinating with the
|
|
11
|
+
* consumer's `for await` loop. Events pushed after iteration starts unblock
|
|
12
|
+
* the awaiting consumer via an internal Promise waiter.
|
|
13
|
+
*
|
|
14
|
+
* Internal to `@salesforce/sfdx-agent-harness-mastra`; not part of the public
|
|
15
|
+
* harness surface. Mirrors the same primitive in `@salesforce/sfdx-agent-harness-claude`
|
|
16
|
+
* to keep each harness's broker self-contained without forcing a shared
|
|
17
|
+
* cross-package surface.
|
|
18
|
+
*/
|
|
19
|
+
export class GenSink {
|
|
20
|
+
buffered = [];
|
|
21
|
+
ended = false;
|
|
22
|
+
waiter = null;
|
|
23
|
+
push(event) {
|
|
24
|
+
if (this.ended)
|
|
25
|
+
return;
|
|
26
|
+
this.buffered.push(event);
|
|
27
|
+
this.wake();
|
|
28
|
+
}
|
|
29
|
+
end() {
|
|
30
|
+
if (this.ended)
|
|
31
|
+
return;
|
|
32
|
+
this.ended = true;
|
|
33
|
+
this.wake();
|
|
34
|
+
}
|
|
35
|
+
async *generator() {
|
|
36
|
+
while (true) {
|
|
37
|
+
if (this.buffered.length > 0) {
|
|
38
|
+
yield this.buffered.shift();
|
|
39
|
+
continue;
|
|
40
|
+
}
|
|
41
|
+
if (this.ended)
|
|
42
|
+
return;
|
|
43
|
+
await new Promise((resolve) => {
|
|
44
|
+
this.waiter = { resolve };
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
wake() {
|
|
49
|
+
const w = this.waiter;
|
|
50
|
+
if (w) {
|
|
51
|
+
this.waiter = null;
|
|
52
|
+
w.resolve();
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=gen-sink.js.map
|
package/dist/index.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
export { MastraHarnessFactory } from './mastra-harness-factory.js';
|
|
1
|
+
export { MastraHarnessFactory, type MastraHarnessFactoryConfig } from './mastra-harness-factory.js';
|
|
2
2
|
export type { MastraAgentHarness } from './mastra-harness.js';
|
|
3
|
-
export { type MastraAgentConfig, type MastraToolSearchConfig, type SkillSearchHandle, type ToolSearchHandle,
|
|
3
|
+
export { type MastraAgentConfig, type MastraToolSearchConfig, type SkillSearchHandle, type ToolSearchHandle, } from './tool-search.js';
|
|
4
4
|
export type { MastraModelConfigFactory, ResolvedModelConfig } from './model-config-factory.js';
|
|
5
5
|
export { DefaultMastraModelConfigFactory } from './default-model-config-factory.js';
|
|
6
6
|
export { LLMGExpressMastraModelConfigFactory, type LLMGExpressConfig } from './llmg-express-model-config-factory.js';
|
package/dist/index.js
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
* See LICENSE.txt for license terms.
|
|
4
4
|
*/
|
|
5
5
|
export { MastraHarnessFactory } from './mastra-harness-factory.js';
|
|
6
|
-
export {
|
|
6
|
+
export {} from './tool-search.js';
|
|
7
7
|
export { DefaultMastraModelConfigFactory } from './default-model-config-factory.js';
|
|
8
8
|
export { LLMGExpressMastraModelConfigFactory } from './llmg-express-model-config-factory.js';
|
|
9
9
|
//# sourceMappingURL=index.js.map
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type
|
|
1
|
+
import { type LLMGatewayClient } from '@salesforce/llm-gateway-sdk';
|
|
2
2
|
import type { MastraModelConfigFactory, ResolvedModelConfig } from './model-config-factory.js';
|
|
3
3
|
export interface LLMGExpressConfig {
|
|
4
4
|
/** API key for authenticating with LLM Gateway Express. */
|
|
@@ -12,12 +12,14 @@ export interface LLMGExpressConfig {
|
|
|
12
12
|
* Model configuration factory for LLM Gateway Express (non-production,
|
|
13
13
|
* API-key-authenticated, OpenAI-compatible endpoint).
|
|
14
14
|
*
|
|
15
|
-
*
|
|
16
|
-
*
|
|
17
|
-
*
|
|
15
|
+
* Routing is via a Mastra OpenAICompatibleConfig that Mastra resolves
|
|
16
|
+
* internally using its built-in OpenAI-compatible provider support.
|
|
17
|
+
* Multimodal validation uses the gateway client's model as a proxy for
|
|
18
|
+
* the express endpoint's capabilities (the express endpoint does not
|
|
19
|
+
* publish its own file-format caps).
|
|
18
20
|
*/
|
|
19
21
|
export declare class LLMGExpressMastraModelConfigFactory implements MastraModelConfigFactory {
|
|
20
22
|
private readonly config;
|
|
21
23
|
constructor(config: LLMGExpressConfig);
|
|
22
|
-
create(
|
|
24
|
+
create(llmGatewayClient: LLMGatewayClient): ResolvedModelConfig;
|
|
23
25
|
}
|
|
@@ -2,27 +2,34 @@
|
|
|
2
2
|
* Copyright 2026, Salesforce, Inc. All rights reserved.
|
|
3
3
|
* See LICENSE.txt for license terms.
|
|
4
4
|
*/
|
|
5
|
+
import { validateMultimodalFiles } from '@salesforce/llm-gateway-sdk';
|
|
5
6
|
/**
|
|
6
7
|
* Model configuration factory for LLM Gateway Express (non-production,
|
|
7
8
|
* API-key-authenticated, OpenAI-compatible endpoint).
|
|
8
9
|
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
10
|
+
* Routing is via a Mastra OpenAICompatibleConfig that Mastra resolves
|
|
11
|
+
* internally using its built-in OpenAI-compatible provider support.
|
|
12
|
+
* Multimodal validation uses the gateway client's model as a proxy for
|
|
13
|
+
* the express endpoint's capabilities (the express endpoint does not
|
|
14
|
+
* publish its own file-format caps).
|
|
12
15
|
*/
|
|
13
16
|
export class LLMGExpressMastraModelConfigFactory {
|
|
14
17
|
config;
|
|
15
18
|
constructor(config) {
|
|
16
19
|
this.config = config;
|
|
17
20
|
}
|
|
18
|
-
create(
|
|
21
|
+
create(llmGatewayClient) {
|
|
19
22
|
const model = {
|
|
20
23
|
providerId: 'llmg-express',
|
|
21
24
|
modelId: this.config.modelId,
|
|
22
25
|
url: this.config.baseUrl,
|
|
23
26
|
apiKey: this.config.apiKey,
|
|
24
27
|
};
|
|
25
|
-
|
|
28
|
+
const gatewayModel = llmGatewayClient.getModel();
|
|
29
|
+
return {
|
|
30
|
+
model,
|
|
31
|
+
validateFiles: (files) => validateMultimodalFiles(files, gatewayModel),
|
|
32
|
+
};
|
|
26
33
|
}
|
|
27
34
|
}
|
|
28
35
|
//# sourceMappingURL=llmg-express-model-config-factory.js.map
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { ChunkType } from '@mastra/core/stream';
|
|
2
|
-
import {
|
|
2
|
+
import type { LogBus } from '@salesforce/agentic-common';
|
|
3
3
|
import type { ChatEvent } from '@salesforce/sfdx-agent-sdk';
|
|
4
4
|
/**
|
|
5
5
|
* Adapts Mastra `ChunkType` stream events to our {@link ChatEvent} discriminated union.
|
|
@@ -2,7 +2,6 @@
|
|
|
2
2
|
* Copyright 2026, Salesforce, Inc. All rights reserved.
|
|
3
3
|
* See LICENSE.txt for license terms.
|
|
4
4
|
*/
|
|
5
|
-
import { getErrorMessage } from '@salesforce/agentic-common';
|
|
6
5
|
/**
|
|
7
6
|
* Adapts Mastra `ChunkType` stream events to our {@link ChatEvent} discriminated union.
|
|
8
7
|
*
|
|
@@ -103,14 +102,17 @@ export class MastraEventAdapter {
|
|
|
103
102
|
result: chunk.payload.result,
|
|
104
103
|
isError: false,
|
|
105
104
|
};
|
|
106
|
-
case 'tool-error':
|
|
105
|
+
case 'tool-error': {
|
|
106
|
+
const error = chunk.payload.error instanceof Error ? chunk.payload.error : new Error(String(chunk.payload.error));
|
|
107
107
|
return {
|
|
108
108
|
type: 'tool-result',
|
|
109
109
|
toolCallId: chunk.payload.toolCallId,
|
|
110
110
|
toolName: chunk.payload.toolName,
|
|
111
|
-
result:
|
|
111
|
+
result: error.message,
|
|
112
112
|
isError: true,
|
|
113
|
+
error,
|
|
113
114
|
};
|
|
115
|
+
}
|
|
114
116
|
case 'step-start':
|
|
115
117
|
return { type: 'step-start', stepIndex: this.stepIndex++ };
|
|
116
118
|
case 'step-finish':
|
|
@@ -199,6 +201,7 @@ function mapUsage(usage) {
|
|
|
199
201
|
totalTokens: usage.totalTokens ?? undefined,
|
|
200
202
|
reasoningTokens: usage.reasoningTokens,
|
|
201
203
|
cachedInputTokens: usage.cachedInputTokens,
|
|
204
|
+
cacheWriteInputTokens: usage.cacheCreationInputTokens ? usage.cacheCreationInputTokens : undefined,
|
|
202
205
|
};
|
|
203
206
|
}
|
|
204
207
|
//# sourceMappingURL=mastra-event-adapter.js.map
|
|
@@ -1,11 +1,28 @@
|
|
|
1
1
|
import type { HarnessFactory } from '@salesforce/sfdx-agent-sdk';
|
|
2
2
|
import { type MastraAgentHarness } from './mastra-harness.js';
|
|
3
3
|
import type { MastraModelConfigFactory } from './model-config-factory.js';
|
|
4
|
+
export interface MastraHarnessFactoryConfig {
|
|
5
|
+
/**
|
|
6
|
+
* Strategy for resolving the Mastra model configuration. Defaults to
|
|
7
|
+
* `DefaultMastraModelConfigFactory`, which targets the standard LLM
|
|
8
|
+
* Gateway path.
|
|
9
|
+
*/
|
|
10
|
+
modelConfigFactory?: MastraModelConfigFactory;
|
|
11
|
+
/**
|
|
12
|
+
* How long to wait for a `requireToolApproval` consumer to call
|
|
13
|
+
* `approveToolCall` / `declineToolCall` before auto-denying via
|
|
14
|
+
* `agent.abortRunStream(...)` and yielding a synthetic `error`
|
|
15
|
+
* (`code: 'tool-approval-timeout'`) + `finish` (`finishReason: 'error'`)
|
|
16
|
+
* terminal pair. Defaults to `600_000` (10 minutes), matching
|
|
17
|
+
* `ClaudeHarnessFactoryConfig.toolApprovalTimeoutMs`.
|
|
18
|
+
*/
|
|
19
|
+
toolApprovalTimeoutMs?: number;
|
|
20
|
+
}
|
|
4
21
|
/** Mastra-backed factory for creating AgentHarness instances. */
|
|
5
22
|
export declare class MastraHarnessFactory implements HarnessFactory<MastraAgentHarness> {
|
|
6
|
-
private readonly
|
|
23
|
+
private readonly config;
|
|
7
24
|
readonly harnessId = "mastra";
|
|
8
25
|
readonly protocolVersion = 1;
|
|
9
|
-
constructor(
|
|
26
|
+
constructor(config?: MastraHarnessFactoryConfig);
|
|
10
27
|
create(storageRootFolder: string): Promise<MastraAgentHarness>;
|
|
11
28
|
}
|
|
@@ -3,16 +3,20 @@
|
|
|
3
3
|
* See LICENSE.txt for license terms.
|
|
4
4
|
*/
|
|
5
5
|
import { MastraHarness } from './mastra-harness.js';
|
|
6
|
+
const DEFAULT_TOOL_APPROVAL_TIMEOUT_MS = 600_000;
|
|
6
7
|
/** Mastra-backed factory for creating AgentHarness instances. */
|
|
7
8
|
export class MastraHarnessFactory {
|
|
8
|
-
|
|
9
|
+
config;
|
|
9
10
|
harnessId = 'mastra';
|
|
10
11
|
protocolVersion = 1;
|
|
11
|
-
constructor(
|
|
12
|
-
this.
|
|
12
|
+
constructor(config = {}) {
|
|
13
|
+
this.config = config;
|
|
13
14
|
}
|
|
14
15
|
async create(storageRootFolder) {
|
|
15
|
-
return new MastraHarness(storageRootFolder,
|
|
16
|
+
return new MastraHarness(storageRootFolder, {
|
|
17
|
+
modelConfigFactory: this.config.modelConfigFactory,
|
|
18
|
+
toolApprovalTimeoutMs: this.config.toolApprovalTimeoutMs ?? DEFAULT_TOOL_APPROVAL_TIMEOUT_MS,
|
|
19
|
+
});
|
|
16
20
|
}
|
|
17
21
|
}
|
|
18
22
|
//# sourceMappingURL=mastra-harness-factory.js.map
|