@sensigo/realm-cli 0.1.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 +109 -0
- package/dist/agent/agent-utils.d.ts +27 -0
- package/dist/agent/agent-utils.d.ts.map +1 -0
- package/dist/agent/agent-utils.js +79 -0
- package/dist/agent/agent-utils.js.map +1 -0
- package/dist/agent/anthropic-provider.d.ts +23 -0
- package/dist/agent/anthropic-provider.d.ts.map +1 -0
- package/dist/agent/anthropic-provider.js +245 -0
- package/dist/agent/anthropic-provider.js.map +1 -0
- package/dist/agent/gate/slack-gate-notifier.d.ts +80 -0
- package/dist/agent/gate/slack-gate-notifier.d.ts.map +1 -0
- package/dist/agent/gate/slack-gate-notifier.js +315 -0
- package/dist/agent/gate/slack-gate-notifier.js.map +1 -0
- package/dist/agent/gate/slack-gate-server.d.ts +30 -0
- package/dist/agent/gate/slack-gate-server.d.ts.map +1 -0
- package/dist/agent/gate/slack-gate-server.js +99 -0
- package/dist/agent/gate/slack-gate-server.js.map +1 -0
- package/dist/agent/gate/slack-socket-client.d.ts +20 -0
- package/dist/agent/gate/slack-socket-client.d.ts.map +1 -0
- package/dist/agent/gate/slack-socket-client.js +141 -0
- package/dist/agent/gate/slack-socket-client.js.map +1 -0
- package/dist/agent/gate-intent-interpreter.d.ts +29 -0
- package/dist/agent/gate-intent-interpreter.d.ts.map +1 -0
- package/dist/agent/gate-intent-interpreter.js +33 -0
- package/dist/agent/gate-intent-interpreter.js.map +1 -0
- package/dist/agent/index.d.ts +4 -0
- package/dist/agent/index.d.ts.map +1 -0
- package/dist/agent/index.js +4 -0
- package/dist/agent/index.js.map +1 -0
- package/dist/agent/llm-provider.d.ts +46 -0
- package/dist/agent/llm-provider.d.ts.map +1 -0
- package/dist/agent/llm-provider.js +55 -0
- package/dist/agent/llm-provider.js.map +1 -0
- package/dist/agent/mcp/mcp-client.d.ts +18 -0
- package/dist/agent/mcp/mcp-client.d.ts.map +1 -0
- package/dist/agent/mcp/mcp-client.js +108 -0
- package/dist/agent/mcp/mcp-client.js.map +1 -0
- package/dist/agent/mcp/mcp-extensions.d.ts +40 -0
- package/dist/agent/mcp/mcp-extensions.d.ts.map +1 -0
- package/dist/agent/mcp/mcp-extensions.js +2 -0
- package/dist/agent/mcp/mcp-extensions.js.map +1 -0
- package/dist/agent/mcp-client.d.ts +18 -0
- package/dist/agent/mcp-client.d.ts.map +1 -0
- package/dist/agent/mcp-client.js +108 -0
- package/dist/agent/mcp-client.js.map +1 -0
- package/dist/agent/mcp-types.d.ts +40 -0
- package/dist/agent/mcp-types.d.ts.map +1 -0
- package/dist/agent/mcp-types.js +2 -0
- package/dist/agent/mcp-types.js.map +1 -0
- package/dist/agent/openai-provider.d.ts +30 -0
- package/dist/agent/openai-provider.d.ts.map +1 -0
- package/dist/agent/openai-provider.js +253 -0
- package/dist/agent/openai-provider.js.map +1 -0
- package/dist/agent/openai-reasoning-provider.d.ts +18 -0
- package/dist/agent/openai-reasoning-provider.d.ts.map +1 -0
- package/dist/agent/openai-reasoning-provider.js +76 -0
- package/dist/agent/openai-reasoning-provider.js.map +1 -0
- package/dist/agent/preflight.d.ts +36 -0
- package/dist/agent/preflight.d.ts.map +1 -0
- package/dist/agent/preflight.js +81 -0
- package/dist/agent/preflight.js.map +1 -0
- package/dist/agent/providers/agent-utils.d.ts +27 -0
- package/dist/agent/providers/agent-utils.d.ts.map +1 -0
- package/dist/agent/providers/agent-utils.js +79 -0
- package/dist/agent/providers/agent-utils.js.map +1 -0
- package/dist/agent/providers/anthropic-provider.d.ts +23 -0
- package/dist/agent/providers/anthropic-provider.d.ts.map +1 -0
- package/dist/agent/providers/anthropic-provider.js +257 -0
- package/dist/agent/providers/anthropic-provider.js.map +1 -0
- package/dist/agent/providers/llm-provider.d.ts +46 -0
- package/dist/agent/providers/llm-provider.d.ts.map +1 -0
- package/dist/agent/providers/llm-provider.js +56 -0
- package/dist/agent/providers/llm-provider.js.map +1 -0
- package/dist/agent/providers/openai-provider.d.ts +30 -0
- package/dist/agent/providers/openai-provider.d.ts.map +1 -0
- package/dist/agent/providers/openai-provider.js +253 -0
- package/dist/agent/providers/openai-provider.js.map +1 -0
- package/dist/agent/providers/openai-reasoning-provider.d.ts +19 -0
- package/dist/agent/providers/openai-reasoning-provider.d.ts.map +1 -0
- package/dist/agent/providers/openai-reasoning-provider.js +89 -0
- package/dist/agent/providers/openai-reasoning-provider.js.map +1 -0
- package/dist/agent/run-agent.d.ts +50 -0
- package/dist/agent/run-agent.d.ts.map +1 -0
- package/dist/agent/run-agent.js +327 -0
- package/dist/agent/run-agent.js.map +1 -0
- package/dist/agent/slack-gate-notifier.d.ts +80 -0
- package/dist/agent/slack-gate-notifier.d.ts.map +1 -0
- package/dist/agent/slack-gate-notifier.js +315 -0
- package/dist/agent/slack-gate-notifier.js.map +1 -0
- package/dist/agent/slack-gate-poller.d.ts +28 -0
- package/dist/agent/slack-gate-poller.d.ts.map +1 -0
- package/dist/agent/slack-gate-poller.js +66 -0
- package/dist/agent/slack-gate-poller.js.map +1 -0
- package/dist/agent/slack-gate-server.d.ts +30 -0
- package/dist/agent/slack-gate-server.d.ts.map +1 -0
- package/dist/agent/slack-gate-server.js +99 -0
- package/dist/agent/slack-gate-server.js.map +1 -0
- package/dist/agent/slack-socket-client.d.ts +20 -0
- package/dist/agent/slack-socket-client.d.ts.map +1 -0
- package/dist/agent/slack-socket-client.js +141 -0
- package/dist/agent/slack-socket-client.js.map +1 -0
- package/dist/commands/agent.d.ts +3 -0
- package/dist/commands/agent.d.ts.map +1 -0
- package/dist/commands/agent.js +183 -0
- package/dist/commands/agent.js.map +1 -0
- package/dist/commands/cleanup.d.ts +16 -0
- package/dist/commands/cleanup.d.ts.map +1 -0
- package/dist/commands/cleanup.js +79 -0
- package/dist/commands/cleanup.js.map +1 -0
- package/dist/commands/diff.d.ts +41 -0
- package/dist/commands/diff.d.ts.map +1 -0
- package/dist/commands/diff.js +203 -0
- package/dist/commands/diff.js.map +1 -0
- package/dist/commands/init.d.ts +10 -0
- package/dist/commands/init.d.ts.map +1 -0
- package/dist/commands/init.js +97 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/inspect.d.ts +14 -0
- package/dist/commands/inspect.d.ts.map +1 -0
- package/dist/commands/inspect.js +224 -0
- package/dist/commands/inspect.js.map +1 -0
- package/dist/commands/list.d.ts +18 -0
- package/dist/commands/list.d.ts.map +1 -0
- package/dist/commands/list.js +88 -0
- package/dist/commands/list.js.map +1 -0
- package/dist/commands/mcp.d.ts +8 -0
- package/dist/commands/mcp.d.ts.map +1 -0
- package/dist/commands/mcp.js +22 -0
- package/dist/commands/mcp.js.map +1 -0
- package/dist/commands/migrate.d.ts +3 -0
- package/dist/commands/migrate.d.ts.map +1 -0
- package/dist/commands/migrate.js +42 -0
- package/dist/commands/migrate.js.map +1 -0
- package/dist/commands/register.d.ts +6 -0
- package/dist/commands/register.d.ts.map +1 -0
- package/dist/commands/register.js +51 -0
- package/dist/commands/register.js.map +1 -0
- package/dist/commands/replay-format.d.ts +3 -0
- package/dist/commands/replay-format.d.ts.map +1 -0
- package/dist/commands/replay-format.js +10 -0
- package/dist/commands/replay-format.js.map +1 -0
- package/dist/commands/replay.d.ts +38 -0
- package/dist/commands/replay.d.ts.map +1 -0
- package/dist/commands/replay.js +173 -0
- package/dist/commands/replay.js.map +1 -0
- package/dist/commands/respond.d.ts +20 -0
- package/dist/commands/respond.d.ts.map +1 -0
- package/dist/commands/respond.js +49 -0
- package/dist/commands/respond.js.map +1 -0
- package/dist/commands/resume.d.ts +15 -0
- package/dist/commands/resume.d.ts.map +1 -0
- package/dist/commands/resume.js +63 -0
- package/dist/commands/resume.js.map +1 -0
- package/dist/commands/run.d.ts +3 -0
- package/dist/commands/run.d.ts.map +1 -0
- package/dist/commands/run.js +127 -0
- package/dist/commands/run.js.map +1 -0
- package/dist/commands/serve.d.ts +33 -0
- package/dist/commands/serve.d.ts.map +1 -0
- package/dist/commands/serve.js +144 -0
- package/dist/commands/serve.js.map +1 -0
- package/dist/commands/test.d.ts +12 -0
- package/dist/commands/test.d.ts.map +1 -0
- package/dist/commands/test.js +58 -0
- package/dist/commands/test.js.map +1 -0
- package/dist/commands/validate.d.ts +3 -0
- package/dist/commands/validate.d.ts.map +1 -0
- package/dist/commands/validate.js +35 -0
- package/dist/commands/validate.js.map +1 -0
- package/dist/commands/watch.d.ts +18 -0
- package/dist/commands/watch.d.ts.map +1 -0
- package/dist/commands/watch.js +112 -0
- package/dist/commands/watch.js.map +1 -0
- package/dist/commands/webhook.d.ts +51 -0
- package/dist/commands/webhook.d.ts.map +1 -0
- package/dist/commands/webhook.js +227 -0
- package/dist/commands/webhook.js.map +1 -0
- package/dist/commands-registry.d.ts +7 -0
- package/dist/commands-registry.d.ts.map +1 -0
- package/dist/commands-registry.js +44 -0
- package/dist/commands-registry.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +21 -0
- package/dist/index.js.map +1 -0
- package/dist/store/replay-store.d.ts +29 -0
- package/dist/store/replay-store.d.ts.map +1 -0
- package/dist/store/replay-store.js +31 -0
- package/dist/store/replay-store.js.map +1 -0
- package/package.json +83 -0
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import type { LlmProvider } from './llm-provider.js';
|
|
2
|
+
/** Structured output from LLM interpretation of a gate reply. */
|
|
3
|
+
export interface GateInterpretation {
|
|
4
|
+
/** One of the allowed gate choices, or 'unclear' when intent cannot be determined. */
|
|
5
|
+
choice: string | 'unclear';
|
|
6
|
+
/** Confidence in the interpretation. */
|
|
7
|
+
confidence: 'high' | 'medium' | 'low';
|
|
8
|
+
/** Brief explanation of the interpretation reasoning. */
|
|
9
|
+
reason: string;
|
|
10
|
+
}
|
|
11
|
+
export interface InterpretGateIntentOptions {
|
|
12
|
+
/** Raw message text from the Slack thread. */
|
|
13
|
+
userMessage: string;
|
|
14
|
+
/** The gate's valid choices (e.g. ['send', 'reject']). */
|
|
15
|
+
allowedChoices: string[];
|
|
16
|
+
/** Name of the gate step for context. */
|
|
17
|
+
gateStepName: string;
|
|
18
|
+
/** Optional headline from the gate preview — provides brief context without overwhelming the prompt. */
|
|
19
|
+
previewSummary?: string;
|
|
20
|
+
/** LLM provider to use — same instance configured for the agent run. */
|
|
21
|
+
llmClient: LlmProvider;
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Asks the LLM to interpret a human's Slack reply as one of the allowed gate choices.
|
|
25
|
+
* Returns a structured interpretation with confidence level and reasoning.
|
|
26
|
+
* The LLM is solely responsible for understanding intent — no hardcoded synonyms.
|
|
27
|
+
*/
|
|
28
|
+
export declare function interpretGateIntent(options: InterpretGateIntentOptions): Promise<GateInterpretation>;
|
|
29
|
+
//# sourceMappingURL=gate-intent-interpreter.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gate-intent-interpreter.d.ts","sourceRoot":"","sources":["../../src/agent/gate-intent-interpreter.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD,iEAAiE;AACjE,MAAM,WAAW,kBAAkB;IACjC,sFAAsF;IACtF,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;IAC3B,wCAAwC;IACxC,UAAU,EAAE,MAAM,GAAG,QAAQ,GAAG,KAAK,CAAC;IACtC,yDAAyD;IACzD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,0BAA0B;IACzC,8CAA8C;IAC9C,WAAW,EAAE,MAAM,CAAC;IACpB,0DAA0D;IAC1D,cAAc,EAAE,MAAM,EAAE,CAAC;IACzB,yCAAyC;IACzC,YAAY,EAAE,MAAM,CAAC;IACrB,wGAAwG;IACxG,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,wEAAwE;IACxE,SAAS,EAAE,WAAW,CAAC;CACxB;AAED;;;;GAIG;AACH,wBAAsB,mBAAmB,CACvC,OAAO,EAAE,0BAA0B,GAClC,OAAO,CAAC,kBAAkB,CAAC,CAiC7B"}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Asks the LLM to interpret a human's Slack reply as one of the allowed gate choices.
|
|
3
|
+
* Returns a structured interpretation with confidence level and reasoning.
|
|
4
|
+
* The LLM is solely responsible for understanding intent — no hardcoded synonyms.
|
|
5
|
+
*/
|
|
6
|
+
export async function interpretGateIntent(options) {
|
|
7
|
+
const { userMessage, allowedChoices, gateStepName, previewSummary, llmClient } = options;
|
|
8
|
+
const contextLine = previewSummary !== undefined ? `\nGate context: ${previewSummary}` : '';
|
|
9
|
+
const choiceList = allowedChoices.map((c) => `"${c}"`).join(', ');
|
|
10
|
+
const prompt = `You are interpreting a Slack message from a human reviewer responding to a workflow gate.\n` +
|
|
11
|
+
`Gate step: "${gateStepName}"${contextLine}\n` +
|
|
12
|
+
`Allowed choices: ${allowedChoices.join(', ')}\n\n` +
|
|
13
|
+
`Message: "${userMessage}"\n\n` +
|
|
14
|
+
`Determine which choice the user intends. Return JSON with:\n` +
|
|
15
|
+
`- "choice": one of [${choiceList}, "unclear"]\n` +
|
|
16
|
+
`- "confidence": "high", "medium", or "low"\n` +
|
|
17
|
+
`- "reason": brief explanation of your interpretation`;
|
|
18
|
+
const schema = {
|
|
19
|
+
type: 'object',
|
|
20
|
+
required: ['choice', 'confidence', 'reason'],
|
|
21
|
+
properties: {
|
|
22
|
+
choice: { type: 'string' },
|
|
23
|
+
confidence: { type: 'string', enum: ['high', 'medium', 'low'] },
|
|
24
|
+
reason: { type: 'string' },
|
|
25
|
+
},
|
|
26
|
+
};
|
|
27
|
+
const result = await llmClient.callStep(prompt, schema);
|
|
28
|
+
const choice = result['choice'] ?? 'unclear';
|
|
29
|
+
const confidence = result['confidence'] ?? 'low';
|
|
30
|
+
const reason = result['reason'] ?? '';
|
|
31
|
+
return { choice, confidence, reason };
|
|
32
|
+
}
|
|
33
|
+
//# sourceMappingURL=gate-intent-interpreter.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gate-intent-interpreter.js","sourceRoot":"","sources":["../../src/agent/gate-intent-interpreter.ts"],"names":[],"mappings":"AA0BA;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,mBAAmB,CACvC,OAAmC;IAEnC,MAAM,EAAE,WAAW,EAAE,cAAc,EAAE,YAAY,EAAE,cAAc,EAAE,SAAS,EAAE,GAAG,OAAO,CAAC;IAEzF,MAAM,WAAW,GAAG,cAAc,KAAK,SAAS,CAAC,CAAC,CAAC,mBAAmB,cAAc,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;IAC5F,MAAM,UAAU,GAAG,cAAc,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAElE,MAAM,MAAM,GACV,6FAA6F;QAC7F,eAAe,YAAY,IAAI,WAAW,IAAI;QAC9C,oBAAoB,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,MAAM;QACnD,aAAa,WAAW,OAAO;QAC/B,8DAA8D;QAC9D,uBAAuB,UAAU,gBAAgB;QACjD,8CAA8C;QAC9C,sDAAsD,CAAC;IAEzD,MAAM,MAAM,GAAG;QACb,IAAI,EAAE,QAAQ;QACd,QAAQ,EAAE,CAAC,QAAQ,EAAE,YAAY,EAAE,QAAQ,CAAC;QAC5C,UAAU,EAAE;YACV,MAAM,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;YAC1B,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,QAAQ,EAAE,KAAK,CAAC,EAAE;YAC/D,MAAM,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;SAC3B;KACF,CAAC;IAEF,MAAM,MAAM,GAAG,MAAM,SAAS,CAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAExD,MAAM,MAAM,GAAI,MAAM,CAAC,QAAQ,CAAwB,IAAI,SAAS,CAAC;IACrE,MAAM,UAAU,GAAI,MAAM,CAAC,YAAY,CAA2C,IAAI,KAAK,CAAC;IAC5F,MAAM,MAAM,GAAI,MAAM,CAAC,QAAQ,CAAwB,IAAI,EAAE,CAAC;IAE9D,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,EAAE,CAAC;AACxC,CAAC"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
export { LlmProvider, ToolCapableLlmProvider } from './providers/llm-provider.js';
|
|
2
|
+
export type { ProviderCapabilities } from './providers/llm-provider.js';
|
|
3
|
+
export type { ToolExecutor, StepWithToolsResult, ToolCallRecord, McpServerConfig, } from './mcp/mcp-extensions.js';
|
|
4
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/agent/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,WAAW,EAAE,sBAAsB,EAAE,MAAM,6BAA6B,CAAC;AAClF,YAAY,EAAE,oBAAoB,EAAE,MAAM,6BAA6B,CAAC;AACxE,YAAY,EACV,YAAY,EACZ,mBAAmB,EACnB,cAAc,EACd,eAAe,GAChB,MAAM,yBAAyB,CAAC"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
// Public agent interface surface for @sensigo/realm-cli/agent.
|
|
2
|
+
// Custom provider authors implement LlmProvider or ToolCapableLlmProvider against these types.
|
|
3
|
+
export { LlmProvider, ToolCapableLlmProvider } from './providers/llm-provider.js';
|
|
4
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/agent/index.ts"],"names":[],"mappings":"AAAA,+DAA+D;AAC/D,+FAA+F;AAC/F,OAAO,EAAE,WAAW,EAAE,sBAAsB,EAAE,MAAM,6BAA6B,CAAC"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import type { ToolDefinition, ToolExecutor, StepWithToolsResult } from './mcp-types.js';
|
|
2
|
+
/**
|
|
3
|
+
* Describes the optional feature set that an LLM provider supports.
|
|
4
|
+
* Custom providers can override {@link LlmProvider.capabilities} to declare
|
|
5
|
+
* features beyond the universal baseline.
|
|
6
|
+
*/
|
|
7
|
+
export interface ProviderCapabilities {
|
|
8
|
+
/**
|
|
9
|
+
* Whether this provider sends `response_format: { type: 'json_object' }` in API requests.
|
|
10
|
+
* When false, JSON compliance is enforced through system prompt instruction and retry only.
|
|
11
|
+
* This is the universal baseline — all providers work without json_object mode.
|
|
12
|
+
*/
|
|
13
|
+
jsonMode: boolean;
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* Abstract base class for LLM providers used by realm agent.
|
|
17
|
+
* Extend this class to implement a custom provider.
|
|
18
|
+
*/
|
|
19
|
+
export declare abstract class LlmProvider {
|
|
20
|
+
/** Call the LLM with a step prompt and return a JSON object. */
|
|
21
|
+
abstract callStep(prompt: string, inputSchema?: Record<string, unknown>): Promise<Record<string, unknown>>;
|
|
22
|
+
/** Returns the capability set for this provider instance. */
|
|
23
|
+
capabilities(): ProviderCapabilities;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Extended abstract class for providers that support the agentic tool-calling loop.
|
|
27
|
+
* Extend this class if your provider can drive tool-enabled workflow steps.
|
|
28
|
+
*/
|
|
29
|
+
export declare abstract class ToolCapableLlmProvider extends LlmProvider {
|
|
30
|
+
abstract callStepWithTools(prompt: string, tools: ToolDefinition[], executor: ToolExecutor, options: {
|
|
31
|
+
inputSchema?: Record<string, unknown>;
|
|
32
|
+
maxToolCalls?: number;
|
|
33
|
+
toolTimeoutMs?: number;
|
|
34
|
+
}): Promise<StepWithToolsResult>;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Returns true if the provider supports the agentic tool-calling loop.
|
|
38
|
+
*/
|
|
39
|
+
export declare function isToolCapable(provider: LlmProvider): provider is ToolCapableLlmProvider;
|
|
40
|
+
export type ProviderName = 'openai' | 'anthropic';
|
|
41
|
+
/**
|
|
42
|
+
* Resolves the correct LLM provider from environment and CLI flags.
|
|
43
|
+
* Throws if no API key is found or the specified package is not installed.
|
|
44
|
+
*/
|
|
45
|
+
export declare function resolveProvider(providerFlag: ProviderName | undefined, modelFlag: string | undefined, baseUrlFlag?: string): Promise<LlmProvider>;
|
|
46
|
+
//# sourceMappingURL=llm-provider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"llm-provider.d.ts","sourceRoot":"","sources":["../../src/agent/llm-provider.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAE,YAAY,EAAE,mBAAmB,EAAE,MAAM,gBAAgB,CAAC;AAExF;;;;GAIG;AACH,MAAM,WAAW,oBAAoB;IACnC;;;;OAIG;IACH,QAAQ,EAAE,OAAO,CAAC;CACnB;AAED;;;GAGG;AACH,8BAAsB,WAAW;IAC/B,gEAAgE;IAChE,QAAQ,CAAC,QAAQ,CACf,MAAM,EAAE,MAAM,EACd,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACpC,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAEnC,6DAA6D;IAC7D,YAAY,IAAI,oBAAoB;CAGrC;AAED;;;GAGG;AACH,8BAAsB,sBAAuB,SAAQ,WAAW;IAC9D,QAAQ,CAAC,iBAAiB,CACxB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,cAAc,EAAE,EACvB,QAAQ,EAAE,YAAY,EACtB,OAAO,EAAE;QACP,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;QACtC,YAAY,CAAC,EAAE,MAAM,CAAC;QACtB,aAAa,CAAC,EAAE,MAAM,CAAC;KACxB,GACA,OAAO,CAAC,mBAAmB,CAAC;CAChC;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,WAAW,GAAG,QAAQ,IAAI,sBAAsB,CAEvF;AAED,MAAM,MAAM,YAAY,GAAG,QAAQ,GAAG,WAAW,CAAC;AAElD;;;GAGG;AACH,wBAAsB,eAAe,CACnC,YAAY,EAAE,YAAY,GAAG,SAAS,EACtC,SAAS,EAAE,MAAM,GAAG,SAAS,EAC7B,WAAW,CAAC,EAAE,MAAM,GACnB,OAAO,CAAC,WAAW,CAAC,CAkCtB"}
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Abstract base class for LLM providers used by realm agent.
|
|
3
|
+
* Extend this class to implement a custom provider.
|
|
4
|
+
*/
|
|
5
|
+
export class LlmProvider {
|
|
6
|
+
/** Returns the capability set for this provider instance. */
|
|
7
|
+
capabilities() {
|
|
8
|
+
return { jsonMode: false };
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Extended abstract class for providers that support the agentic tool-calling loop.
|
|
13
|
+
* Extend this class if your provider can drive tool-enabled workflow steps.
|
|
14
|
+
*/
|
|
15
|
+
export class ToolCapableLlmProvider extends LlmProvider {
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Returns true if the provider supports the agentic tool-calling loop.
|
|
19
|
+
*/
|
|
20
|
+
export function isToolCapable(provider) {
|
|
21
|
+
return provider instanceof ToolCapableLlmProvider;
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Resolves the correct LLM provider from environment and CLI flags.
|
|
25
|
+
* Throws if no API key is found or the specified package is not installed.
|
|
26
|
+
*/
|
|
27
|
+
export async function resolveProvider(providerFlag, modelFlag, baseUrlFlag) {
|
|
28
|
+
const hasOpenAI = process.env['OPENAI_API_KEY'] !== undefined;
|
|
29
|
+
const hasAnthropic = process.env['ANTHROPIC_API_KEY'] !== undefined;
|
|
30
|
+
if (!hasOpenAI && !hasAnthropic) {
|
|
31
|
+
throw new Error('realm agent requires an LLM API key. Set OPENAI_API_KEY or ANTHROPIC_API_KEY.');
|
|
32
|
+
}
|
|
33
|
+
const provider = providerFlag ?? (hasOpenAI ? 'openai' : 'anthropic');
|
|
34
|
+
if (baseUrlFlag !== undefined && provider === 'anthropic') {
|
|
35
|
+
throw new Error('--base-url is only supported with --provider openai (or OpenAI-compatible endpoints). ' +
|
|
36
|
+
'For Anthropic, configure the endpoint via the ANTHROPIC_BASE_URL environment variable.');
|
|
37
|
+
}
|
|
38
|
+
if (provider === 'openai') {
|
|
39
|
+
// Match o1, o1-mini, o1-preview, o3, o3-mini, o4-mini, etc. The user has
|
|
40
|
+
// explicitly declared the model name, so matching on name is the correct
|
|
41
|
+
// signal here — not an internal allowlist.
|
|
42
|
+
const REASONING_MODELS = /^o[1-4](-|$)/i;
|
|
43
|
+
if (modelFlag !== undefined && REASONING_MODELS.test(modelFlag)) {
|
|
44
|
+
const { OpenAIReasoningProvider } = await import('./openai-reasoning-provider.js');
|
|
45
|
+
return new OpenAIReasoningProvider(modelFlag);
|
|
46
|
+
}
|
|
47
|
+
const { OpenAIProvider } = await import('./openai-provider.js');
|
|
48
|
+
return new OpenAIProvider(modelFlag ?? 'gpt-4o', baseUrlFlag);
|
|
49
|
+
}
|
|
50
|
+
else {
|
|
51
|
+
const { AnthropicProvider } = await import('./anthropic-provider.js');
|
|
52
|
+
return new AnthropicProvider(modelFlag ?? 'claude-sonnet-4-5');
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
//# sourceMappingURL=llm-provider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"llm-provider.js","sourceRoot":"","sources":["../../src/agent/llm-provider.ts"],"names":[],"mappings":"AAiBA;;;GAGG;AACH,MAAM,OAAgB,WAAW;IAO/B,6DAA6D;IAC7D,YAAY;QACV,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE,CAAC;IAC7B,CAAC;CACF;AAED;;;GAGG;AACH,MAAM,OAAgB,sBAAuB,SAAQ,WAAW;CAW/D;AAED;;GAEG;AACH,MAAM,UAAU,aAAa,CAAC,QAAqB;IACjD,OAAO,QAAQ,YAAY,sBAAsB,CAAC;AACpD,CAAC;AAID;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,eAAe,CACnC,YAAsC,EACtC,SAA6B,EAC7B,WAAoB;IAEpB,MAAM,SAAS,GAAG,OAAO,CAAC,GAAG,CAAC,gBAAgB,CAAC,KAAK,SAAS,CAAC;IAC9D,MAAM,YAAY,GAAG,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAC,KAAK,SAAS,CAAC;IAEpE,IAAI,CAAC,SAAS,IAAI,CAAC,YAAY,EAAE,CAAC;QAChC,MAAM,IAAI,KAAK,CACb,+EAA+E,CAChF,CAAC;IACJ,CAAC;IAED,MAAM,QAAQ,GAAG,YAAY,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC;IAEtE,IAAI,WAAW,KAAK,SAAS,IAAI,QAAQ,KAAK,WAAW,EAAE,CAAC;QAC1D,MAAM,IAAI,KAAK,CACb,wFAAwF;YACtF,wFAAwF,CAC3F,CAAC;IACJ,CAAC;IAED,IAAI,QAAQ,KAAK,QAAQ,EAAE,CAAC;QAC1B,yEAAyE;QACzE,yEAAyE;QACzE,2CAA2C;QAC3C,MAAM,gBAAgB,GAAG,eAAe,CAAC;QACzC,IAAI,SAAS,KAAK,SAAS,IAAI,gBAAgB,CAAC,IAAI,CAAC,SAAS,CAAC,EAAE,CAAC;YAChE,MAAM,EAAE,uBAAuB,EAAE,GAAG,MAAM,MAAM,CAAC,gCAAgC,CAAC,CAAC;YACnF,OAAO,IAAI,uBAAuB,CAAC,SAAS,CAAC,CAAC;QAChD,CAAC;QACD,MAAM,EAAE,cAAc,EAAE,GAAG,MAAM,MAAM,CAAC,sBAAsB,CAAC,CAAC;QAChE,OAAO,IAAI,cAAc,CAAC,SAAS,IAAI,QAAQ,EAAE,WAAW,CAAC,CAAC;IAChE,CAAC;SAAM,CAAC;QACN,MAAM,EAAE,iBAAiB,EAAE,GAAG,MAAM,MAAM,CAAC,yBAAyB,CAAC,CAAC;QACtE,OAAO,IAAI,iBAAiB,CAAC,SAAS,IAAI,mBAAmB,CAAC,CAAC;IACjE,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { Client } from '@modelcontextprotocol/sdk/client';
|
|
2
|
+
import type { McpClient as IMcpClient, McpServerConfig, McpTool } from './mcp-extensions.js';
|
|
3
|
+
export declare class McpClient implements IMcpClient {
|
|
4
|
+
private readonly _servers;
|
|
5
|
+
private readonly _clients;
|
|
6
|
+
constructor(servers: McpServerConfig[], signal?: AbortSignal);
|
|
7
|
+
/**
|
|
8
|
+
* Creates and connects an SDK Client for the given config.
|
|
9
|
+
* Override in tests to inject an in-process transport and avoid spawning real subprocesses.
|
|
10
|
+
*/
|
|
11
|
+
protected _createClient(config: McpServerConfig, expandedEnv: Record<string, string>): Promise<Client>;
|
|
12
|
+
connect(serverId: string): Promise<void>;
|
|
13
|
+
getTools(serverId: string, allowList: string[]): Promise<McpTool[]>;
|
|
14
|
+
call(serverId: string, toolName: string, args: Record<string, unknown>): Promise<unknown>;
|
|
15
|
+
disconnect(): Promise<void>;
|
|
16
|
+
private _expandEnv;
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=mcp-client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-client.d.ts","sourceRoot":"","sources":["../../../src/agent/mcp/mcp-client.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,MAAM,EAAE,MAAM,kCAAkC,CAAC;AAG1D,OAAO,KAAK,EAAE,SAAS,IAAI,UAAU,EAAE,eAAe,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAC;AAE7F,qBAAa,SAAU,YAAW,UAAU;IAC1C,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAA+B;IACxD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAkC;gBAE/C,OAAO,EAAE,eAAe,EAAE,EAAE,MAAM,CAAC,EAAE,WAAW;IAc5D;;;OAGG;cACa,aAAa,CAC3B,MAAM,EAAE,eAAe,EACvB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAClC,OAAO,CAAC,MAAM,CAAC;IAqBZ,OAAO,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAqBxC,QAAQ,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC;IAanE,IAAI,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,OAAO,CAAC;IAMzF,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC;IAMjC,OAAO,CAAC,UAAU;CAmBnB"}
|
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
// mcp-client.ts — Manages stdio MCP server subprocess lifecycles.
|
|
2
|
+
// This is the only file in the codebase that imports @modelcontextprotocol/sdk directly.
|
|
3
|
+
import { Client } from '@modelcontextprotocol/sdk/client';
|
|
4
|
+
import { StdioClientTransport } from '@modelcontextprotocol/sdk/client/stdio.js';
|
|
5
|
+
import { WorkflowError } from '@sensigo/realm';
|
|
6
|
+
export class McpClient {
|
|
7
|
+
_servers;
|
|
8
|
+
_clients = new Map();
|
|
9
|
+
constructor(servers, signal) {
|
|
10
|
+
this._servers = new Map(servers.map((s) => [s.id, s]));
|
|
11
|
+
if (signal) {
|
|
12
|
+
// Register unconditionally — a signal that fires before first connect must still trigger cleanup.
|
|
13
|
+
signal.addEventListener('abort', () => {
|
|
14
|
+
void this.disconnect();
|
|
15
|
+
}, { once: true });
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Creates and connects an SDK Client for the given config.
|
|
20
|
+
* Override in tests to inject an in-process transport and avoid spawning real subprocesses.
|
|
21
|
+
*/
|
|
22
|
+
async _createClient(config, expandedEnv) {
|
|
23
|
+
const params = {
|
|
24
|
+
command: config.command ?? '',
|
|
25
|
+
...(config.args !== undefined ? { args: config.args } : {}),
|
|
26
|
+
...(Object.keys(expandedEnv).length > 0 ? { env: expandedEnv } : {}),
|
|
27
|
+
};
|
|
28
|
+
const transport = new StdioClientTransport(params);
|
|
29
|
+
const client = new Client({ name: 'realm-agent', version: '0.1.0' });
|
|
30
|
+
try {
|
|
31
|
+
await client.connect(transport);
|
|
32
|
+
}
|
|
33
|
+
catch (e) {
|
|
34
|
+
throw new WorkflowError(`MCP server '${config.id}': connection failed: ${String(e)}`, {
|
|
35
|
+
code: 'MCP_CONNECTION_FAILED',
|
|
36
|
+
category: 'ENGINE',
|
|
37
|
+
agentAction: 'stop',
|
|
38
|
+
retryable: false,
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
return client;
|
|
42
|
+
}
|
|
43
|
+
async connect(serverId) {
|
|
44
|
+
if (this._clients.has(serverId))
|
|
45
|
+
return;
|
|
46
|
+
const config = this._servers.get(serverId);
|
|
47
|
+
if (!config) {
|
|
48
|
+
throw new WorkflowError(`MCP server '${serverId}' is not configured`, {
|
|
49
|
+
code: 'MCP_CONNECTION_FAILED',
|
|
50
|
+
category: 'ENGINE',
|
|
51
|
+
agentAction: 'stop',
|
|
52
|
+
retryable: false,
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
const expandedEnv = this._expandEnv(serverId, config);
|
|
56
|
+
const client = await this._createClient(config, expandedEnv);
|
|
57
|
+
// Idempotency check after await — guards against concurrent connect() calls.
|
|
58
|
+
if (!this._clients.has(serverId)) {
|
|
59
|
+
this._clients.set(serverId, client);
|
|
60
|
+
}
|
|
61
|
+
else {
|
|
62
|
+
void client.close();
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
async getTools(serverId, allowList) {
|
|
66
|
+
await this.connect(serverId);
|
|
67
|
+
const client = this._clients.get(serverId);
|
|
68
|
+
const result = await client.listTools();
|
|
69
|
+
const tools = result.tools.map((t) => ({
|
|
70
|
+
name: t.name,
|
|
71
|
+
description: t.description ?? '',
|
|
72
|
+
inputSchema: t.inputSchema,
|
|
73
|
+
}));
|
|
74
|
+
if (allowList.length === 0)
|
|
75
|
+
return tools;
|
|
76
|
+
return tools.filter((t) => allowList.includes(t.name));
|
|
77
|
+
}
|
|
78
|
+
async call(serverId, toolName, args) {
|
|
79
|
+
await this.connect(serverId);
|
|
80
|
+
const client = this._clients.get(serverId);
|
|
81
|
+
return client.callTool({ name: toolName, arguments: args });
|
|
82
|
+
}
|
|
83
|
+
async disconnect() {
|
|
84
|
+
const clients = [...this._clients.values()];
|
|
85
|
+
this._clients.clear();
|
|
86
|
+
await Promise.allSettled(clients.map((c) => c.close()));
|
|
87
|
+
}
|
|
88
|
+
_expandEnv(serverId, config) {
|
|
89
|
+
const expanded = {};
|
|
90
|
+
for (const [key, value] of Object.entries(config.env ?? {})) {
|
|
91
|
+
const result = value.replace(/\$\{([^}]+)\}/g, (_match, varName) => {
|
|
92
|
+
const v = process.env[varName];
|
|
93
|
+
if (v === undefined) {
|
|
94
|
+
throw new WorkflowError(`MCP server '${serverId}': env var ${varName} is not set`, {
|
|
95
|
+
code: 'MCP_CONNECTION_FAILED',
|
|
96
|
+
category: 'ENGINE',
|
|
97
|
+
agentAction: 'stop',
|
|
98
|
+
retryable: false,
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
return v;
|
|
102
|
+
});
|
|
103
|
+
expanded[key] = result;
|
|
104
|
+
}
|
|
105
|
+
return expanded;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
//# sourceMappingURL=mcp-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-client.js","sourceRoot":"","sources":["../../../src/agent/mcp/mcp-client.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { ToolCallRecord, McpServerConfig } from '@sensigo/realm';
|
|
2
|
+
export type { ToolCallRecord, McpServerConfig };
|
|
3
|
+
export interface McpTool {
|
|
4
|
+
name: string;
|
|
5
|
+
description: string;
|
|
6
|
+
inputSchema: Record<string, unknown>;
|
|
7
|
+
}
|
|
8
|
+
export interface ToolDefinition {
|
|
9
|
+
id: string;
|
|
10
|
+
serverId: string;
|
|
11
|
+
name: string;
|
|
12
|
+
description: string;
|
|
13
|
+
inputSchema: Record<string, unknown>;
|
|
14
|
+
}
|
|
15
|
+
export type ToolExecutor = (toolName: string, args: Record<string, unknown>) => Promise<unknown>;
|
|
16
|
+
export interface StepWithToolsResult {
|
|
17
|
+
output: Record<string, unknown>;
|
|
18
|
+
toolCalls: ToolCallRecord[];
|
|
19
|
+
}
|
|
20
|
+
export interface McpClient {
|
|
21
|
+
/**
|
|
22
|
+
* Lazily connects to a server on first call. Idempotent.
|
|
23
|
+
* stdio failures throw WorkflowError(MCP_CONNECTION_FAILED, stop).
|
|
24
|
+
*/
|
|
25
|
+
connect(serverId: string): Promise<void>;
|
|
26
|
+
/**
|
|
27
|
+
* Returns tools from the specified server, filtered to the allow-list.
|
|
28
|
+
* Triggers lazy-connect on first call — the subprocess may spawn here.
|
|
29
|
+
*/
|
|
30
|
+
getTools(serverId: string, allowList: string[]): Promise<McpTool[]>;
|
|
31
|
+
/** Execute a tool on the specified server. */
|
|
32
|
+
call(serverId: string, toolName: string, args: Record<string, unknown>): Promise<unknown>;
|
|
33
|
+
/**
|
|
34
|
+
* Shut down all server connections. Idempotent — safe to call multiple times.
|
|
35
|
+
* Must be called in finally blocks.
|
|
36
|
+
* If constructed with an AbortSignal, also called automatically on abort.
|
|
37
|
+
*/
|
|
38
|
+
disconnect(): Promise<void>;
|
|
39
|
+
}
|
|
40
|
+
//# sourceMappingURL=mcp-extensions.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-extensions.d.ts","sourceRoot":"","sources":["../../../src/agent/mcp/mcp-extensions.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,cAAc,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AACtE,YAAY,EAAE,cAAc,EAAE,eAAe,EAAE,CAAC;AAGhD,MAAM,WAAW,OAAO;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACtC;AAGD,MAAM,WAAW,cAAc;IAC7B,EAAE,EAAE,MAAM,CAAC;IACX,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACtC;AAGD,MAAM,MAAM,YAAY,GAAG,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;AAGjG,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAChC,SAAS,EAAE,cAAc,EAAE,CAAC;CAE7B;AAGD,MAAM,WAAW,SAAS;IACxB;;;OAGG;IACH,OAAO,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACzC;;;OAGG;IACH,QAAQ,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC;IACpE,8CAA8C;IAC9C,IAAI,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IAC1F;;;;OAIG;IACH,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;CAC7B"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-extensions.js","sourceRoot":"","sources":["../../../src/agent/mcp/mcp-extensions.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { Client } from '@modelcontextprotocol/sdk/client';
|
|
2
|
+
import type { McpClient as IMcpClient, McpServerConfig, McpTool } from './mcp-types.js';
|
|
3
|
+
export declare class McpClient implements IMcpClient {
|
|
4
|
+
private readonly _servers;
|
|
5
|
+
private readonly _clients;
|
|
6
|
+
constructor(servers: McpServerConfig[], signal?: AbortSignal);
|
|
7
|
+
/**
|
|
8
|
+
* Creates and connects an SDK Client for the given config.
|
|
9
|
+
* Override in tests to inject an in-process transport and avoid spawning real subprocesses.
|
|
10
|
+
*/
|
|
11
|
+
protected _createClient(config: McpServerConfig, expandedEnv: Record<string, string>): Promise<Client>;
|
|
12
|
+
connect(serverId: string): Promise<void>;
|
|
13
|
+
getTools(serverId: string, allowList: string[]): Promise<McpTool[]>;
|
|
14
|
+
call(serverId: string, toolName: string, args: Record<string, unknown>): Promise<unknown>;
|
|
15
|
+
disconnect(): Promise<void>;
|
|
16
|
+
private _expandEnv;
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=mcp-client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-client.d.ts","sourceRoot":"","sources":["../../src/agent/mcp-client.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,MAAM,EAAE,MAAM,kCAAkC,CAAC;AAG1D,OAAO,KAAK,EAAE,SAAS,IAAI,UAAU,EAAE,eAAe,EAAE,OAAO,EAAE,MAAM,gBAAgB,CAAC;AAExF,qBAAa,SAAU,YAAW,UAAU;IAC1C,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAA+B;IACxD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAkC;gBAE/C,OAAO,EAAE,eAAe,EAAE,EAAE,MAAM,CAAC,EAAE,WAAW;IAc5D;;;OAGG;cACa,aAAa,CAC3B,MAAM,EAAE,eAAe,EACvB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAClC,OAAO,CAAC,MAAM,CAAC;IAqBZ,OAAO,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAqBxC,QAAQ,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC;IAanE,IAAI,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,OAAO,CAAC;IAMzF,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC;IAMjC,OAAO,CAAC,UAAU;CAmBnB"}
|
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
// mcp-client.ts — Manages stdio MCP server subprocess lifecycles.
|
|
2
|
+
// This is the only file in the codebase that imports @modelcontextprotocol/sdk directly.
|
|
3
|
+
import { Client } from '@modelcontextprotocol/sdk/client';
|
|
4
|
+
import { StdioClientTransport } from '@modelcontextprotocol/sdk/client/stdio.js';
|
|
5
|
+
import { WorkflowError } from '@sensigo/realm';
|
|
6
|
+
export class McpClient {
|
|
7
|
+
_servers;
|
|
8
|
+
_clients = new Map();
|
|
9
|
+
constructor(servers, signal) {
|
|
10
|
+
this._servers = new Map(servers.map((s) => [s.id, s]));
|
|
11
|
+
if (signal) {
|
|
12
|
+
// Register unconditionally — a signal that fires before first connect must still trigger cleanup.
|
|
13
|
+
signal.addEventListener('abort', () => {
|
|
14
|
+
void this.disconnect();
|
|
15
|
+
}, { once: true });
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Creates and connects an SDK Client for the given config.
|
|
20
|
+
* Override in tests to inject an in-process transport and avoid spawning real subprocesses.
|
|
21
|
+
*/
|
|
22
|
+
async _createClient(config, expandedEnv) {
|
|
23
|
+
const params = {
|
|
24
|
+
command: config.command ?? '',
|
|
25
|
+
...(config.args !== undefined ? { args: config.args } : {}),
|
|
26
|
+
...(Object.keys(expandedEnv).length > 0 ? { env: expandedEnv } : {}),
|
|
27
|
+
};
|
|
28
|
+
const transport = new StdioClientTransport(params);
|
|
29
|
+
const client = new Client({ name: 'realm-agent', version: '0.1.0' });
|
|
30
|
+
try {
|
|
31
|
+
await client.connect(transport);
|
|
32
|
+
}
|
|
33
|
+
catch (e) {
|
|
34
|
+
throw new WorkflowError(`MCP server '${config.id}': connection failed: ${String(e)}`, {
|
|
35
|
+
code: 'MCP_CONNECTION_FAILED',
|
|
36
|
+
category: 'ENGINE',
|
|
37
|
+
agentAction: 'stop',
|
|
38
|
+
retryable: false,
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
return client;
|
|
42
|
+
}
|
|
43
|
+
async connect(serverId) {
|
|
44
|
+
if (this._clients.has(serverId))
|
|
45
|
+
return;
|
|
46
|
+
const config = this._servers.get(serverId);
|
|
47
|
+
if (!config) {
|
|
48
|
+
throw new WorkflowError(`MCP server '${serverId}' is not configured`, {
|
|
49
|
+
code: 'MCP_CONNECTION_FAILED',
|
|
50
|
+
category: 'ENGINE',
|
|
51
|
+
agentAction: 'stop',
|
|
52
|
+
retryable: false,
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
const expandedEnv = this._expandEnv(serverId, config);
|
|
56
|
+
const client = await this._createClient(config, expandedEnv);
|
|
57
|
+
// Idempotency check after await — guards against concurrent connect() calls.
|
|
58
|
+
if (!this._clients.has(serverId)) {
|
|
59
|
+
this._clients.set(serverId, client);
|
|
60
|
+
}
|
|
61
|
+
else {
|
|
62
|
+
void client.close();
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
async getTools(serverId, allowList) {
|
|
66
|
+
await this.connect(serverId);
|
|
67
|
+
const client = this._clients.get(serverId);
|
|
68
|
+
const result = await client.listTools();
|
|
69
|
+
const tools = result.tools.map((t) => ({
|
|
70
|
+
name: t.name,
|
|
71
|
+
description: t.description ?? '',
|
|
72
|
+
inputSchema: t.inputSchema,
|
|
73
|
+
}));
|
|
74
|
+
if (allowList.length === 0)
|
|
75
|
+
return tools;
|
|
76
|
+
return tools.filter((t) => allowList.includes(t.name));
|
|
77
|
+
}
|
|
78
|
+
async call(serverId, toolName, args) {
|
|
79
|
+
await this.connect(serverId);
|
|
80
|
+
const client = this._clients.get(serverId);
|
|
81
|
+
return client.callTool({ name: toolName, arguments: args });
|
|
82
|
+
}
|
|
83
|
+
async disconnect() {
|
|
84
|
+
const clients = [...this._clients.values()];
|
|
85
|
+
this._clients.clear();
|
|
86
|
+
await Promise.allSettled(clients.map((c) => c.close()));
|
|
87
|
+
}
|
|
88
|
+
_expandEnv(serverId, config) {
|
|
89
|
+
const expanded = {};
|
|
90
|
+
for (const [key, value] of Object.entries(config.env ?? {})) {
|
|
91
|
+
const result = value.replace(/\$\{([^}]+)\}/g, (_match, varName) => {
|
|
92
|
+
const v = process.env[varName];
|
|
93
|
+
if (v === undefined) {
|
|
94
|
+
throw new WorkflowError(`MCP server '${serverId}': env var ${varName} is not set`, {
|
|
95
|
+
code: 'MCP_CONNECTION_FAILED',
|
|
96
|
+
category: 'ENGINE',
|
|
97
|
+
agentAction: 'stop',
|
|
98
|
+
retryable: false,
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
return v;
|
|
102
|
+
});
|
|
103
|
+
expanded[key] = result;
|
|
104
|
+
}
|
|
105
|
+
return expanded;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
//# sourceMappingURL=mcp-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-client.js","sourceRoot":"","sources":["../../src/agent/mcp-client.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { ToolCallRecord, McpServerConfig } from '@sensigo/realm';
|
|
2
|
+
export type { ToolCallRecord, McpServerConfig };
|
|
3
|
+
export interface McpTool {
|
|
4
|
+
name: string;
|
|
5
|
+
description: string;
|
|
6
|
+
inputSchema: Record<string, unknown>;
|
|
7
|
+
}
|
|
8
|
+
export interface ToolDefinition {
|
|
9
|
+
id: string;
|
|
10
|
+
serverId: string;
|
|
11
|
+
name: string;
|
|
12
|
+
description: string;
|
|
13
|
+
inputSchema: Record<string, unknown>;
|
|
14
|
+
}
|
|
15
|
+
export type ToolExecutor = (toolName: string, args: Record<string, unknown>) => Promise<unknown>;
|
|
16
|
+
export interface StepWithToolsResult {
|
|
17
|
+
output: Record<string, unknown>;
|
|
18
|
+
toolCalls: ToolCallRecord[];
|
|
19
|
+
}
|
|
20
|
+
export interface McpClient {
|
|
21
|
+
/**
|
|
22
|
+
* Lazily connects to a server on first call. Idempotent.
|
|
23
|
+
* stdio failures throw WorkflowError(MCP_CONNECTION_FAILED, stop).
|
|
24
|
+
*/
|
|
25
|
+
connect(serverId: string): Promise<void>;
|
|
26
|
+
/**
|
|
27
|
+
* Returns tools from the specified server, filtered to the allow-list.
|
|
28
|
+
* Triggers lazy-connect on first call — the subprocess may spawn here.
|
|
29
|
+
*/
|
|
30
|
+
getTools(serverId: string, allowList: string[]): Promise<McpTool[]>;
|
|
31
|
+
/** Execute a tool on the specified server. */
|
|
32
|
+
call(serverId: string, toolName: string, args: Record<string, unknown>): Promise<unknown>;
|
|
33
|
+
/**
|
|
34
|
+
* Shut down all server connections. Idempotent — safe to call multiple times.
|
|
35
|
+
* Must be called in finally blocks.
|
|
36
|
+
* If constructed with an AbortSignal, also called automatically on abort.
|
|
37
|
+
*/
|
|
38
|
+
disconnect(): Promise<void>;
|
|
39
|
+
}
|
|
40
|
+
//# sourceMappingURL=mcp-types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-types.d.ts","sourceRoot":"","sources":["../../src/agent/mcp-types.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,cAAc,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AACtE,YAAY,EAAE,cAAc,EAAE,eAAe,EAAE,CAAC;AAGhD,MAAM,WAAW,OAAO;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACtC;AAGD,MAAM,WAAW,cAAc;IAC7B,EAAE,EAAE,MAAM,CAAC;IACX,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACtC;AAGD,MAAM,MAAM,YAAY,GAAG,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;AAGjG,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAChC,SAAS,EAAE,cAAc,EAAE,CAAC;CAE7B;AAGD,MAAM,WAAW,SAAS;IACxB;;;OAGG;IACH,OAAO,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACzC;;;OAGG;IACH,QAAQ,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC;IACpE,8CAA8C;IAC9C,IAAI,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IAC1F;;;;OAIG;IACH,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;CAC7B"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mcp-types.js","sourceRoot":"","sources":["../../src/agent/mcp-types.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { ToolCapableLlmProvider, type ProviderCapabilities } from './llm-provider.js';
|
|
2
|
+
import type { ToolDefinition, ToolExecutor, StepWithToolsResult } from './mcp-types.js';
|
|
3
|
+
/**
|
|
4
|
+
* OpenAI LLM provider for realm agent.
|
|
5
|
+
* Uses the Chat Completions API. Sends `response_format: json_object` on native
|
|
6
|
+
* OpenAI endpoints; falls back to prompt-only JSON enforcement on compat endpoints
|
|
7
|
+
* behind `--base-url`. Retries once if the model returns non-JSON content.
|
|
8
|
+
*/
|
|
9
|
+
export declare class OpenAIProvider extends ToolCapableLlmProvider {
|
|
10
|
+
private readonly model;
|
|
11
|
+
private readonly baseUrl;
|
|
12
|
+
constructor(model: string, baseUrl?: string);
|
|
13
|
+
/**
|
|
14
|
+
* Native OpenAI endpoints have a well-defined, tested capability surface that includes
|
|
15
|
+
* json_object mode. Custom compat endpoints behind --base-url do not guarantee this feature.
|
|
16
|
+
* Default to prompt-only enforcement for any unknown endpoint.
|
|
17
|
+
*/
|
|
18
|
+
capabilities(): ProviderCapabilities;
|
|
19
|
+
callStep(prompt: string, inputSchema?: Record<string, unknown>): Promise<Record<string, unknown>>;
|
|
20
|
+
/**
|
|
21
|
+
* Agentic loop for tool-capable steps. Executes tool calls serially (V1 constraint)
|
|
22
|
+
* until the model returns a final JSON answer or the tool call budget is exhausted.
|
|
23
|
+
*/
|
|
24
|
+
callStepWithTools(prompt: string, tools: ToolDefinition[], executor: ToolExecutor, options: {
|
|
25
|
+
inputSchema?: Record<string, unknown>;
|
|
26
|
+
maxToolCalls?: number;
|
|
27
|
+
toolTimeoutMs?: number;
|
|
28
|
+
}): Promise<StepWithToolsResult>;
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=openai-provider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"openai-provider.d.ts","sourceRoot":"","sources":["../../src/agent/openai-provider.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,sBAAsB,EAAE,KAAK,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AACtF,OAAO,KAAK,EAEV,cAAc,EACd,YAAY,EACZ,mBAAmB,EACpB,MAAM,gBAAgB,CAAC;AAWxB;;;;;GAKG;AACH,qBAAa,cAAe,SAAQ,sBAAsB;IACxD,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAS;IAC/B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAqB;gBAEjC,KAAK,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;IAM3C;;;;OAIG;IACH,YAAY,IAAI,oBAAoB;IAI9B,QAAQ,CACZ,MAAM,EAAE,MAAM,EACd,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACpC,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IA8DnC;;;OAGG;IACG,iBAAiB,CACrB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,cAAc,EAAE,EACvB,QAAQ,EAAE,YAAY,EACtB,OAAO,EAAE;QACP,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;QACtC,YAAY,CAAC,EAAE,MAAM,CAAC;QACtB,aAAa,CAAC,EAAE,MAAM,CAAC;KACxB,GACA,OAAO,CAAC,mBAAmB,CAAC;CA0LhC"}
|