@indemn/cli 1.6.0 → 1.7.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/.claude-plugin/marketplace.json +3 -3
- package/.claude-plugin/plugin.json +9 -4
- package/.github/workflows/ci.yml +10 -0
- package/.github/workflows/publish.yml +2 -2
- package/.mcp.json +1 -4
- package/CONTRIBUTING.md +3 -1
- package/README.md +69 -176
- package/dist/cli/agents.d.ts.map +1 -1
- package/dist/cli/agents.js +226 -18
- package/dist/cli/agents.js.map +1 -1
- package/dist/cli/analytics.d.ts +3 -0
- package/dist/cli/analytics.d.ts.map +1 -0
- package/dist/cli/analytics.js +133 -0
- package/dist/cli/analytics.js.map +1 -0
- package/dist/cli/auth.d.ts.map +1 -1
- package/dist/cli/auth.js +62 -17
- package/dist/cli/auth.js.map +1 -1
- package/dist/cli/billing.d.ts +3 -0
- package/dist/cli/billing.d.ts.map +1 -0
- package/dist/cli/billing.js +23 -0
- package/dist/cli/billing.js.map +1 -0
- package/dist/cli/campaigns.d.ts +3 -0
- package/dist/cli/campaigns.d.ts.map +1 -0
- package/dist/cli/campaigns.js +34 -0
- package/dist/cli/campaigns.js.map +1 -0
- package/dist/cli/chat.d.ts.map +1 -1
- package/dist/cli/chat.js +69 -102
- package/dist/cli/chat.js.map +1 -1
- package/dist/cli/config.d.ts.map +1 -1
- package/dist/cli/config.js +71 -27
- package/dist/cli/config.js.map +1 -1
- package/dist/cli/conversations.d.ts +3 -0
- package/dist/cli/conversations.d.ts.map +1 -0
- package/dist/cli/conversations.js +129 -0
- package/dist/cli/conversations.js.map +1 -0
- package/dist/cli/distribution.d.ts +3 -0
- package/dist/cli/distribution.d.ts.map +1 -0
- package/dist/cli/distribution.js +122 -0
- package/dist/cli/distribution.js.map +1 -0
- package/dist/cli/eval.d.ts.map +1 -1
- package/dist/cli/eval.js +315 -71
- package/dist/cli/eval.js.map +1 -1
- package/dist/cli/functions.d.ts.map +1 -1
- package/dist/cli/functions.js +109 -38
- package/dist/cli/functions.js.map +1 -1
- package/dist/cli/index.js +63 -54
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/init.d.ts +27 -0
- package/dist/cli/init.d.ts.map +1 -0
- package/dist/cli/init.js +152 -0
- package/dist/cli/init.js.map +1 -0
- package/dist/cli/kb.d.ts.map +1 -1
- package/dist/cli/kb.js +141 -15
- package/dist/cli/kb.js.map +1 -1
- package/dist/cli/link.d.ts +21 -0
- package/dist/cli/link.d.ts.map +1 -0
- package/dist/cli/link.js +112 -0
- package/dist/cli/link.js.map +1 -0
- package/dist/cli/org.d.ts.map +1 -1
- package/dist/cli/org.js +79 -67
- package/dist/cli/org.js.map +1 -1
- package/dist/cli/platform.d.ts +3 -0
- package/dist/cli/platform.d.ts.map +1 -0
- package/dist/cli/platform.js +133 -0
- package/dist/cli/platform.js.map +1 -0
- package/dist/cli/tickets.d.ts +3 -0
- package/dist/cli/tickets.d.ts.map +1 -0
- package/dist/cli/tickets.js +125 -0
- package/dist/cli/tickets.js.map +1 -0
- package/dist/cli/utils/output.d.ts +15 -9
- package/dist/cli/utils/output.d.ts.map +1 -1
- package/dist/cli/utils/output.js +53 -46
- package/dist/cli/utils/output.js.map +1 -1
- package/dist/cli/voice.d.ts +3 -0
- package/dist/cli/voice.d.ts.map +1 -0
- package/dist/cli/voice.js +206 -0
- package/dist/cli/voice.js.map +1 -0
- package/dist/core/diff.d.ts +16 -0
- package/dist/core/diff.d.ts.map +1 -0
- package/dist/core/diff.js +57 -0
- package/dist/core/diff.js.map +1 -0
- package/dist/core/org-resolver.d.ts +37 -0
- package/dist/core/org-resolver.d.ts.map +1 -0
- package/dist/core/org-resolver.js +73 -0
- package/dist/core/org-resolver.js.map +1 -0
- package/dist/core/runtime.d.ts +36 -0
- package/dist/core/runtime.d.ts.map +1 -0
- package/dist/core/runtime.js +62 -0
- package/dist/core/runtime.js.map +1 -0
- package/dist/core/scope.d.ts +33 -0
- package/dist/core/scope.d.ts.map +1 -0
- package/dist/core/scope.js +37 -0
- package/dist/core/scope.js.map +1 -0
- package/dist/mcp/registry.d.ts +67 -0
- package/dist/mcp/registry.d.ts.map +1 -0
- package/dist/mcp/registry.js +195 -0
- package/dist/mcp/registry.js.map +1 -0
- package/dist/mcp/server.d.ts +9 -0
- package/dist/mcp/server.d.ts.map +1 -1
- package/dist/mcp/server.js +87 -2
- package/dist/mcp/server.js.map +1 -1
- package/dist/mcp/tool-meta.d.ts +21 -0
- package/dist/mcp/tool-meta.d.ts.map +1 -0
- package/dist/mcp/tool-meta.js +203 -0
- package/dist/mcp/tool-meta.js.map +1 -0
- package/dist/mcp/tools.d.ts +2 -1
- package/dist/mcp/tools.d.ts.map +1 -1
- package/dist/mcp/tools.js +1462 -215
- package/dist/mcp/tools.js.map +1 -1
- package/dist/sdk/agent-bundle.d.ts +99 -0
- package/dist/sdk/agent-bundle.d.ts.map +1 -0
- package/dist/sdk/agent-bundle.js +211 -0
- package/dist/sdk/agent-bundle.js.map +1 -0
- package/dist/sdk/agents.d.ts +54 -1
- package/dist/sdk/agents.d.ts.map +1 -1
- package/dist/sdk/agents.js +59 -5
- package/dist/sdk/agents.js.map +1 -1
- package/dist/sdk/analytics.d.ts +158 -0
- package/dist/sdk/analytics.d.ts.map +1 -0
- package/dist/sdk/analytics.js +185 -0
- package/dist/sdk/analytics.js.map +1 -0
- package/dist/sdk/auth.d.ts +34 -12
- package/dist/sdk/auth.d.ts.map +1 -1
- package/dist/sdk/auth.js +60 -77
- package/dist/sdk/auth.js.map +1 -1
- package/dist/sdk/billing.d.ts +25 -0
- package/dist/sdk/billing.d.ts.map +1 -0
- package/dist/sdk/billing.js +61 -0
- package/dist/sdk/billing.js.map +1 -0
- package/dist/sdk/campaigns.d.ts +35 -0
- package/dist/sdk/campaigns.d.ts.map +1 -0
- package/dist/sdk/campaigns.js +59 -0
- package/dist/sdk/campaigns.js.map +1 -0
- package/dist/sdk/chat.d.ts +25 -2
- package/dist/sdk/chat.d.ts.map +1 -1
- package/dist/sdk/chat.js +37 -10
- package/dist/sdk/chat.js.map +1 -1
- package/dist/sdk/client.d.ts +93 -5
- package/dist/sdk/client.d.ts.map +1 -1
- package/dist/sdk/client.js +362 -100
- package/dist/sdk/client.js.map +1 -1
- package/dist/sdk/config-change.d.ts +74 -0
- package/dist/sdk/config-change.d.ts.map +1 -0
- package/dist/sdk/config-change.js +117 -0
- package/dist/sdk/config-change.js.map +1 -0
- package/dist/sdk/config.d.ts.map +1 -1
- package/dist/sdk/config.js +2 -1
- package/dist/sdk/config.js.map +1 -1
- package/dist/sdk/conversations.d.ts +101 -0
- package/dist/sdk/conversations.d.ts.map +1 -0
- package/dist/sdk/conversations.js +155 -0
- package/dist/sdk/conversations.js.map +1 -0
- package/dist/sdk/credentials.d.ts +25 -0
- package/dist/sdk/credentials.d.ts.map +1 -0
- package/dist/sdk/credentials.js +44 -0
- package/dist/sdk/credentials.js.map +1 -0
- package/dist/sdk/distribution.d.ts +94 -0
- package/dist/sdk/distribution.d.ts.map +1 -0
- package/dist/sdk/distribution.js +100 -0
- package/dist/sdk/distribution.js.map +1 -0
- package/dist/sdk/eval.d.ts +81 -0
- package/dist/sdk/eval.d.ts.map +1 -1
- package/dist/sdk/eval.js +117 -0
- package/dist/sdk/eval.js.map +1 -1
- package/dist/sdk/functions.d.ts +14 -1
- package/dist/sdk/functions.d.ts.map +1 -1
- package/dist/sdk/functions.js +48 -5
- package/dist/sdk/functions.js.map +1 -1
- package/dist/sdk/index.d.ts +2 -0
- package/dist/sdk/index.d.ts.map +1 -1
- package/dist/sdk/index.js +2 -0
- package/dist/sdk/index.js.map +1 -1
- package/dist/sdk/jarvis-chat.d.ts +28 -0
- package/dist/sdk/jarvis-chat.d.ts.map +1 -0
- package/dist/sdk/jarvis-chat.js +117 -0
- package/dist/sdk/jarvis-chat.js.map +1 -0
- package/dist/sdk/kb.d.ts +69 -1
- package/dist/sdk/kb.d.ts.map +1 -1
- package/dist/sdk/kb.js +111 -24
- package/dist/sdk/kb.js.map +1 -1
- package/dist/sdk/orgs.d.ts +13 -0
- package/dist/sdk/orgs.d.ts.map +1 -0
- package/dist/sdk/orgs.js +59 -0
- package/dist/sdk/orgs.js.map +1 -0
- package/dist/sdk/platform.d.ts +62 -0
- package/dist/sdk/platform.d.ts.map +1 -0
- package/dist/sdk/platform.js +95 -0
- package/dist/sdk/platform.js.map +1 -0
- package/dist/sdk/session.d.ts +25 -0
- package/dist/sdk/session.d.ts.map +1 -0
- package/dist/sdk/session.js +69 -0
- package/dist/sdk/session.js.map +1 -0
- package/dist/sdk/skills.d.ts +46 -0
- package/dist/sdk/skills.d.ts.map +1 -0
- package/dist/sdk/skills.js +203 -0
- package/dist/sdk/skills.js.map +1 -0
- package/dist/sdk/test-chat.d.ts +52 -0
- package/dist/sdk/test-chat.d.ts.map +1 -0
- package/dist/sdk/test-chat.js +134 -0
- package/dist/sdk/test-chat.js.map +1 -0
- package/dist/sdk/tickets.d.ts +98 -0
- package/dist/sdk/tickets.d.ts.map +1 -0
- package/dist/sdk/tickets.js +91 -0
- package/dist/sdk/tickets.js.map +1 -0
- package/dist/sdk/types.d.ts +91 -6
- package/dist/sdk/types.d.ts.map +1 -1
- package/dist/sdk/voice.d.ts +147 -0
- package/dist/sdk/voice.d.ts.map +1 -0
- package/dist/sdk/voice.js +236 -0
- package/dist/sdk/voice.js.map +1 -0
- package/package.json +22 -3
- package/scripts/check-skills.mjs +25 -0
- package/skills/agent-builder/SKILL.md +89 -252
- package/skills/evaluations/SKILL.md +23 -234
- package/skills/evaluations/references/analysis.md +95 -0
- package/skills/evaluations/references/cli-reference.md +28 -0
- package/skills/evaluations/references/json-formats.md +100 -0
- package/src/cli/agents.ts +202 -22
- package/src/cli/analytics.ts +138 -0
- package/src/cli/auth.ts +56 -18
- package/src/cli/billing.ts +25 -0
- package/src/cli/campaigns.ts +33 -0
- package/src/cli/chat.ts +66 -115
- package/src/cli/config.ts +65 -31
- package/src/cli/conversations.ts +133 -0
- package/src/cli/distribution.ts +116 -0
- package/src/cli/eval.ts +254 -70
- package/src/cli/functions.ts +105 -39
- package/src/cli/index.ts +58 -55
- package/src/cli/init.ts +154 -0
- package/src/cli/kb.ts +120 -17
- package/src/cli/link.ts +117 -0
- package/src/cli/org.ts +81 -75
- package/src/cli/platform.ts +128 -0
- package/src/cli/tickets.ts +130 -0
- package/src/cli/utils/output.ts +51 -42
- package/src/cli/voice.ts +204 -0
- package/src/core/diff.ts +52 -0
- package/src/core/org-resolver.ts +113 -0
- package/src/core/runtime.ts +73 -0
- package/src/core/scope.ts +64 -0
- package/src/mcp/registry.ts +236 -0
- package/src/mcp/server.ts +84 -2
- package/src/mcp/tool-meta.ts +241 -0
- package/src/mcp/tools.ts +1529 -265
- package/src/sdk/agent-bundle.ts +245 -0
- package/src/sdk/agents.ts +74 -5
- package/src/sdk/analytics.ts +220 -0
- package/src/sdk/auth.ts +87 -107
- package/src/sdk/billing.ts +59 -0
- package/src/sdk/campaigns.ts +60 -0
- package/src/sdk/chat.ts +44 -10
- package/src/sdk/client.ts +373 -102
- package/src/sdk/config-change.ts +148 -0
- package/src/sdk/config.ts +2 -1
- package/src/sdk/conversations.ts +199 -0
- package/src/sdk/credentials.ts +53 -0
- package/src/sdk/distribution.ts +132 -0
- package/src/sdk/eval.ts +140 -0
- package/src/sdk/functions.ts +52 -6
- package/src/sdk/index.ts +2 -0
- package/src/sdk/jarvis-chat.ts +112 -0
- package/src/sdk/kb.ts +116 -29
- package/src/sdk/orgs.ts +62 -0
- package/src/sdk/platform.ts +115 -0
- package/src/sdk/session.ts +90 -0
- package/src/sdk/skills.ts +188 -0
- package/src/sdk/test-chat.ts +151 -0
- package/src/sdk/tickets.ts +120 -0
- package/src/sdk/types.ts +88 -6
- package/src/sdk/voice.ts +262 -0
- package/test/cli/entry.test.ts +34 -0
- package/test/cli/init.test.ts +66 -0
- package/test/cli/link.test.ts +57 -0
- package/test/core/org-resolver.test.ts +92 -0
- package/test/core/runtime.test.ts +30 -0
- package/test/core/scope.test.ts +93 -0
- package/test/harness.test.ts +24 -0
- package/test/helpers/config-home.ts +22 -0
- package/test/helpers/fake-middleware.ts +56 -0
- package/test/helpers/fetch-recorder.ts +75 -0
- package/test/helpers/jwt.ts +9 -0
- package/test/helpers/mcp-pair.ts +38 -0
- package/test/mcp/__snapshots__/tools-snapshot.test.ts.snap +145 -0
- package/test/mcp/askers.test.ts +60 -0
- package/test/mcp/elicit-timeout.test.ts +29 -0
- package/test/mcp/registry.test.ts +169 -0
- package/test/mcp/shaping.test.ts +41 -0
- package/test/mcp/tools-snapshot.test.ts +42 -0
- package/test/sdk/agents.test.ts +232 -0
- package/test/sdk/analytics.test.ts +89 -0
- package/test/sdk/auth.test.ts +70 -0
- package/test/sdk/billing.test.ts +47 -0
- package/test/sdk/campaigns.test.ts +43 -0
- package/test/sdk/client.test.ts +80 -0
- package/test/sdk/config-change.test.ts +142 -0
- package/test/sdk/conversations.test.ts +80 -0
- package/test/sdk/credentials.test.ts +33 -0
- package/test/sdk/distribution.test.ts +55 -0
- package/test/sdk/eval.test.ts +155 -0
- package/test/sdk/kb-upload.test.ts +50 -0
- package/test/sdk/kb.test.ts +95 -0
- package/test/sdk/orgs.test.ts +48 -0
- package/test/sdk/platform.test.ts +89 -0
- package/test/sdk/renewal.test.ts +115 -0
- package/test/sdk/session.test.ts +60 -0
- package/test/sdk/skills.test.ts +235 -0
- package/test/sdk/test-chat.test.ts +112 -0
- package/test/sdk/tickets.test.ts +42 -0
- package/test/sdk/voice.test.ts +147 -0
- package/vitest.config.ts +11 -0
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import type { IndemnClient } from './client.js';
|
|
2
|
+
import { type DiffLine } from '../core/diff.js';
|
|
3
|
+
import type { BotConfiguration } from './types.js';
|
|
4
|
+
export interface ConfigChange {
|
|
5
|
+
system_prompt?: string;
|
|
6
|
+
greeting?: string;
|
|
7
|
+
model?: {
|
|
8
|
+
provider: string;
|
|
9
|
+
model: string;
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
interface Snapshot {
|
|
13
|
+
system_prompt: string;
|
|
14
|
+
greeting: string;
|
|
15
|
+
model: string;
|
|
16
|
+
}
|
|
17
|
+
export interface ConfigPlan {
|
|
18
|
+
agentId: string;
|
|
19
|
+
current: Snapshot;
|
|
20
|
+
next: Snapshot;
|
|
21
|
+
/** Fields that would change: system_prompt, greeting, model. */
|
|
22
|
+
changes: Array<keyof Snapshot>;
|
|
23
|
+
promptDiff: DiffLine[];
|
|
24
|
+
/** Lifecycle from the V2 platform, or "unknown" when it cannot be read. */
|
|
25
|
+
lifecycle: string;
|
|
26
|
+
raw: BotConfiguration;
|
|
27
|
+
/** The model with its parameters, checked against the agent's channels. */
|
|
28
|
+
llm?: {
|
|
29
|
+
provider: string;
|
|
30
|
+
model: string;
|
|
31
|
+
parameters: Record<string, unknown>;
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* The model as the dashboard saves it: refused when the agent takes calls and the model cannot, and sent with
|
|
36
|
+
* its parameters (fixed ones plus each adjustable field's current value or default).
|
|
37
|
+
*/
|
|
38
|
+
export declare function modelForAgent(client: IndemnClient, model: {
|
|
39
|
+
provider: string;
|
|
40
|
+
model: string;
|
|
41
|
+
}, channels: string[], current?: Record<string, unknown>): Promise<{
|
|
42
|
+
provider: string;
|
|
43
|
+
model: string;
|
|
44
|
+
parameters: Record<string, unknown>;
|
|
45
|
+
}>;
|
|
46
|
+
/** What a configuration change would do, without doing it. */
|
|
47
|
+
export declare function planConfigChange(client: IndemnClient, agentId: string, change: ConfigChange): Promise<ConfigPlan>;
|
|
48
|
+
/** Published, or not known because the V2 platform could not be read: either way it may be live, so it gets the extra consent. */
|
|
49
|
+
export declare function mayBeLive(lifecycle: string | undefined): boolean;
|
|
50
|
+
/** How a confirmation says an agent may be live. */
|
|
51
|
+
export declare function liveText(lifecycle: string | undefined): string;
|
|
52
|
+
/** Short text for a confirmation: what changes, how much, and whether customers see it. */
|
|
53
|
+
export declare function describePlan(plan: ConfigPlan, opts?: {
|
|
54
|
+
maxDiffLines?: number;
|
|
55
|
+
}): string;
|
|
56
|
+
/**
|
|
57
|
+
* Apply a planned change the way the dashboard does, then read it back.
|
|
58
|
+
* - The dashboard shows `system_prompt_ops` before `system_prompt`, so the
|
|
59
|
+
* stale ops are cleared or the dashboard keeps showing the old prompt.
|
|
60
|
+
* - copilot parses `first_message` from a JSON string.
|
|
61
|
+
* - copilot can answer success with data:false even when it saved, so the
|
|
62
|
+
* result is judged by reading the configuration back.
|
|
63
|
+
*/
|
|
64
|
+
export declare function applyConfigChange(client: IndemnClient, plan: ConfigPlan, change: ConfigChange): Promise<{
|
|
65
|
+
applied: string[];
|
|
66
|
+
mismatched: string[];
|
|
67
|
+
}>;
|
|
68
|
+
/** "openai/gpt-4.1", or a bare model name with the provider guessed as before. */
|
|
69
|
+
export declare function modelArg(value: string): {
|
|
70
|
+
provider: string;
|
|
71
|
+
model: string;
|
|
72
|
+
};
|
|
73
|
+
export {};
|
|
74
|
+
//# sourceMappingURL=config-change.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config-change.d.ts","sourceRoot":"","sources":["../../src/sdk/config-change.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAKhD,OAAO,EAAmC,KAAK,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AACjF,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAEnD,MAAM,WAAW,YAAY;IAC3B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,KAAK,CAAC,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC;CAC7C;AAED,UAAU,QAAQ;IAChB,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,UAAU;IACzB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,QAAQ,CAAC;IAClB,IAAI,EAAE,QAAQ,CAAC;IACf,gEAAgE;IAChE,OAAO,EAAE,KAAK,CAAC,MAAM,QAAQ,CAAC,CAAC;IAC/B,UAAU,EAAE,QAAQ,EAAE,CAAC;IACvB,2EAA2E;IAC3E,SAAS,EAAE,MAAM,CAAC;IAClB,GAAG,EAAE,gBAAgB,CAAC;IACtB,2EAA2E;IAC3E,GAAG,CAAC,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;KAAE,CAAC;CAChF;AAaD;;;GAGG;AACH,wBAAsB,aAAa,CACjC,MAAM,EAAE,YAAY,EAAE,KAAK,EAAE;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,OAAO,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,GAC1H,OAAO,CAAC;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;CAAE,CAAC,CAUnF;AAMD,8DAA8D;AAC9D,wBAAsB,gBAAgB,CAAC,MAAM,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,YAAY,GAAG,OAAO,CAAC,UAAU,CAAC,CAsBvH;AAED,kIAAkI;AAClI,wBAAgB,SAAS,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,GAAG,OAAO,CAEhE;AAED,oDAAoD;AACpD,wBAAgB,QAAQ,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,CAE9D;AAED,2FAA2F;AAC3F,wBAAgB,YAAY,CAAC,IAAI,EAAE,UAAU,EAAE,IAAI,GAAE;IAAE,YAAY,CAAC,EAAE,MAAM,CAAA;CAAO,GAAG,MAAM,CAU3F;AAED;;;;;;;GAOG;AACH,wBAAsB,iBAAiB,CAAC,MAAM,EAAE,YAAY,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,YAAY,GAAG,OAAO,CAAC;IAAE,OAAO,EAAE,MAAM,EAAE,CAAC;IAAC,UAAU,EAAE,MAAM,EAAE,CAAA;CAAE,CAAC,CAgB1J;AAED,kFAAkF;AAClF,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,CAK3E"}
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
import { ConfigSDK } from './config.js';
|
|
2
|
+
import { AgentInsightsSDK, AgentsSDK } from './agents.js';
|
|
3
|
+
import { FunctionsSDK } from './functions.js';
|
|
4
|
+
import { CliError } from '../core/runtime.js';
|
|
5
|
+
import { diffStats, formatDiff, lineDiff } from '../core/diff.js';
|
|
6
|
+
function snapshot(cfg) {
|
|
7
|
+
const llm = cfg.llm_config;
|
|
8
|
+
return {
|
|
9
|
+
system_prompt: cfg.ai_config?.system_prompt ?? '',
|
|
10
|
+
greeting: cfg.first_message?.text ?? '',
|
|
11
|
+
model: llm?.model ? `${llm.provider ?? '?'}/${llm.model}` : '',
|
|
12
|
+
};
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* The model as the dashboard saves it: refused when the agent takes calls and the model cannot, and sent with
|
|
16
|
+
* its parameters (fixed ones plus each adjustable field's current value or default).
|
|
17
|
+
*/
|
|
18
|
+
export async function modelForAgent(client, model, channels, current = {}) {
|
|
19
|
+
const catalog = await new FunctionsSDK(client).listLLMModels();
|
|
20
|
+
const entry = catalog.find((p) => p.provider === model.provider)?.models?.find((m) => m.model_id === model.model);
|
|
21
|
+
if (!entry)
|
|
22
|
+
throw new CliError(`Model ${model.provider}/${model.model} is not in the platform's model list. See \`indemn models\`.`);
|
|
23
|
+
if (channels.map((c) => c.toUpperCase()).includes('VOICE') && !(entry.channels ?? []).includes('VOICE')) {
|
|
24
|
+
throw new CliError(`${model.provider}/${model.model} cannot take calls, and this agent answers the phone. Pick a model that supports voice (see \`indemn models\`).`);
|
|
25
|
+
}
|
|
26
|
+
const parameters = { ...(entry.static_parameters ?? {}) };
|
|
27
|
+
for (const [key, field] of Object.entries(entry.exposed_fields ?? {}))
|
|
28
|
+
parameters[key] = current[key] !== undefined ? current[key] : field?.default;
|
|
29
|
+
return { ...model, parameters };
|
|
30
|
+
}
|
|
31
|
+
function channelTypes(agent) {
|
|
32
|
+
return (agent.channels ?? []).map((c) => (typeof c === 'string' ? c : String(c.type ?? c.name ?? '')));
|
|
33
|
+
}
|
|
34
|
+
/** What a configuration change would do, without doing it. */
|
|
35
|
+
export async function planConfigChange(client, agentId, change) {
|
|
36
|
+
const raw = await new ConfigSDK(client).getConfig(agentId);
|
|
37
|
+
const current = snapshot(raw);
|
|
38
|
+
const next = {
|
|
39
|
+
system_prompt: change.system_prompt ?? current.system_prompt,
|
|
40
|
+
greeting: change.greeting ?? current.greeting,
|
|
41
|
+
model: change.model ? `${change.model.provider}/${change.model.model}` : current.model,
|
|
42
|
+
};
|
|
43
|
+
const changes = Object.keys(next).filter((k) => next[k] !== current[k]);
|
|
44
|
+
let llm;
|
|
45
|
+
if (change.model && changes.includes('model')) {
|
|
46
|
+
const agent = await new AgentsSDK(client).getAgent(agentId);
|
|
47
|
+
const saved = (raw.llm_config?.parameters) ?? {};
|
|
48
|
+
llm = await modelForAgent(client, change.model, channelTypes(agent), saved);
|
|
49
|
+
}
|
|
50
|
+
let lifecycle = 'unknown';
|
|
51
|
+
try {
|
|
52
|
+
lifecycle = (await new AgentInsightsSDK(client).detail(agentId)).lifecycle ?? 'prototype';
|
|
53
|
+
}
|
|
54
|
+
catch {
|
|
55
|
+
// The V2 platform may be unreachable; callers treat "unknown" as published (mayBeLive).
|
|
56
|
+
}
|
|
57
|
+
return { agentId, current, next, changes, promptDiff: lineDiff(current.system_prompt, next.system_prompt), lifecycle, raw, llm };
|
|
58
|
+
}
|
|
59
|
+
/** Published, or not known because the V2 platform could not be read: either way it may be live, so it gets the extra consent. */
|
|
60
|
+
export function mayBeLive(lifecycle) {
|
|
61
|
+
return lifecycle === 'published' || lifecycle === 'unknown';
|
|
62
|
+
}
|
|
63
|
+
/** How a confirmation says an agent may be live. */
|
|
64
|
+
export function liveText(lifecycle) {
|
|
65
|
+
return lifecycle === 'published' ? 'is PUBLISHED (live for customers)' : 'may be live for customers (its status could not be read)';
|
|
66
|
+
}
|
|
67
|
+
/** Short text for a confirmation: what changes, how much, and whether customers see it. */
|
|
68
|
+
export function describePlan(plan, opts = {}) {
|
|
69
|
+
if (plan.changes.length === 0)
|
|
70
|
+
return `No change to agent ${plan.agentId}.`;
|
|
71
|
+
const parts = [`Agent ${plan.agentId}${mayBeLive(plan.lifecycle) ? ` ${liveText(plan.lifecycle)}` : ` (${plan.lifecycle})`}.`];
|
|
72
|
+
if (plan.changes.includes('system_prompt')) {
|
|
73
|
+
const { added, removed } = diffStats(plan.promptDiff);
|
|
74
|
+
parts.push(`Prompt: +${added} / -${removed} lines.\n${formatDiff(plan.promptDiff, { maxLines: opts.maxDiffLines ?? 40 })}`);
|
|
75
|
+
}
|
|
76
|
+
if (plan.changes.includes('greeting'))
|
|
77
|
+
parts.push(`Greeting: "${plan.current.greeting}" -> "${plan.next.greeting}".`);
|
|
78
|
+
if (plan.changes.includes('model'))
|
|
79
|
+
parts.push(`Model: ${plan.current.model || '(none)'} -> ${plan.next.model}.`);
|
|
80
|
+
return parts.join('\n');
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Apply a planned change the way the dashboard does, then read it back.
|
|
84
|
+
* - The dashboard shows `system_prompt_ops` before `system_prompt`, so the
|
|
85
|
+
* stale ops are cleared or the dashboard keeps showing the old prompt.
|
|
86
|
+
* - copilot parses `first_message` from a JSON string.
|
|
87
|
+
* - copilot can answer success with data:false even when it saved, so the
|
|
88
|
+
* result is judged by reading the configuration back.
|
|
89
|
+
*/
|
|
90
|
+
export async function applyConfigChange(client, plan, change) {
|
|
91
|
+
const input = {};
|
|
92
|
+
if (plan.changes.includes('system_prompt')) {
|
|
93
|
+
input.system_prompt = change.system_prompt;
|
|
94
|
+
input.system_prompt_ops = null;
|
|
95
|
+
}
|
|
96
|
+
if (plan.changes.includes('greeting')) {
|
|
97
|
+
input.first_message = JSON.stringify({ ...(plan.raw.first_message ?? {}), text: change.greeting });
|
|
98
|
+
}
|
|
99
|
+
if (plan.changes.includes('model') && change.model)
|
|
100
|
+
input.llm_config = plan.llm ?? { provider: change.model.provider, model: change.model.model };
|
|
101
|
+
if (Object.keys(input).length === 0)
|
|
102
|
+
return { applied: [], mismatched: [] };
|
|
103
|
+
const sdk = new ConfigSDK(client);
|
|
104
|
+
await sdk.setConfig(plan.agentId, input);
|
|
105
|
+
const after = snapshot(await sdk.getConfig(plan.agentId));
|
|
106
|
+
const mismatched = plan.changes.filter((k) => after[k] !== plan.next[k]);
|
|
107
|
+
return { applied: plan.changes.filter((k) => !mismatched.includes(k)), mismatched };
|
|
108
|
+
}
|
|
109
|
+
/** "openai/gpt-4.1", or a bare model name with the provider guessed as before. */
|
|
110
|
+
export function modelArg(value) {
|
|
111
|
+
const i = value.indexOf('/');
|
|
112
|
+
if (i > 0)
|
|
113
|
+
return { provider: value.slice(0, i), model: value.slice(i + 1) };
|
|
114
|
+
const provider = value.startsWith('claude') ? 'anthropic' : value.startsWith('gemini') ? 'google' : 'openai';
|
|
115
|
+
return { provider, model: value };
|
|
116
|
+
}
|
|
117
|
+
//# sourceMappingURL=config-change.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config-change.js","sourceRoot":"","sources":["../../src/sdk/config-change.ts"],"names":[],"mappings":"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"}
|
package/dist/sdk/config.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/sdk/config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAChD,OAAO,KAAK,EAAE,gBAAgB,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAEnE,qBAAa,SAAS;IACR,OAAO,CAAC,MAAM;gBAAN,MAAM,EAAE,YAAY;IAElC,SAAS,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAMrD,SAAS,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,cAAc,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAO3E,SAAS,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC;IAKvD,SAAS,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/sdk/config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAChD,OAAO,KAAK,EAAE,gBAAgB,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAEnE,qBAAa,SAAS;IACR,OAAO,CAAC,MAAM;gBAAN,MAAM,EAAE,YAAY;IAElC,SAAS,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAMrD,SAAS,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,cAAc,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAO3E,SAAS,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC;IAKvD,SAAS,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;CAI5E"}
|
package/dist/sdk/config.js
CHANGED
|
@@ -14,7 +14,8 @@ export class ConfigSDK {
|
|
|
14
14
|
return config.ai_config?.system_prompt;
|
|
15
15
|
}
|
|
16
16
|
async setPrompt(agentId, prompt) {
|
|
17
|
-
|
|
17
|
+
// Clear the dashboard's editor copy, or the dashboard keeps showing the old prompt.
|
|
18
|
+
return this.setConfig(agentId, { system_prompt: prompt, system_prompt_ops: null });
|
|
18
19
|
}
|
|
19
20
|
}
|
|
20
21
|
//# sourceMappingURL=config.js.map
|
package/dist/sdk/config.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/sdk/config.ts"],"names":[],"mappings":"AAGA,MAAM,OAAO,SAAS;IACA;IAApB,YAAoB,MAAoB;QAApB,WAAM,GAAN,MAAM,CAAc;IAAG,CAAC;IAE5C,KAAK,CAAC,SAAS,CAAC,OAAe;QAC7B,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAC3B,wCAAwC,OAAO,iBAAiB,CACjE,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,SAAS,CAAC,OAAe,EAAE,IAAoB;QACnD,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAC3B,wCAAwC,OAAO,iBAAiB,EAChE,IAAI,CACL,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,SAAS,CAAC,OAAe;QAC7B,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC;QAC7C,OAAO,MAAM,CAAC,SAAS,EAAE,aAAa,CAAC;IACzC,CAAC;IAED,KAAK,CAAC,SAAS,CAAC,OAAe,EAAE,MAAc;QAC7C,OAAO,IAAI,CAAC,SAAS,CAAC,OAAO,EAAE,EAAE,aAAa,EAAE,MAAM,EAAE,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/sdk/config.ts"],"names":[],"mappings":"AAGA,MAAM,OAAO,SAAS;IACA;IAApB,YAAoB,MAAoB;QAApB,WAAM,GAAN,MAAM,CAAc;IAAG,CAAC;IAE5C,KAAK,CAAC,SAAS,CAAC,OAAe;QAC7B,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAC3B,wCAAwC,OAAO,iBAAiB,CACjE,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,SAAS,CAAC,OAAe,EAAE,IAAoB;QACnD,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAC3B,wCAAwC,OAAO,iBAAiB,EAChE,IAAI,CACL,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,SAAS,CAAC,OAAe;QAC7B,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC;QAC7C,OAAO,MAAM,CAAC,SAAS,EAAE,aAAa,CAAC;IACzC,CAAC;IAED,KAAK,CAAC,SAAS,CAAC,OAAe,EAAE,MAAc;QAC7C,oFAAoF;QACpF,OAAO,IAAI,CAAC,SAAS,CAAC,OAAO,EAAE,EAAE,aAAa,EAAE,MAAM,EAAE,iBAAiB,EAAE,IAAI,EAAE,CAAC,CAAC;IACrF,CAAC;CACF"}
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
import type { IndemnClient } from './client.js';
|
|
2
|
+
/** A copilot conversation ("request"). Only the fields the CLI relies on are typed. */
|
|
3
|
+
export interface Conversation {
|
|
4
|
+
_id: string;
|
|
5
|
+
request_id: string;
|
|
6
|
+
id_project: string;
|
|
7
|
+
id_organization?: string;
|
|
8
|
+
isTestMode?: boolean;
|
|
9
|
+
status?: number | string;
|
|
10
|
+
first_text?: string;
|
|
11
|
+
createdAt?: string;
|
|
12
|
+
updatedAt?: string;
|
|
13
|
+
attributes?: Record<string, unknown> & {
|
|
14
|
+
isTestMode?: boolean;
|
|
15
|
+
conversation_tester?: string;
|
|
16
|
+
preview?: string;
|
|
17
|
+
};
|
|
18
|
+
[key: string]: unknown;
|
|
19
|
+
}
|
|
20
|
+
export declare function idOf(value: unknown): string;
|
|
21
|
+
/**
|
|
22
|
+
* Link to one conversation in the dashboard. The dashboard routes by hash; `view=single`
|
|
23
|
+
* opens that conversation whether it is live or a test (the link its own agent preview copies).
|
|
24
|
+
*/
|
|
25
|
+
export declare function conversationUrl(client: IndemnClient, projectId: string, requestId: string): string;
|
|
26
|
+
export interface ConversationMessage {
|
|
27
|
+
_id?: string;
|
|
28
|
+
sender?: string;
|
|
29
|
+
senderFullname?: string;
|
|
30
|
+
text?: string;
|
|
31
|
+
type?: string;
|
|
32
|
+
createdAt?: string;
|
|
33
|
+
role: 'user' | 'agent' | 'system';
|
|
34
|
+
}
|
|
35
|
+
export interface ConversationList {
|
|
36
|
+
count: number;
|
|
37
|
+
conversations: Conversation[];
|
|
38
|
+
}
|
|
39
|
+
export declare function isCliConversation(c: Conversation): boolean;
|
|
40
|
+
/** Test flag of a conversation from either the stored field or its lifted attribute. */
|
|
41
|
+
export declare function isTestConversation(c: Conversation): boolean;
|
|
42
|
+
/**
|
|
43
|
+
* A conversation as an evaluation test set with one scenario item, ready for
|
|
44
|
+
* `indemn test-sets create`. Success criteria are left for a person to write.
|
|
45
|
+
*/
|
|
46
|
+
export declare function conversationToTestSet(c: Conversation, messages: ConversationMessage[], agentId: string): {
|
|
47
|
+
name: string;
|
|
48
|
+
description: string;
|
|
49
|
+
agent_id: string;
|
|
50
|
+
items: {
|
|
51
|
+
type: string;
|
|
52
|
+
name: string;
|
|
53
|
+
inputs: {
|
|
54
|
+
persona: string;
|
|
55
|
+
initial_message: string;
|
|
56
|
+
max_turns: number;
|
|
57
|
+
};
|
|
58
|
+
expected: {
|
|
59
|
+
success_criteria: string[];
|
|
60
|
+
expected_outcome: string | undefined;
|
|
61
|
+
};
|
|
62
|
+
tags: string[];
|
|
63
|
+
}[];
|
|
64
|
+
};
|
|
65
|
+
export declare class ConversationsSDK {
|
|
66
|
+
private client;
|
|
67
|
+
constructor(client: IndemnClient);
|
|
68
|
+
/**
|
|
69
|
+
* One agent's conversations in the current org, newest first, test ones
|
|
70
|
+
* included (the org Conversations API filters by agent on the server).
|
|
71
|
+
*/
|
|
72
|
+
list(agentId: string, opts?: {
|
|
73
|
+
limit?: number;
|
|
74
|
+
page?: number;
|
|
75
|
+
includeTest?: boolean;
|
|
76
|
+
from?: string;
|
|
77
|
+
to?: string;
|
|
78
|
+
cliOnly?: boolean;
|
|
79
|
+
}): Promise<ConversationList>;
|
|
80
|
+
/** All messages of a conversation, oldest first, with who said each one. */
|
|
81
|
+
messages(projectId: string, requestId: string, agentId?: string): Promise<ConversationMessage[]>;
|
|
82
|
+
/** One conversation by its request id (for a CLI chat this is the socket session id). */
|
|
83
|
+
get(projectId: string, requestId: string): Promise<Conversation>;
|
|
84
|
+
/**
|
|
85
|
+
* Mark a conversation as test through the same route the dashboard uses, so
|
|
86
|
+
* copilot also records "Marked as test" and reverses usage billing.
|
|
87
|
+
*/
|
|
88
|
+
markTest(projectId: string, requestId: string): Promise<Conversation>;
|
|
89
|
+
/**
|
|
90
|
+
* Read a new CLI conversation back from copilot and stop unless it is stored
|
|
91
|
+
* as a test conversation in the expected org. The conversation is created
|
|
92
|
+
* asynchronously, so this polls until it appears.
|
|
93
|
+
*/
|
|
94
|
+
verifyTestConversation(projectId: string, requestId: string, expectedOrgId: string, opts?: {
|
|
95
|
+
timeoutMs?: number;
|
|
96
|
+
intervalMs?: number;
|
|
97
|
+
}): Promise<Conversation>;
|
|
98
|
+
}
|
|
99
|
+
/** The project that holds an agent's conversations (checked by copilot against the org). */
|
|
100
|
+
export declare function projectOfAgent(client: IndemnClient, agentId: string): Promise<string>;
|
|
101
|
+
//# sourceMappingURL=conversations.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"conversations.d.ts","sourceRoot":"","sources":["../../src/sdk/conversations.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import { CliError } from '../core/runtime.js';
|
|
2
|
+
export function idOf(value) {
|
|
3
|
+
if (value && typeof value === 'object' && '_id' in value)
|
|
4
|
+
return String(value._id);
|
|
5
|
+
return value === undefined || value === null ? '' : String(value);
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* Link to one conversation in the dashboard. The dashboard routes by hash; `view=single`
|
|
9
|
+
* opens that conversation whether it is live or a test (the link its own agent preview copies).
|
|
10
|
+
*/
|
|
11
|
+
export function conversationUrl(client, projectId, requestId) {
|
|
12
|
+
const base = client.getHosts().copilot.replace(/\/api\/?$/, '');
|
|
13
|
+
return `${base}/#/project/${projectId}/wsrequest/${encodeURIComponent(requestId)}/messages?view=single`;
|
|
14
|
+
}
|
|
15
|
+
/** Agent replies are stored under the agent's bare id (older ones as `bot_<id>`). */
|
|
16
|
+
function roleOf(sender, agentId) {
|
|
17
|
+
if (!sender || sender === 'system')
|
|
18
|
+
return 'system';
|
|
19
|
+
return sender === agentId || sender.startsWith('bot_') ? 'agent' : 'user';
|
|
20
|
+
}
|
|
21
|
+
export function isCliConversation(c) {
|
|
22
|
+
const attrs = (c.attributes ?? {});
|
|
23
|
+
const flat = c;
|
|
24
|
+
const user = String(flat.user_id ?? attrs.user_id ?? flat.unique_user_id ?? attrs.unique_user_id ?? flat.requester_id ?? '');
|
|
25
|
+
return user.startsWith('cli-user-');
|
|
26
|
+
}
|
|
27
|
+
/** Test flag of a conversation from either the stored field or its lifted attribute. */
|
|
28
|
+
export function isTestConversation(c) {
|
|
29
|
+
const flat = c;
|
|
30
|
+
const v = flat.isTestMode ?? c.attributes?.isTestMode;
|
|
31
|
+
return v === true || v === 'true';
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* A conversation as an evaluation test set with one scenario item, ready for
|
|
35
|
+
* `indemn test-sets create`. Success criteria are left for a person to write.
|
|
36
|
+
*/
|
|
37
|
+
export function conversationToTestSet(c, messages, agentId) {
|
|
38
|
+
const userTurns = messages.filter((m) => m.role === 'user' && m.text && m.text !== 'Get Started');
|
|
39
|
+
const agentTurns = messages.filter((m) => m.role === 'agent' && m.text);
|
|
40
|
+
return {
|
|
41
|
+
name: `From conversation ${c.request_id}`,
|
|
42
|
+
description: `Created from conversation ${c.request_id} of agent ${agentId}. Write the success criteria before running it.`,
|
|
43
|
+
agent_id: agentId,
|
|
44
|
+
items: [
|
|
45
|
+
{
|
|
46
|
+
type: 'scenario',
|
|
47
|
+
name: `Replay of ${c.request_id}`,
|
|
48
|
+
inputs: {
|
|
49
|
+
persona: `A customer who opened with: "${userTurns[0]?.text ?? ''}". Follow-ups in the original: ${userTurns.slice(1).map((m) => `"${m.text}"`).join(', ') || 'none'}.`,
|
|
50
|
+
initial_message: userTurns[0]?.text ?? '',
|
|
51
|
+
max_turns: Math.min(60, Math.max(1, userTurns.length)),
|
|
52
|
+
},
|
|
53
|
+
expected: {
|
|
54
|
+
success_criteria: [],
|
|
55
|
+
expected_outcome: agentTurns.at(-1)?.text,
|
|
56
|
+
},
|
|
57
|
+
tags: ['from-conversation', c.request_id],
|
|
58
|
+
},
|
|
59
|
+
],
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
export class ConversationsSDK {
|
|
63
|
+
client;
|
|
64
|
+
constructor(client) {
|
|
65
|
+
this.client = client;
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* One agent's conversations in the current org, newest first, test ones
|
|
69
|
+
* included (the org Conversations API filters by agent on the server).
|
|
70
|
+
*/
|
|
71
|
+
async list(agentId, opts = {}) {
|
|
72
|
+
const query = {
|
|
73
|
+
'attr[id_bot]': agentId,
|
|
74
|
+
limit: String(Math.min(opts.limit ?? 50, 100)),
|
|
75
|
+
page: String(opts.page ?? 0),
|
|
76
|
+
sort: 'created_at',
|
|
77
|
+
direction: '-1',
|
|
78
|
+
};
|
|
79
|
+
if (opts.from)
|
|
80
|
+
query.start_date = opts.from;
|
|
81
|
+
if (opts.to)
|
|
82
|
+
query.end_date = opts.to;
|
|
83
|
+
const res = await this.client.copilotGet('/organization/:org_id/conversations', query);
|
|
84
|
+
let conversations = res.conversations ?? [];
|
|
85
|
+
if (opts.includeTest === false)
|
|
86
|
+
conversations = conversations.filter((c) => !isTestConversation(c));
|
|
87
|
+
if (opts.cliOnly)
|
|
88
|
+
conversations = conversations.filter(isCliConversation);
|
|
89
|
+
return { count: res.count ?? conversations.length, conversations };
|
|
90
|
+
}
|
|
91
|
+
/** All messages of a conversation, oldest first, with who said each one. */
|
|
92
|
+
async messages(projectId, requestId, agentId) {
|
|
93
|
+
const raw = await this.client.copilotGet(`/${projectId}/requests/${encodeURIComponent(requestId)}/messages`);
|
|
94
|
+
return (raw ?? []).map((m) => ({
|
|
95
|
+
_id: m._id, sender: m.sender, senderFullname: m.senderFullname, text: m.text, type: m.type, createdAt: m.createdAt,
|
|
96
|
+
role: roleOf(m.sender, agentId),
|
|
97
|
+
}));
|
|
98
|
+
}
|
|
99
|
+
/** One conversation by its request id (for a CLI chat this is the socket session id). */
|
|
100
|
+
async get(projectId, requestId) {
|
|
101
|
+
return this.client.copilotGet(`/${projectId}/requests/${encodeURIComponent(requestId)}`);
|
|
102
|
+
}
|
|
103
|
+
/**
|
|
104
|
+
* Mark a conversation as test through the same route the dashboard uses, so
|
|
105
|
+
* copilot also records "Marked as test" and reverses usage billing.
|
|
106
|
+
*/
|
|
107
|
+
async markTest(projectId, requestId) {
|
|
108
|
+
return this.client.copilotRequestRaw('PATCH', `/${projectId}/requests/${encodeURIComponent(requestId)}`, { isTestMode: true });
|
|
109
|
+
}
|
|
110
|
+
/**
|
|
111
|
+
* Read a new CLI conversation back from copilot and stop unless it is stored
|
|
112
|
+
* as a test conversation in the expected org. The conversation is created
|
|
113
|
+
* asynchronously, so this polls until it appears.
|
|
114
|
+
*/
|
|
115
|
+
async verifyTestConversation(projectId, requestId, expectedOrgId, opts = {}) {
|
|
116
|
+
const timeoutMs = opts.timeoutMs ?? 20_000;
|
|
117
|
+
const intervalMs = opts.intervalMs ?? 1_000;
|
|
118
|
+
const started = Date.now();
|
|
119
|
+
for (;;) {
|
|
120
|
+
let conversation;
|
|
121
|
+
try {
|
|
122
|
+
conversation = await this.get(projectId, requestId);
|
|
123
|
+
}
|
|
124
|
+
catch (err) {
|
|
125
|
+
if (!(err instanceof Error) || !/not found/i.test(err.message))
|
|
126
|
+
throw err;
|
|
127
|
+
}
|
|
128
|
+
if (conversation) {
|
|
129
|
+
const org = idOf(conversation.id_organization);
|
|
130
|
+
if (conversation.isTestMode !== true || conversation.attributes?.isTestMode === false) {
|
|
131
|
+
throw new CliError(`Conversation ${requestId} was stored as a live conversation, not a test. Nothing was sent. ` +
|
|
132
|
+
'Mark it as test with `indemn conversations mark-test` and report this.');
|
|
133
|
+
}
|
|
134
|
+
if (org && org !== expectedOrgId) {
|
|
135
|
+
throw new CliError(`Conversation ${requestId} was stored in org ${org}, not ${expectedOrgId}. Nothing was sent.`);
|
|
136
|
+
}
|
|
137
|
+
return conversation;
|
|
138
|
+
}
|
|
139
|
+
if (Date.now() - started >= timeoutMs) {
|
|
140
|
+
throw new CliError(`Could not confirm within ${Math.round(timeoutMs / 1000)} s that conversation ${requestId} is a test conversation. Nothing was sent.`);
|
|
141
|
+
}
|
|
142
|
+
await new Promise((resolve) => setTimeout(resolve, intervalMs));
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
/** The project that holds an agent's conversations (checked by copilot against the org). */
|
|
147
|
+
export async function projectOfAgent(client, agentId) {
|
|
148
|
+
const { AgentsSDK } = await import('./agents.js');
|
|
149
|
+
const agent = await new AgentsSDK(client).getAgent(agentId);
|
|
150
|
+
const projectId = idOf(agent?.id_project);
|
|
151
|
+
if (!projectId)
|
|
152
|
+
throw new CliError(`Agent ${agentId} has no project in this org.`);
|
|
153
|
+
return projectId;
|
|
154
|
+
}
|
|
155
|
+
//# sourceMappingURL=conversations.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"conversations.js","sourceRoot":"","sources":["../../src/sdk/conversations.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAiB9C,MAAM,UAAU,IAAI,CAAC,KAAc;IACjC,IAAI,KAAK,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,IAAI,KAAK;QAAE,OAAO,MAAM,CAAE,KAA0B,CAAC,GAAG,CAAC,CAAC;IACzG,OAAO,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;AACpE,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,eAAe,CAAC,MAAoB,EAAE,SAAiB,EAAE,SAAiB;IACxF,MAAM,IAAI,GAAG,MAAM,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,WAAW,EAAE,EAAE,CAAC,CAAC;IAChE,OAAO,GAAG,IAAI,cAAc,SAAS,cAAc,kBAAkB,CAAC,SAAS,CAAC,uBAAuB,CAAC;AAC1G,CAAC;AAiBD,qFAAqF;AACrF,SAAS,MAAM,CAAC,MAA0B,EAAE,OAAgB;IAC1D,IAAI,CAAC,MAAM,IAAI,MAAM,KAAK,QAAQ;QAAE,OAAO,QAAQ,CAAC;IACpD,OAAO,MAAM,KAAK,OAAO,IAAI,MAAM,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC;AAC5E,CAAC;AAED,MAAM,UAAU,iBAAiB,CAAC,CAAe;IAC/C,MAAM,KAAK,GAAG,CAAC,CAAC,CAAC,UAAU,IAAI,EAAE,CAA4B,CAAC;IAC9D,MAAM,IAAI,GAAG,CAA4B,CAAC;IAC1C,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,OAAO,IAAI,KAAK,CAAC,OAAO,IAAI,IAAI,CAAC,cAAc,IAAI,KAAK,CAAC,cAAc,IAAI,IAAI,CAAC,YAAY,IAAI,EAAE,CAAC,CAAC;IAC7H,OAAO,IAAI,CAAC,UAAU,CAAC,WAAW,CAAC,CAAC;AACtC,CAAC;AAED,wFAAwF;AACxF,MAAM,UAAU,kBAAkB,CAAC,CAAe;IAChD,MAAM,IAAI,GAAG,CAA4B,CAAC;IAC1C,MAAM,CAAC,GAAG,IAAI,CAAC,UAAU,IAAI,CAAC,CAAC,UAAU,EAAE,UAAU,CAAC;IACtD,OAAO,CAAC,KAAK,IAAI,IAAI,CAAC,KAAK,MAAM,CAAC;AACpC,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,qBAAqB,CAAC,CAAe,EAAE,QAA+B,EAAE,OAAe;IACrG,MAAM,SAAS,GAAG,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,MAAM,IAAI,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,IAAI,KAAK,aAAa,CAAC,CAAC;IAClG,MAAM,UAAU,GAAG,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,OAAO,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC;IACxE,OAAO;QACL,IAAI,EAAE,qBAAqB,CAAC,CAAC,UAAU,EAAE;QACzC,WAAW,EAAE,6BAA6B,CAAC,CAAC,UAAU,aAAa,OAAO,iDAAiD;QAC3H,QAAQ,EAAE,OAAO;QACjB,KAAK,EAAE;YACL;gBACE,IAAI,EAAE,UAAU;gBAChB,IAAI,EAAE,aAAa,CAAC,CAAC,UAAU,EAAE;gBACjC,MAAM,EAAE;oBACN,OAAO,EAAE,gCAAgC,SAAS,CAAC,CAAC,CAAC,EAAE,IAAI,IAAI,EAAE,kCAAkC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,CAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,MAAM,GAAG;oBACvK,eAAe,EAAE,SAAS,CAAC,CAAC,CAAC,EAAE,IAAI,IAAI,EAAE;oBACzC,SAAS,EAAE,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,SAAS,CAAC,MAAM,CAAC,CAAC;iBACvD;gBACD,QAAQ,EAAE;oBACR,gBAAgB,EAAE,EAAc;oBAChC,gBAAgB,EAAE,UAAU,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,IAAI;iBAC1C;gBACD,IAAI,EAAE,CAAC,mBAAmB,EAAE,CAAC,CAAC,UAAU,CAAC;aAC1C;SACF;KACF,CAAC;AACJ,CAAC;AAED,MAAM,OAAO,gBAAgB;IACP;IAApB,YAAoB,MAAoB;QAApB,WAAM,GAAN,MAAM,CAAc;IAAG,CAAC;IAE5C;;;OAGG;IACH,KAAK,CAAC,IAAI,CAAC,OAAe,EAAE,OAExB,EAAE;QACJ,MAAM,KAAK,GAA2B;YACpC,cAAc,EAAE,OAAO;YACvB,KAAK,EAAE,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,IAAI,EAAE,EAAE,GAAG,CAAC,CAAC;YAC9C,IAAI,EAAE,MAAM,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC,CAAC;YAC5B,IAAI,EAAE,YAAY;YAClB,SAAS,EAAE,IAAI;SAChB,CAAC;QACF,IAAI,IAAI,CAAC,IAAI;YAAE,KAAK,CAAC,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC;QAC5C,IAAI,IAAI,CAAC,EAAE;YAAE,KAAK,CAAC,QAAQ,GAAG,IAAI,CAAC,EAAE,CAAC;QACtC,MAAM,GAAG,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,UAAU,CAAqD,qCAAqC,EAAE,KAAK,CAAC,CAAC;QAC3I,IAAI,aAAa,GAAG,GAAG,CAAC,aAAa,IAAI,EAAE,CAAC;QAC5C,IAAI,IAAI,CAAC,WAAW,KAAK,KAAK;YAAE,aAAa,GAAG,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,CAAC,CAAC;QACpG,IAAI,IAAI,CAAC,OAAO;YAAE,aAAa,GAAG,aAAa,CAAC,MAAM,CAAC,iBAAiB,CAAC,CAAC;QAC1E,OAAO,EAAE,KAAK,EAAE,GAAG,CAAC,KAAK,IAAI,aAAa,CAAC,MAAM,EAAE,aAAa,EAAE,CAAC;IACrE,CAAC;IAED,4EAA4E;IAC5E,KAAK,CAAC,QAAQ,CAAC,SAAiB,EAAE,SAAiB,EAAE,OAAgB;QACnE,MAAM,GAAG,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,UAAU,CACtC,IAAI,SAAS,aAAa,kBAAkB,CAAC,SAAS,CAAC,WAAW,CACnE,CAAC;QACF,OAAO,CAAC,GAAG,IAAI,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YAC7B,GAAG,EAAE,CAAC,CAAC,GAAG,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,cAAc,EAAE,CAAC,CAAC,cAAc,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,SAAS,EAAE,CAAC,CAAC,SAAS;YAClH,IAAI,EAAE,MAAM,CAAC,CAAC,CAAC,MAAM,EAAE,OAAO,CAAC;SAChC,CAAC,CAAC,CAAC;IACN,CAAC;IAED,yFAAyF;IACzF,KAAK,CAAC,GAAG,CAAC,SAAiB,EAAE,SAAiB;QAC5C,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAAe,IAAI,SAAS,aAAa,kBAAkB,CAAC,SAAS,CAAC,EAAE,CAAC,CAAC;IACzG,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,QAAQ,CAAC,SAAiB,EAAE,SAAiB;QACjD,OAAO,IAAI,CAAC,MAAM,CAAC,iBAAiB,CAAe,OAAO,EAAE,IAAI,SAAS,aAAa,kBAAkB,CAAC,SAAS,CAAC,EAAE,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,CAAC,CAAC;IAC/I,CAAC;IAED;;;;OAIG;IACH,KAAK,CAAC,sBAAsB,CAC1B,SAAiB,EACjB,SAAiB,EACjB,aAAqB,EACrB,OAAoD,EAAE;QAEtD,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,IAAI,MAAM,CAAC;QAC3C,MAAM,UAAU,GAAG,IAAI,CAAC,UAAU,IAAI,KAAK,CAAC;QAC5C,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QAC3B,SAAS,CAAC;YACR,IAAI,YAAsC,CAAC;YAC3C,IAAI,CAAC;gBACH,YAAY,GAAG,MAAM,IAAI,CAAC,GAAG,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC;YACtD,CAAC;YAAC,OAAO,GAAG,EAAE,CAAC;gBACb,IAAI,CAAC,CAAC,GAAG,YAAY,KAAK,CAAC,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,GAAG,CAAC,OAAO,CAAC;oBAAE,MAAM,GAAG,CAAC;YAC5E,CAAC;YACD,IAAI,YAAY,EAAE,CAAC;gBACjB,MAAM,GAAG,GAAG,IAAI,CAAC,YAAY,CAAC,eAAe,CAAC,CAAC;gBAC/C,IAAI,YAAY,CAAC,UAAU,KAAK,IAAI,IAAI,YAAY,CAAC,UAAU,EAAE,UAAU,KAAK,KAAK,EAAE,CAAC;oBACtF,MAAM,IAAI,QAAQ,CAChB,gBAAgB,SAAS,oEAAoE;wBAC3F,wEAAwE,CAC3E,CAAC;gBACJ,CAAC;gBACD,IAAI,GAAG,IAAI,GAAG,KAAK,aAAa,EAAE,CAAC;oBACjC,MAAM,IAAI,QAAQ,CAAC,gBAAgB,SAAS,sBAAsB,GAAG,SAAS,aAAa,qBAAqB,CAAC,CAAC;gBACpH,CAAC;gBACD,OAAO,YAAY,CAAC;YACtB,CAAC;YACD,IAAI,IAAI,CAAC,GAAG,EAAE,GAAG,OAAO,IAAI,SAAS,EAAE,CAAC;gBACtC,MAAM,IAAI,QAAQ,CAChB,4BAA4B,IAAI,CAAC,KAAK,CAAC,SAAS,GAAG,IAAI,CAAC,wBAAwB,SAAS,4CAA4C,CACtI,CAAC;YACJ,CAAC;YACD,MAAM,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC,CAAC;QAClE,CAAC;IACH,CAAC;CACF;AAED,4FAA4F;AAC5F,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,MAAoB,EAAE,OAAe;IACxE,MAAM,EAAE,SAAS,EAAE,GAAG,MAAM,MAAM,CAAC,aAAa,CAAC,CAAC;IAClD,MAAM,KAAK,GAAG,MAAM,IAAI,SAAS,CAAC,MAAM,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;IAC5D,MAAM,SAAS,GAAG,IAAI,CAAC,KAAK,EAAE,UAAU,CAAC,CAAC;IAC1C,IAAI,CAAC,SAAS;QAAE,MAAM,IAAI,QAAQ,CAAC,SAAS,OAAO,8BAA8B,CAAC,CAAC;IACnF,OAAO,SAAS,CAAC;AACnB,CAAC"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { Environment, IndemnConfig } from './types.js';
|
|
2
|
+
export type Credential = {
|
|
3
|
+
kind: 'token';
|
|
4
|
+
token: string;
|
|
5
|
+
source: 'env' | 'config';
|
|
6
|
+
environment: Environment;
|
|
7
|
+
} | {
|
|
8
|
+
kind: 'api_key';
|
|
9
|
+
key: string;
|
|
10
|
+
source: 'env' | 'config';
|
|
11
|
+
environment: Environment;
|
|
12
|
+
};
|
|
13
|
+
/**
|
|
14
|
+
* Which credential a request uses, in order:
|
|
15
|
+
* 1. INDEMN_TOKEN with INDEMN_ENV: a session handed over by a host, such as Darwin starting the toolbox for Jarvis.
|
|
16
|
+
* 2. INDEMN_API_KEY: pipelines that already hold a dev key.
|
|
17
|
+
* 3. The session saved by `indemn login`.
|
|
18
|
+
* 4. An API key saved by a login from before token-first auth.
|
|
19
|
+
*/
|
|
20
|
+
export declare function resolveCredential(config: IndemnConfig | null, env?: NodeJS.ProcessEnv): Credential | null;
|
|
21
|
+
/** copilot reads its own session with the JWT scheme; API keys go as Bearer and copilot converts them. */
|
|
22
|
+
export declare function copilotAuthHeader(c: Credential): string;
|
|
23
|
+
/** Darwin accepts only the session token, as Bearer (like the dashboard sends it). */
|
|
24
|
+
export declare function darwinAuthHeader(c: Credential): string;
|
|
25
|
+
//# sourceMappingURL=credentials.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"credentials.d.ts","sourceRoot":"","sources":["../../src/sdk/credentials.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAG5D,MAAM,MAAM,UAAU,GAClB;IAAE,IAAI,EAAE,OAAO,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,KAAK,GAAG,QAAQ,CAAC;IAAC,WAAW,EAAE,WAAW,CAAA;CAAE,GACpF;IAAE,IAAI,EAAE,SAAS,CAAC;IAAC,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,KAAK,GAAG,QAAQ,CAAC;IAAC,WAAW,EAAE,WAAW,CAAA;CAAE,CAAC;AAUzF;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,YAAY,GAAG,IAAI,EAAE,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,UAAU,GAAG,IAAI,CAiBtH;AAED,0GAA0G;AAC1G,wBAAgB,iBAAiB,CAAC,CAAC,EAAE,UAAU,GAAG,MAAM,CAEvD;AAED,sFAAsF;AACtF,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,UAAU,GAAG,MAAM,CAKtD"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import { CliError } from '../core/runtime.js';
|
|
2
|
+
function isEnvironment(value) {
|
|
3
|
+
return value === 'dev' || value === 'production';
|
|
4
|
+
}
|
|
5
|
+
function keyEnvironment(key) {
|
|
6
|
+
return key.startsWith('ind_live_') ? 'production' : 'dev';
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Which credential a request uses, in order:
|
|
10
|
+
* 1. INDEMN_TOKEN with INDEMN_ENV: a session handed over by a host, such as Darwin starting the toolbox for Jarvis.
|
|
11
|
+
* 2. INDEMN_API_KEY: pipelines that already hold a dev key.
|
|
12
|
+
* 3. The session saved by `indemn login`.
|
|
13
|
+
* 4. An API key saved by a login from before token-first auth.
|
|
14
|
+
*/
|
|
15
|
+
export function resolveCredential(config, env = process.env) {
|
|
16
|
+
if (env.INDEMN_TOKEN) {
|
|
17
|
+
if (!isEnvironment(env.INDEMN_ENV)) {
|
|
18
|
+
throw new CliError('INDEMN_TOKEN needs INDEMN_ENV set to dev or production.');
|
|
19
|
+
}
|
|
20
|
+
return { kind: 'token', token: env.INDEMN_TOKEN.replace(/^(JWT|Bearer)\s+/i, ''), source: 'env', environment: env.INDEMN_ENV };
|
|
21
|
+
}
|
|
22
|
+
if (env.INDEMN_API_KEY) {
|
|
23
|
+
return { kind: 'api_key', key: env.INDEMN_API_KEY, source: 'env', environment: keyEnvironment(env.INDEMN_API_KEY) };
|
|
24
|
+
}
|
|
25
|
+
if (config?.session?.token) {
|
|
26
|
+
return { kind: 'token', token: config.session.token, source: 'config', environment: config.environment };
|
|
27
|
+
}
|
|
28
|
+
if (config?.api_key) {
|
|
29
|
+
return { kind: 'api_key', key: config.api_key, source: 'config', environment: config.environment };
|
|
30
|
+
}
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
/** copilot reads its own session with the JWT scheme; API keys go as Bearer and copilot converts them. */
|
|
34
|
+
export function copilotAuthHeader(c) {
|
|
35
|
+
return c.kind === 'token' ? `JWT ${c.token}` : `Bearer ${c.key}`;
|
|
36
|
+
}
|
|
37
|
+
/** Darwin accepts only the session token, as Bearer (like the dashboard sends it). */
|
|
38
|
+
export function darwinAuthHeader(c) {
|
|
39
|
+
if (c.kind !== 'token') {
|
|
40
|
+
throw new CliError('The V2 platform needs a login session, not an API key. Run `indemn login`.');
|
|
41
|
+
}
|
|
42
|
+
return `Bearer ${c.token}`;
|
|
43
|
+
}
|
|
44
|
+
//# sourceMappingURL=credentials.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"credentials.js","sourceRoot":"","sources":["../../src/sdk/credentials.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAM9C,SAAS,aAAa,CAAC,KAAc;IACnC,OAAO,KAAK,KAAK,KAAK,IAAI,KAAK,KAAK,YAAY,CAAC;AACnD,CAAC;AAED,SAAS,cAAc,CAAC,GAAW;IACjC,OAAO,GAAG,CAAC,UAAU,CAAC,WAAW,CAAC,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,KAAK,CAAC;AAC5D,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,iBAAiB,CAAC,MAA2B,EAAE,MAAyB,OAAO,CAAC,GAAG;IACjG,IAAI,GAAG,CAAC,YAAY,EAAE,CAAC;QACrB,IAAI,CAAC,aAAa,CAAC,GAAG,CAAC,UAAU,CAAC,EAAE,CAAC;YACnC,MAAM,IAAI,QAAQ,CAAC,yDAAyD,CAAC,CAAC;QAChF,CAAC;QACD,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,GAAG,CAAC,YAAY,CAAC,OAAO,CAAC,mBAAmB,EAAE,EAAE,CAAC,EAAE,MAAM,EAAE,KAAK,EAAE,WAAW,EAAE,GAAG,CAAC,UAAU,EAAE,CAAC;IACjI,CAAC;IACD,IAAI,GAAG,CAAC,cAAc,EAAE,CAAC;QACvB,OAAO,EAAE,IAAI,EAAE,SAAS,EAAE,GAAG,EAAE,GAAG,CAAC,cAAc,EAAE,MAAM,EAAE,KAAK,EAAE,WAAW,EAAE,cAAc,CAAC,GAAG,CAAC,cAAc,CAAC,EAAE,CAAC;IACtH,CAAC;IACD,IAAI,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;QAC3B,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,CAAC,OAAO,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,CAAC,WAAW,EAAE,CAAC;IAC3G,CAAC;IACD,IAAI,MAAM,EAAE,OAAO,EAAE,CAAC;QACpB,OAAO,EAAE,IAAI,EAAE,SAAS,EAAE,GAAG,EAAE,MAAM,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,CAAC,WAAW,EAAE,CAAC;IACrG,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED,0GAA0G;AAC1G,MAAM,UAAU,iBAAiB,CAAC,CAAa;IAC7C,OAAO,CAAC,CAAC,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,GAAG,EAAE,CAAC;AACnE,CAAC;AAED,sFAAsF;AACtF,MAAM,UAAU,gBAAgB,CAAC,CAAa;IAC5C,IAAI,CAAC,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;QACvB,MAAM,IAAI,QAAQ,CAAC,4EAA4E,CAAC,CAAC;IACnG,CAAC;IACD,OAAO,UAAU,CAAC,CAAC,KAAK,EAAE,CAAC;AAC7B,CAAC"}
|