@kweaver-ai/kweaver-sdk 0.6.9 → 0.6.10
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/dist/api/agent-list.js +15 -2
- package/dist/api/ontology-query.d.ts +32 -3
- package/dist/api/toolboxes.d.ts +16 -0
- package/dist/api/toolboxes.js +39 -5
- package/dist/cli.js +5 -1
- package/dist/client.d.ts +3 -0
- package/dist/client.js +5 -0
- package/dist/commands/bkn-schema.d.ts +27 -0
- package/dist/commands/bkn-schema.js +232 -7
- package/dist/commands/bkn.js +2 -1
- package/dist/commands/tool.d.ts +12 -0
- package/dist/commands/tool.js +177 -7
- package/dist/index.d.ts +4 -0
- package/dist/index.js +2 -0
- package/dist/resources/agents.js +19 -5
- package/dist/resources/toolboxes.d.ts +39 -0
- package/dist/resources/toolboxes.js +54 -0
- package/package.json +1 -1
package/dist/api/agent-list.js
CHANGED
|
@@ -12,11 +12,24 @@ export async function listAgents(options) {
|
|
|
12
12
|
custom_space_id,
|
|
13
13
|
is_to_square,
|
|
14
14
|
});
|
|
15
|
-
|
|
15
|
+
// Some deployments (observed on dip-poc.aishu.cn) return an empty entries
|
|
16
|
+
// array when this endpoint is called with `application/json`; the same
|
|
17
|
+
// payload sent as `text/plain` works. Other deployments only accept
|
|
18
|
+
// `application/json` (and reject text/plain with 4xx). Try text/plain first
|
|
19
|
+
// and fall back to application/json on 4xx so both platform variants work
|
|
20
|
+
// out of the box.
|
|
21
|
+
const tryPost = async (contentType) => fetchWithRetry(url, {
|
|
16
22
|
method: "POST",
|
|
17
|
-
headers:
|
|
23
|
+
headers: {
|
|
24
|
+
...buildHeaders(accessToken, businessDomain),
|
|
25
|
+
"content-type": contentType,
|
|
26
|
+
},
|
|
18
27
|
body,
|
|
19
28
|
});
|
|
29
|
+
let response = await tryPost("text/plain;charset=UTF-8");
|
|
30
|
+
if (!response.ok && response.status >= 400 && response.status < 500) {
|
|
31
|
+
response = await tryPost("application/json");
|
|
32
|
+
}
|
|
20
33
|
const responseBody = await response.text();
|
|
21
34
|
if (!response.ok) {
|
|
22
35
|
throw new HttpError(response.status, response.statusText, responseBody);
|
|
@@ -44,11 +44,40 @@ export declare function actionTypeQuery(options: ActionTypeQueryOptions): Promis
|
|
|
44
44
|
/**
|
|
45
45
|
* Action-type execute: POST (has side effects).
|
|
46
46
|
*
|
|
47
|
-
* The request body must
|
|
48
|
-
*
|
|
47
|
+
* The request body must use the envelope shape below — top-level scalar fields
|
|
48
|
+
* (other than `trigger_type` and `_instance_identities`) are silently dropped
|
|
49
|
+
* by the backend, which causes downstream tools to receive `null` parameters
|
|
50
|
+
* (and typically respond with 401 token expired or 500 type errors).
|
|
51
|
+
*
|
|
49
52
|
* ```json
|
|
50
|
-
* {
|
|
53
|
+
* {
|
|
54
|
+
* "trigger_type": "manual",
|
|
55
|
+
* "_instance_identities": [{"<primary_key>": "<value>"}],
|
|
56
|
+
* "dynamic_params": {
|
|
57
|
+
* "<param_name>": "<value>",
|
|
58
|
+
* "Authorization": "Bearer <token>"
|
|
59
|
+
* }
|
|
60
|
+
* }
|
|
51
61
|
* ```
|
|
62
|
+
*
|
|
63
|
+
* - `_instance_identities` may be `[]` for "create"-style actions.
|
|
64
|
+
* - Each ActionType parameter has a `value_from` discriminator:
|
|
65
|
+
* • `input` — caller MUST supply via `dynamic_params`. Includes
|
|
66
|
+
* `source: header` params (e.g. `Authorization`/`token`),
|
|
67
|
+
* which are usually credentials for the DOWNSTREAM system
|
|
68
|
+
* the action calls — NOT the platform session token. The
|
|
69
|
+
* SDK never auto-forwards its session token.
|
|
70
|
+
* • `const` — frozen in the ActionType snapshot; values in body are
|
|
71
|
+
* silently ignored. Edit the ActionType definition to
|
|
72
|
+
* `input` first if you need caller override.
|
|
73
|
+
* • `property` — auto-populated from the resolved instance's property;
|
|
74
|
+
* do not (and cannot) supply via body.
|
|
75
|
+
*
|
|
76
|
+
* Practical recipe: query the ActionType, filter parameters where
|
|
77
|
+
* `value_from == "input"`, put exactly those names into `dynamic_params`.
|
|
78
|
+
*
|
|
79
|
+
* See `skills/kweaver-core/references/bkn.md` ("action-type execute 请求体契约")
|
|
80
|
+
* for the full contract and troubleshooting table.
|
|
52
81
|
*/
|
|
53
82
|
export interface ActionTypeExecuteOptions extends OntologyQueryBaseOptions {
|
|
54
83
|
atId: string;
|
package/dist/api/toolboxes.d.ts
CHANGED
|
@@ -44,4 +44,20 @@ export interface ListToolsOptions extends BaseOpts {
|
|
|
44
44
|
boxId: string;
|
|
45
45
|
}
|
|
46
46
|
export declare function listTools(opts: ListToolsOptions): Promise<string>;
|
|
47
|
+
export interface InvokeToolOptions extends BaseOpts {
|
|
48
|
+
boxId: string;
|
|
49
|
+
toolId: string;
|
|
50
|
+
/** Optional headers to forward to the downstream tool (e.g. Authorization). */
|
|
51
|
+
header?: Record<string, unknown>;
|
|
52
|
+
/** Optional query params to forward. */
|
|
53
|
+
query?: Record<string, unknown>;
|
|
54
|
+
/** JSON body forwarded to the downstream tool. */
|
|
55
|
+
body?: unknown;
|
|
56
|
+
/** Per-call timeout in seconds; backend default applies when omitted. */
|
|
57
|
+
timeout?: number;
|
|
58
|
+
}
|
|
59
|
+
/** Execute a published+enabled tool through the toolbox proxy. */
|
|
60
|
+
export declare function executeTool(opts: InvokeToolOptions): Promise<string>;
|
|
61
|
+
/** Debug a tool through the toolbox proxy (works on draft/disabled tools too). */
|
|
62
|
+
export declare function debugTool(opts: InvokeToolOptions): Promise<string>;
|
|
47
63
|
export {};
|
package/dist/api/toolboxes.js
CHANGED
|
@@ -5,15 +5,24 @@ import { buildHeaders } from "./headers.js";
|
|
|
5
5
|
// Backend endpoints under /api/agent-operator-integration/v1/tool-box.
|
|
6
6
|
//
|
|
7
7
|
// Verified against kweaver/examples/03-action-lifecycle/run.sh (lines 78–197):
|
|
8
|
-
// POST /tool-box
|
|
9
|
-
// DELETE /tool-box/{id}
|
|
10
|
-
// POST /tool-box/{id}/status
|
|
11
|
-
// POST /tool-box/{id}/tool
|
|
12
|
-
// POST /tool-box/{id}/tools/status
|
|
8
|
+
// POST /tool-box create
|
|
9
|
+
// DELETE /tool-box/{id} delete
|
|
10
|
+
// POST /tool-box/{id}/status publish/draft
|
|
11
|
+
// POST /tool-box/{id}/tool upload tool (multipart)
|
|
12
|
+
// POST /tool-box/{id}/tools/status enable/disable (batch)
|
|
13
13
|
//
|
|
14
14
|
// Verified during Task 8 e2e against the live backend (2026-04-18):
|
|
15
15
|
// GET /tool-box/list?keyword=&limit=&offset= list toolboxes
|
|
16
16
|
// GET /tool-box/{id}/tools/list list tools
|
|
17
|
+
//
|
|
18
|
+
// Verified live on 2026-04-23 against dip-poc.aishu.cn:
|
|
19
|
+
// POST /tool-box/{box}/proxy/{tool} execute tool (envelope JSON)
|
|
20
|
+
// POST /tool-box/{box}/tool/{tool}/debug debug tool (envelope JSON)
|
|
21
|
+
//
|
|
22
|
+
// Envelope shape required by /proxy and /debug:
|
|
23
|
+
// { "timeout": <s>, "header": {...}, "query": {...}, "body": {...} }
|
|
24
|
+
// Flat-shape requests cause the forwarder to drop downstream Authorization
|
|
25
|
+
// headers, which manifests as 401 "token expired" from the underlying tool.
|
|
17
26
|
const PATH = "/api/agent-operator-integration/v1/tool-box";
|
|
18
27
|
function url(base, suffix = "") {
|
|
19
28
|
return `${base.replace(/\/+$/, "")}${PATH}${suffix}`;
|
|
@@ -88,3 +97,28 @@ export async function listTools(opts) {
|
|
|
88
97
|
});
|
|
89
98
|
return body;
|
|
90
99
|
}
|
|
100
|
+
function buildEnvelope(opts) {
|
|
101
|
+
const envelope = {};
|
|
102
|
+
if (opts.timeout !== undefined)
|
|
103
|
+
envelope.timeout = opts.timeout;
|
|
104
|
+
envelope.header = opts.header ?? {};
|
|
105
|
+
envelope.query = opts.query ?? {};
|
|
106
|
+
envelope.body = opts.body ?? {};
|
|
107
|
+
return JSON.stringify(envelope);
|
|
108
|
+
}
|
|
109
|
+
async function invokeTool(opts, suffix) {
|
|
110
|
+
const { body } = await fetchTextOrThrow(url(opts.baseUrl, suffix), {
|
|
111
|
+
method: "POST",
|
|
112
|
+
headers: { ...buildHeaders(opts.accessToken, opts.businessDomain ?? "bd_public"), "content-type": "application/json" },
|
|
113
|
+
body: buildEnvelope(opts),
|
|
114
|
+
});
|
|
115
|
+
return body;
|
|
116
|
+
}
|
|
117
|
+
/** Execute a published+enabled tool through the toolbox proxy. */
|
|
118
|
+
export async function executeTool(opts) {
|
|
119
|
+
return invokeTool(opts, `/${encodeURIComponent(opts.boxId)}/proxy/${encodeURIComponent(opts.toolId)}`);
|
|
120
|
+
}
|
|
121
|
+
/** Debug a tool through the toolbox proxy (works on draft/disabled tools too). */
|
|
122
|
+
export async function debugTool(opts) {
|
|
123
|
+
return invokeTool(opts, `/${encodeURIComponent(opts.boxId)}/tool/${encodeURIComponent(opts.toolId)}/debug`);
|
|
124
|
+
}
|
package/dist/cli.js
CHANGED
|
@@ -88,7 +88,8 @@ Usage:
|
|
|
88
88
|
kweaver bkn object-type list|get|create|update|delete|query|properties <kn-id> ...
|
|
89
89
|
kweaver bkn relation-type list|get|create|update|delete <kn-id> ...
|
|
90
90
|
kweaver bkn subgraph <kn-id> <body-json>
|
|
91
|
-
kweaver bkn action-type list|query|execute <kn-id> ... [--wait] [--no-wait] [--timeout N]
|
|
91
|
+
kweaver bkn action-type list|query|inputs|execute <kn-id> ... [--wait] [--no-wait] [--timeout N]
|
|
92
|
+
kweaver bkn action-type execute <kn-id> <at-id> [<envelope-json>|--dynamic-params '<json>' --instance '<json>' --trigger-type <v>]
|
|
92
93
|
kweaver bkn action-execution get <kn-id> <execution-id>
|
|
93
94
|
kweaver bkn action-log list|get|cancel <kn-id> ...
|
|
94
95
|
|
|
@@ -110,6 +111,9 @@ Usage:
|
|
|
110
111
|
kweaver tool upload --toolbox <box-id> <openapi-spec-path> [--metadata-type openapi]
|
|
111
112
|
kweaver tool list --toolbox <box-id> [-bd value]
|
|
112
113
|
kweaver tool enable|disable --toolbox <box-id> <tool-id>... [-bd value]
|
|
114
|
+
kweaver tool execute|debug --toolbox <box-id> <tool-id>
|
|
115
|
+
[--body '<json>'|--body-file <path>]
|
|
116
|
+
[--header '<json>'] [--query '<json>'] [--timeout <s>]
|
|
113
117
|
|
|
114
118
|
kweaver vega health|stats|inspect
|
|
115
119
|
kweaver vega catalog list|get|health|test-connection|discover|resources [options]
|
package/dist/client.d.ts
CHANGED
|
@@ -7,6 +7,7 @@ import { DataViewsResource } from "./resources/dataviews.js";
|
|
|
7
7
|
import { KnowledgeNetworksResource } from "./resources/knowledge-networks.js";
|
|
8
8
|
import { BknResource } from "./resources/bkn.js";
|
|
9
9
|
import { SkillsResource } from "./resources/skills.js";
|
|
10
|
+
import { ToolboxesResource } from "./resources/toolboxes.js";
|
|
10
11
|
import { VegaResource } from "./resources/vega.js";
|
|
11
12
|
/**
|
|
12
13
|
* Shared credentials passed to every resource method.
|
|
@@ -102,6 +103,8 @@ export declare class KWeaverClient implements ClientContext {
|
|
|
102
103
|
readonly vega: VegaResource;
|
|
103
104
|
/** ADP/KWeaver skill registry, market, progressive read, and install helpers. */
|
|
104
105
|
readonly skills: SkillsResource;
|
|
106
|
+
/** Toolbox / tool management plus execute & debug invocation. */
|
|
107
|
+
readonly toolboxes: ToolboxesResource;
|
|
105
108
|
constructor(opts?: KWeaverClientOptions);
|
|
106
109
|
/**
|
|
107
110
|
* Async factory that auto-refreshes expired or revoked tokens.
|
package/dist/client.js
CHANGED
|
@@ -12,6 +12,7 @@ import { DataViewsResource } from "./resources/dataviews.js";
|
|
|
12
12
|
import { KnowledgeNetworksResource } from "./resources/knowledge-networks.js";
|
|
13
13
|
import { BknResource } from "./resources/bkn.js";
|
|
14
14
|
import { SkillsResource } from "./resources/skills.js";
|
|
15
|
+
import { ToolboxesResource } from "./resources/toolboxes.js";
|
|
15
16
|
import { VegaResource } from "./resources/vega.js";
|
|
16
17
|
// ── KWeaverClient ─────────────────────────────────────────────────────────────
|
|
17
18
|
/**
|
|
@@ -64,6 +65,8 @@ export class KWeaverClient {
|
|
|
64
65
|
vega;
|
|
65
66
|
/** ADP/KWeaver skill registry, market, progressive read, and install helpers. */
|
|
66
67
|
skills;
|
|
68
|
+
/** Toolbox / tool management plus execute & debug invocation. */
|
|
69
|
+
toolboxes;
|
|
67
70
|
constructor(opts = {}) {
|
|
68
71
|
const envDomain = process.env.KWEAVER_BUSINESS_DOMAIN;
|
|
69
72
|
if (opts.auth === false && opts.config) {
|
|
@@ -97,6 +100,7 @@ export class KWeaverClient {
|
|
|
97
100
|
this.dataviews = new DataViewsResource(this);
|
|
98
101
|
this.vega = new VegaResource(this);
|
|
99
102
|
this.skills = new SkillsResource(this);
|
|
103
|
+
this.toolboxes = new ToolboxesResource(this);
|
|
100
104
|
return;
|
|
101
105
|
}
|
|
102
106
|
if (opts.config) {
|
|
@@ -151,6 +155,7 @@ export class KWeaverClient {
|
|
|
151
155
|
this.dataviews = new DataViewsResource(this);
|
|
152
156
|
this.vega = new VegaResource(this);
|
|
153
157
|
this.skills = new SkillsResource(this);
|
|
158
|
+
this.toolboxes = new ToolboxesResource(this);
|
|
154
159
|
}
|
|
155
160
|
/**
|
|
156
161
|
* Async factory that auto-refreshes expired or revoked tokens.
|
|
@@ -95,6 +95,33 @@ export interface KnActionTypeExecuteOptions {
|
|
|
95
95
|
timeout: number;
|
|
96
96
|
}
|
|
97
97
|
export declare function parseKnActionTypeExecuteArgs(args: string[]): KnActionTypeExecuteOptions;
|
|
98
|
+
/**
|
|
99
|
+
* Assemble the action-type execute envelope from CLI flags. Each flag is
|
|
100
|
+
* parsed as JSON; instance entries must be JSON objects; dynamic_params must
|
|
101
|
+
* be a JSON object. The shape produced is the contract documented in
|
|
102
|
+
* skills/kweaver-core/references/bkn.md.
|
|
103
|
+
*/
|
|
104
|
+
export declare function buildExecuteEnvelope(opts: {
|
|
105
|
+
triggerType: string;
|
|
106
|
+
dynamicParamsJson?: string;
|
|
107
|
+
instanceJsons: string[];
|
|
108
|
+
}): string;
|
|
109
|
+
export interface InputParameterSummary {
|
|
110
|
+
name: string;
|
|
111
|
+
type?: string;
|
|
112
|
+
source?: string;
|
|
113
|
+
required?: boolean;
|
|
114
|
+
description?: string;
|
|
115
|
+
}
|
|
116
|
+
/**
|
|
117
|
+
* Walk a getActionType response and collect parameters where
|
|
118
|
+
* `value_from === "input"`. The exact response shape varies (sometimes the
|
|
119
|
+
* action-type is at the root, sometimes nested under data/result/...), so we
|
|
120
|
+
* search a few likely locations.
|
|
121
|
+
*/
|
|
122
|
+
export declare function extractInputParameters(rawJson: string): InputParameterSummary[];
|
|
123
|
+
export declare function buildDynamicParamsTemplate(inputs: InputParameterSummary[]): Record<string, unknown>;
|
|
124
|
+
export declare function renderInputsTable(atId: string, inputs: InputParameterSummary[]): string;
|
|
98
125
|
/** Parse relation-type create args: --name --source --target [--mapping src:tgt ...] */
|
|
99
126
|
export declare function parseRelationTypeCreateArgs(args: string[]): {
|
|
100
127
|
knId: string;
|
|
@@ -562,6 +562,9 @@ export function parseKnActionTypeExecuteArgs(args) {
|
|
|
562
562
|
let businessDomain = "";
|
|
563
563
|
let wait = true;
|
|
564
564
|
let timeout = 300;
|
|
565
|
+
let dynamicParamsJson;
|
|
566
|
+
let triggerType;
|
|
567
|
+
const instanceJsons = [];
|
|
565
568
|
const positional = [];
|
|
566
569
|
for (let i = 0; i < args.length; i += 1) {
|
|
567
570
|
const arg = args[i];
|
|
@@ -592,11 +595,41 @@ export function parseKnActionTypeExecuteArgs(args) {
|
|
|
592
595
|
i += 1;
|
|
593
596
|
continue;
|
|
594
597
|
}
|
|
598
|
+
if (arg === "--dynamic-params" && args[i + 1]) {
|
|
599
|
+
dynamicParamsJson = args[++i];
|
|
600
|
+
continue;
|
|
601
|
+
}
|
|
602
|
+
if (arg === "--instance" && args[i + 1]) {
|
|
603
|
+
instanceJsons.push(args[++i]);
|
|
604
|
+
continue;
|
|
605
|
+
}
|
|
606
|
+
if (arg === "--trigger-type" && args[i + 1]) {
|
|
607
|
+
triggerType = args[++i];
|
|
608
|
+
continue;
|
|
609
|
+
}
|
|
595
610
|
positional.push(arg);
|
|
596
611
|
}
|
|
597
|
-
const
|
|
598
|
-
|
|
599
|
-
|
|
612
|
+
const usingFlags = dynamicParamsJson !== undefined || instanceJsons.length > 0 || triggerType !== undefined;
|
|
613
|
+
const [knId, atId, positionalBody] = positional;
|
|
614
|
+
if (!knId || !atId) {
|
|
615
|
+
throw new Error("Missing kn-id or at-id. Usage: kweaver bkn action-type execute <kn-id> <at-id> [<json>|--dynamic-params '<json>' --instance '<json>'] [options]");
|
|
616
|
+
}
|
|
617
|
+
if (positionalBody && usingFlags) {
|
|
618
|
+
throw new Error("Positional body and --dynamic-params/--instance/--trigger-type are mutually exclusive. Use one form.");
|
|
619
|
+
}
|
|
620
|
+
if (!positionalBody && !usingFlags) {
|
|
621
|
+
throw new Error("Missing body. Provide a positional JSON envelope, or use --dynamic-params / --instance / --trigger-type.");
|
|
622
|
+
}
|
|
623
|
+
let body;
|
|
624
|
+
if (positionalBody) {
|
|
625
|
+
body = positionalBody;
|
|
626
|
+
}
|
|
627
|
+
else {
|
|
628
|
+
body = buildExecuteEnvelope({
|
|
629
|
+
triggerType: triggerType ?? "manual",
|
|
630
|
+
dynamicParamsJson,
|
|
631
|
+
instanceJsons,
|
|
632
|
+
});
|
|
600
633
|
}
|
|
601
634
|
if (!businessDomain)
|
|
602
635
|
businessDomain = resolveBusinessDomain();
|
|
@@ -610,6 +643,143 @@ export function parseKnActionTypeExecuteArgs(args) {
|
|
|
610
643
|
timeout,
|
|
611
644
|
};
|
|
612
645
|
}
|
|
646
|
+
/**
|
|
647
|
+
* Assemble the action-type execute envelope from CLI flags. Each flag is
|
|
648
|
+
* parsed as JSON; instance entries must be JSON objects; dynamic_params must
|
|
649
|
+
* be a JSON object. The shape produced is the contract documented in
|
|
650
|
+
* skills/kweaver-core/references/bkn.md.
|
|
651
|
+
*/
|
|
652
|
+
export function buildExecuteEnvelope(opts) {
|
|
653
|
+
const envelope = {
|
|
654
|
+
trigger_type: opts.triggerType,
|
|
655
|
+
_instance_identities: opts.instanceJsons.map((s, idx) => {
|
|
656
|
+
let parsed;
|
|
657
|
+
try {
|
|
658
|
+
parsed = JSON.parse(s);
|
|
659
|
+
}
|
|
660
|
+
catch (e) {
|
|
661
|
+
throw new Error(`--instance #${idx + 1} is not valid JSON: ${e.message}`);
|
|
662
|
+
}
|
|
663
|
+
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
664
|
+
throw new Error(`--instance #${idx + 1} must be a JSON object, got ${Array.isArray(parsed) ? "array" : typeof parsed}`);
|
|
665
|
+
}
|
|
666
|
+
return parsed;
|
|
667
|
+
}),
|
|
668
|
+
};
|
|
669
|
+
if (opts.dynamicParamsJson !== undefined) {
|
|
670
|
+
let parsed;
|
|
671
|
+
try {
|
|
672
|
+
parsed = JSON.parse(opts.dynamicParamsJson);
|
|
673
|
+
}
|
|
674
|
+
catch (e) {
|
|
675
|
+
throw new Error(`--dynamic-params is not valid JSON: ${e.message}`);
|
|
676
|
+
}
|
|
677
|
+
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
678
|
+
throw new Error(`--dynamic-params must be a JSON object, got ${Array.isArray(parsed) ? "array" : typeof parsed}`);
|
|
679
|
+
}
|
|
680
|
+
envelope.dynamic_params = parsed;
|
|
681
|
+
}
|
|
682
|
+
else {
|
|
683
|
+
envelope.dynamic_params = {};
|
|
684
|
+
}
|
|
685
|
+
return JSON.stringify(envelope);
|
|
686
|
+
}
|
|
687
|
+
/**
|
|
688
|
+
* Walk a getActionType response and collect parameters where
|
|
689
|
+
* `value_from === "input"`. The exact response shape varies (sometimes the
|
|
690
|
+
* action-type is at the root, sometimes nested under data/result/...), so we
|
|
691
|
+
* search a few likely locations.
|
|
692
|
+
*/
|
|
693
|
+
export function extractInputParameters(rawJson) {
|
|
694
|
+
let root;
|
|
695
|
+
try {
|
|
696
|
+
root = JSON.parse(rawJson);
|
|
697
|
+
}
|
|
698
|
+
catch {
|
|
699
|
+
return [];
|
|
700
|
+
}
|
|
701
|
+
const candidates = collectParameterArrays(root);
|
|
702
|
+
const seen = new Set();
|
|
703
|
+
const out = [];
|
|
704
|
+
for (const params of candidates) {
|
|
705
|
+
for (const p of params) {
|
|
706
|
+
if (!p || typeof p !== "object")
|
|
707
|
+
continue;
|
|
708
|
+
const obj = p;
|
|
709
|
+
if (obj.value_from !== "input")
|
|
710
|
+
continue;
|
|
711
|
+
const name = typeof obj.name === "string" ? obj.name : "";
|
|
712
|
+
if (!name || seen.has(name))
|
|
713
|
+
continue;
|
|
714
|
+
seen.add(name);
|
|
715
|
+
out.push({
|
|
716
|
+
name,
|
|
717
|
+
type: typeof obj.type === "string" ? obj.type : undefined,
|
|
718
|
+
source: typeof obj.source === "string" ? obj.source : undefined,
|
|
719
|
+
required: typeof obj.required === "boolean" ? obj.required : undefined,
|
|
720
|
+
description: typeof obj.description === "string" ? obj.description : undefined,
|
|
721
|
+
});
|
|
722
|
+
}
|
|
723
|
+
}
|
|
724
|
+
return out;
|
|
725
|
+
}
|
|
726
|
+
function collectParameterArrays(node, acc = []) {
|
|
727
|
+
if (!node)
|
|
728
|
+
return acc;
|
|
729
|
+
if (Array.isArray(node)) {
|
|
730
|
+
for (const item of node)
|
|
731
|
+
collectParameterArrays(item, acc);
|
|
732
|
+
return acc;
|
|
733
|
+
}
|
|
734
|
+
if (typeof node !== "object")
|
|
735
|
+
return acc;
|
|
736
|
+
const obj = node;
|
|
737
|
+
if (Array.isArray(obj.parameters))
|
|
738
|
+
acc.push(obj.parameters);
|
|
739
|
+
for (const v of Object.values(obj))
|
|
740
|
+
collectParameterArrays(v, acc);
|
|
741
|
+
return acc;
|
|
742
|
+
}
|
|
743
|
+
export function buildDynamicParamsTemplate(inputs) {
|
|
744
|
+
const tpl = {};
|
|
745
|
+
for (const p of inputs) {
|
|
746
|
+
tpl[p.name] = placeholderForType(p);
|
|
747
|
+
}
|
|
748
|
+
return tpl;
|
|
749
|
+
}
|
|
750
|
+
function placeholderForType(p) {
|
|
751
|
+
const hint = p.description ? ` (${p.description})` : "";
|
|
752
|
+
const t = (p.type ?? "").toLowerCase();
|
|
753
|
+
if (t === "int" || t === "integer" || t === "long" || t === "number" || t === "float" || t === "double")
|
|
754
|
+
return 0;
|
|
755
|
+
if (t === "bool" || t === "boolean")
|
|
756
|
+
return false;
|
|
757
|
+
if (t === "array" || t === "list")
|
|
758
|
+
return [];
|
|
759
|
+
if (t === "object" || t === "dict" || t === "map")
|
|
760
|
+
return {};
|
|
761
|
+
return `<${p.type ?? "string"}${p.required === false ? "?" : ""}>${hint}`;
|
|
762
|
+
}
|
|
763
|
+
export function renderInputsTable(atId, inputs) {
|
|
764
|
+
if (inputs.length === 0) {
|
|
765
|
+
return `Action type ${atId} has no parameters with value_from=input. dynamic_params can be {}.`;
|
|
766
|
+
}
|
|
767
|
+
const rows = inputs.map(p => [
|
|
768
|
+
p.name,
|
|
769
|
+
p.type ?? "-",
|
|
770
|
+
p.source ?? "-",
|
|
771
|
+
p.required === undefined ? "-" : p.required ? "yes" : "no",
|
|
772
|
+
truncate(p.description ?? "", 60),
|
|
773
|
+
]);
|
|
774
|
+
const header = ["NAME", "TYPE", "SOURCE", "REQUIRED", "DESCRIPTION"];
|
|
775
|
+
const widths = header.map((h, i) => Math.max(h.length, ...rows.map(r => r[i].length)));
|
|
776
|
+
const fmt = (cols) => cols.map((c, i) => c.padEnd(widths[i])).join(" ");
|
|
777
|
+
const lines = [fmt(header), fmt(widths.map(w => "-".repeat(w))), ...rows.map(fmt)];
|
|
778
|
+
return `Action type ${atId} input parameters (value_from=input):\n${lines.join("\n")}`;
|
|
779
|
+
}
|
|
780
|
+
function truncate(s, n) {
|
|
781
|
+
return s.length <= n ? s : s.slice(0, n - 1) + "…";
|
|
782
|
+
}
|
|
613
783
|
// ── Action-type execute helpers ────────────────────────────────────────────────
|
|
614
784
|
const TERMINAL_STATUSES = ["SUCCESS", "FAILED", "CANCELLED"];
|
|
615
785
|
function extractExecutionId(body) {
|
|
@@ -1123,17 +1293,30 @@ kweaver bkn action-type create <kn-id> '<json>' [--pretty] [-bd value]
|
|
|
1123
1293
|
kweaver bkn action-type update <kn-id> <at-id> '<json>' [--pretty] [-bd value]
|
|
1124
1294
|
kweaver bkn action-type delete <kn-id> <at-ids> [-y] [--pretty] [-bd value]
|
|
1125
1295
|
kweaver bkn action-type query <kn-id> <at-id> '<json>' [--pretty] [-bd value]
|
|
1126
|
-
kweaver bkn action-type
|
|
1296
|
+
kweaver bkn action-type inputs <kn-id> <at-id> [--json|--template] [-bd value]
|
|
1297
|
+
kweaver bkn action-type execute <kn-id> <at-id> [<json>|--dynamic-params '<json>' --instance '<json>' --trigger-type <v>] [--pretty] [-bd value] [--wait|--no-wait] [--timeout n]
|
|
1127
1298
|
|
|
1128
1299
|
list: List action types (schema) from ontology-manager.
|
|
1129
1300
|
get: Get a single action type by ID.
|
|
1130
1301
|
create: Create action type(s) (POST JSON body).
|
|
1131
1302
|
update: Update an action type (PUT JSON body).
|
|
1132
1303
|
delete: Delete action type(s) by ID(s).
|
|
1133
|
-
query
|
|
1304
|
+
query: Query actions backing this action type.
|
|
1305
|
+
inputs: List parameters with value_from=input that the caller MUST supply.
|
|
1306
|
+
Default prints a table + a starter dynamic_params template.
|
|
1307
|
+
--json dump filtered parameters as raw JSON
|
|
1308
|
+
--template print only the dynamic_params template object
|
|
1309
|
+
execute: Run an action (has side effects - only use when explicitly requested).
|
|
1310
|
+
Body forms (mutually exclusive):
|
|
1311
|
+
1. Positional envelope JSON: '{"trigger_type":"manual","_instance_identities":[],"dynamic_params":{...}}'
|
|
1312
|
+
2. Flag form (CLI assembles the envelope):
|
|
1313
|
+
--dynamic-params '<json object>' parameters with value_from=input
|
|
1314
|
+
--instance '<json object>' repeatable; one per identity
|
|
1315
|
+
--trigger-type <value> defaults to "manual"
|
|
1134
1316
|
--wait (default) Poll until execution completes
|
|
1135
1317
|
--no-wait Return immediately after starting execution
|
|
1136
|
-
--timeout <seconds> Max wait time when --wait (default: 300)
|
|
1318
|
+
--timeout <seconds> Max wait time when --wait (default: 300)
|
|
1319
|
+
See skills/kweaver-core/references/bkn.md for the full payload contract.`);
|
|
1137
1320
|
return 0;
|
|
1138
1321
|
}
|
|
1139
1322
|
if (action === "list") {
|
|
@@ -1283,6 +1466,48 @@ query/execute: Query or execute actions. execute has side effects - only use whe
|
|
|
1283
1466
|
return 1;
|
|
1284
1467
|
}
|
|
1285
1468
|
}
|
|
1469
|
+
if (action === "inputs") {
|
|
1470
|
+
const parsed = parseOntologyQueryFlags(rest);
|
|
1471
|
+
const flags = new Set(parsed.filteredArgs.filter(a => a.startsWith("--")));
|
|
1472
|
+
const positional = parsed.filteredArgs.filter(a => !a.startsWith("--"));
|
|
1473
|
+
const [knId, atId] = positional;
|
|
1474
|
+
if (!knId || !atId) {
|
|
1475
|
+
console.error("Usage: kweaver bkn action-type inputs <kn-id> <at-id> [--json|--template]");
|
|
1476
|
+
return 1;
|
|
1477
|
+
}
|
|
1478
|
+
if (flags.has("--json") && flags.has("--template")) {
|
|
1479
|
+
console.error("--json and --template are mutually exclusive.");
|
|
1480
|
+
return 1;
|
|
1481
|
+
}
|
|
1482
|
+
try {
|
|
1483
|
+
const token = await ensureValidToken();
|
|
1484
|
+
const raw = await getActionType({
|
|
1485
|
+
baseUrl: token.baseUrl,
|
|
1486
|
+
accessToken: token.accessToken,
|
|
1487
|
+
knId,
|
|
1488
|
+
atId,
|
|
1489
|
+
businessDomain: parsed.businessDomain,
|
|
1490
|
+
});
|
|
1491
|
+
const inputs = extractInputParameters(raw);
|
|
1492
|
+
if (flags.has("--json")) {
|
|
1493
|
+
console.log(formatCallOutput(JSON.stringify(inputs), parsed.pretty));
|
|
1494
|
+
return 0;
|
|
1495
|
+
}
|
|
1496
|
+
const template = buildDynamicParamsTemplate(inputs);
|
|
1497
|
+
if (flags.has("--template")) {
|
|
1498
|
+
console.log(JSON.stringify(template, null, 2));
|
|
1499
|
+
return 0;
|
|
1500
|
+
}
|
|
1501
|
+
console.log(renderInputsTable(atId, inputs));
|
|
1502
|
+
console.log("\n# Starter dynamic_params (fill in real values, then pass via --dynamic-params):");
|
|
1503
|
+
console.log(JSON.stringify(template, null, 2));
|
|
1504
|
+
return 0;
|
|
1505
|
+
}
|
|
1506
|
+
catch (error) {
|
|
1507
|
+
console.error(formatHttpError(error));
|
|
1508
|
+
return 1;
|
|
1509
|
+
}
|
|
1510
|
+
}
|
|
1286
1511
|
if (action === "execute") {
|
|
1287
1512
|
let options;
|
|
1288
1513
|
try {
|
|
@@ -1349,7 +1574,7 @@ query/execute: Query or execute actions. execute has side effects - only use whe
|
|
|
1349
1574
|
return 1;
|
|
1350
1575
|
}
|
|
1351
1576
|
}
|
|
1352
|
-
console.error(`Unknown action-type action: ${action}. Use list, get, create, update, delete, query, or execute.`);
|
|
1577
|
+
console.error(`Unknown action-type action: ${action}. Use list, get, create, update, delete, query, inputs, or execute.`);
|
|
1353
1578
|
return 1;
|
|
1354
1579
|
}
|
|
1355
1580
|
export function parseConceptGroupArgs(args) {
|
package/dist/commands/bkn.js
CHANGED
|
@@ -393,7 +393,8 @@ Subcommands:
|
|
|
393
393
|
action-type update <kn-id> <at-id> '<json>' Update action type
|
|
394
394
|
action-type delete <kn-id> <at-ids> [-y] Delete action type(s)
|
|
395
395
|
action-type query <kn-id> <at-id> '<json>' Query action info
|
|
396
|
-
action-type
|
|
396
|
+
action-type inputs <kn-id> <at-id> List value_from=input params + dynamic_params template
|
|
397
|
+
action-type execute <kn-id> <at-id> '<envelope-json>' | --dynamic-params '<json>' [--instance '<json>']... [--trigger-type <v>] Execute action (has side effects)
|
|
397
398
|
action-execution get <kn-id> <execution-id> Get execution status
|
|
398
399
|
action-log list <kn-id> [options] List action execution logs
|
|
399
400
|
action-log get <kn-id> <log-id> Get single execution log
|
package/dist/commands/tool.d.ts
CHANGED
|
@@ -14,3 +14,15 @@ export interface ToolStatusOptions {
|
|
|
14
14
|
businessDomain: string;
|
|
15
15
|
}
|
|
16
16
|
export declare function parseToolStatusArgs(args: string[], status: "enabled" | "disabled"): ToolStatusOptions;
|
|
17
|
+
export interface ToolInvokeOptions {
|
|
18
|
+
boxId: string;
|
|
19
|
+
toolId: string;
|
|
20
|
+
header?: Record<string, unknown>;
|
|
21
|
+
query?: Record<string, unknown>;
|
|
22
|
+
body?: unknown;
|
|
23
|
+
bodyFile?: string;
|
|
24
|
+
timeout?: number;
|
|
25
|
+
businessDomain: string;
|
|
26
|
+
pretty: boolean;
|
|
27
|
+
}
|
|
28
|
+
export declare function parseToolInvokeArgs(args: string[]): ToolInvokeOptions;
|
package/dist/commands/tool.js
CHANGED
|
@@ -1,18 +1,29 @@
|
|
|
1
|
-
import { access } from "node:fs/promises";
|
|
1
|
+
import { access, readFile } from "node:fs/promises";
|
|
2
2
|
import { ensureValidToken, formatHttpError, with401RefreshRetry } from "../auth/oauth.js";
|
|
3
|
-
import { listTools, setToolStatuses, uploadTool } from "../api/toolboxes.js";
|
|
3
|
+
import { debugTool, executeTool, listTools, setToolStatuses, uploadTool } from "../api/toolboxes.js";
|
|
4
4
|
import { formatCallOutput } from "./call.js";
|
|
5
5
|
import { resolveBusinessDomain } from "../config/store.js";
|
|
6
6
|
const HELP = `kweaver tool
|
|
7
7
|
|
|
8
8
|
Subcommands:
|
|
9
9
|
upload --toolbox <box-id> <openapi-spec-path> [--metadata-type openapi]
|
|
10
|
-
|
|
11
|
-
list --toolbox <box-id>
|
|
12
|
-
enable --toolbox <box-id> <tool-id>...
|
|
13
|
-
disable --toolbox <box-id> <tool-id>...
|
|
10
|
+
Upload an OpenAPI spec file as a tool
|
|
11
|
+
list --toolbox <box-id> List tools in a toolbox
|
|
12
|
+
enable --toolbox <box-id> <tool-id>... Enable one or more tools
|
|
13
|
+
disable --toolbox <box-id> <tool-id>... Disable one or more tools
|
|
14
|
+
execute --toolbox <box-id> <tool-id> [--body '<json>'|--body-file <path>]
|
|
15
|
+
Invoke a published+enabled tool
|
|
16
|
+
debug --toolbox <box-id> <tool-id> [--body '<json>'|--body-file <path>]
|
|
17
|
+
Invoke a tool (works on draft/disabled too)
|
|
14
18
|
|
|
15
|
-
Options:
|
|
19
|
+
Options for execute/debug:
|
|
20
|
+
--header '<json>' Headers map forwarded to the downstream tool
|
|
21
|
+
(Authorization is auto-injected from current session
|
|
22
|
+
when --header omits it; pass {} to send none)
|
|
23
|
+
--query '<json>' Query params map forwarded to the downstream tool
|
|
24
|
+
--timeout <seconds> Per-call timeout (backend default applies when omitted)
|
|
25
|
+
|
|
26
|
+
Common options:
|
|
16
27
|
-bd, --biz-domain <s> Business domain (default: bd_public)
|
|
17
28
|
--pretty Pretty-print JSON (default)
|
|
18
29
|
--compact Single-line JSON (pipeline-friendly)`;
|
|
@@ -31,6 +42,10 @@ export async function runToolCommand(args) {
|
|
|
31
42
|
return runToolStatus(rest, "enabled");
|
|
32
43
|
if (subcommand === "disable")
|
|
33
44
|
return runToolStatus(rest, "disabled");
|
|
45
|
+
if (subcommand === "execute")
|
|
46
|
+
return runToolInvoke(rest, "execute");
|
|
47
|
+
if (subcommand === "debug")
|
|
48
|
+
return runToolInvoke(rest, "debug");
|
|
34
49
|
return Promise.resolve(-1);
|
|
35
50
|
};
|
|
36
51
|
try {
|
|
@@ -206,3 +221,158 @@ async function runToolStatus(args, status) {
|
|
|
206
221
|
console.error(`${status === "enabled" ? "Enabled" : "Disabled"} ${opts.toolIds.length} tool(s) in toolbox ${opts.boxId}`);
|
|
207
222
|
return 0;
|
|
208
223
|
}
|
|
224
|
+
function parseJsonOption(name, raw) {
|
|
225
|
+
let value;
|
|
226
|
+
try {
|
|
227
|
+
value = JSON.parse(raw);
|
|
228
|
+
}
|
|
229
|
+
catch (e) {
|
|
230
|
+
throw new Error(`${name} must be valid JSON: ${e.message}`);
|
|
231
|
+
}
|
|
232
|
+
if (value === null || typeof value !== "object" || Array.isArray(value)) {
|
|
233
|
+
throw new Error(`${name} must be a JSON object`);
|
|
234
|
+
}
|
|
235
|
+
return value;
|
|
236
|
+
}
|
|
237
|
+
export function parseToolInvokeArgs(args) {
|
|
238
|
+
let boxId = "";
|
|
239
|
+
let toolId = "";
|
|
240
|
+
let businessDomain = "";
|
|
241
|
+
let pretty = true;
|
|
242
|
+
let header;
|
|
243
|
+
let query;
|
|
244
|
+
let body;
|
|
245
|
+
let bodyProvided = false;
|
|
246
|
+
let bodyFile;
|
|
247
|
+
let timeout;
|
|
248
|
+
for (let i = 0; i < args.length; i += 1) {
|
|
249
|
+
const a = args[i];
|
|
250
|
+
if (a === "--toolbox" && args[i + 1]) {
|
|
251
|
+
boxId = args[++i];
|
|
252
|
+
continue;
|
|
253
|
+
}
|
|
254
|
+
if (a === "--header" && args[i + 1]) {
|
|
255
|
+
header = parseJsonOption("--header", args[++i]);
|
|
256
|
+
continue;
|
|
257
|
+
}
|
|
258
|
+
if (a === "--query" && args[i + 1]) {
|
|
259
|
+
query = parseJsonOption("--query", args[++i]);
|
|
260
|
+
continue;
|
|
261
|
+
}
|
|
262
|
+
if (a === "--body" && args[i + 1]) {
|
|
263
|
+
const raw = args[++i];
|
|
264
|
+
try {
|
|
265
|
+
body = JSON.parse(raw);
|
|
266
|
+
}
|
|
267
|
+
catch (e) {
|
|
268
|
+
throw new Error(`--body must be valid JSON: ${e.message}`);
|
|
269
|
+
}
|
|
270
|
+
bodyProvided = true;
|
|
271
|
+
continue;
|
|
272
|
+
}
|
|
273
|
+
if (a === "--body-file" && args[i + 1]) {
|
|
274
|
+
bodyFile = args[++i];
|
|
275
|
+
bodyProvided = true;
|
|
276
|
+
continue;
|
|
277
|
+
}
|
|
278
|
+
if (a === "--timeout" && args[i + 1]) {
|
|
279
|
+
const t = Number(args[++i]);
|
|
280
|
+
if (!Number.isFinite(t) || t <= 0)
|
|
281
|
+
throw new Error("--timeout must be a positive number");
|
|
282
|
+
timeout = t;
|
|
283
|
+
continue;
|
|
284
|
+
}
|
|
285
|
+
if ((a === "-bd" || a === "--biz-domain") && args[i + 1]) {
|
|
286
|
+
businessDomain = args[++i];
|
|
287
|
+
continue;
|
|
288
|
+
}
|
|
289
|
+
if (a === "--pretty") {
|
|
290
|
+
pretty = true;
|
|
291
|
+
continue;
|
|
292
|
+
}
|
|
293
|
+
if (a === "--compact") {
|
|
294
|
+
pretty = false;
|
|
295
|
+
continue;
|
|
296
|
+
}
|
|
297
|
+
if (!a.startsWith("-") && !toolId) {
|
|
298
|
+
toolId = a;
|
|
299
|
+
continue;
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
if (!boxId)
|
|
303
|
+
throw new Error("Missing required flag: --toolbox");
|
|
304
|
+
if (!toolId)
|
|
305
|
+
throw new Error("Missing required positional argument: <tool-id>");
|
|
306
|
+
if (bodyFile && body !== undefined)
|
|
307
|
+
throw new Error("--body and --body-file are mutually exclusive");
|
|
308
|
+
if (!businessDomain)
|
|
309
|
+
businessDomain = resolveBusinessDomain();
|
|
310
|
+
return {
|
|
311
|
+
boxId,
|
|
312
|
+
toolId,
|
|
313
|
+
header,
|
|
314
|
+
query,
|
|
315
|
+
body: bodyProvided ? body : undefined,
|
|
316
|
+
bodyFile,
|
|
317
|
+
timeout,
|
|
318
|
+
businessDomain,
|
|
319
|
+
pretty,
|
|
320
|
+
};
|
|
321
|
+
}
|
|
322
|
+
async function loadBodyFile(path) {
|
|
323
|
+
let raw;
|
|
324
|
+
try {
|
|
325
|
+
raw = await readFile(path, "utf8");
|
|
326
|
+
}
|
|
327
|
+
catch (e) {
|
|
328
|
+
throw new Error(`Cannot read --body-file ${path}: ${e.message}`);
|
|
329
|
+
}
|
|
330
|
+
try {
|
|
331
|
+
return JSON.parse(raw);
|
|
332
|
+
}
|
|
333
|
+
catch (e) {
|
|
334
|
+
throw new Error(`--body-file ${path} is not valid JSON: ${e.message}`);
|
|
335
|
+
}
|
|
336
|
+
}
|
|
337
|
+
async function runToolInvoke(args, action) {
|
|
338
|
+
let opts;
|
|
339
|
+
try {
|
|
340
|
+
opts = parseToolInvokeArgs(args);
|
|
341
|
+
}
|
|
342
|
+
catch (e) {
|
|
343
|
+
console.error(e instanceof Error ? e.message : String(e));
|
|
344
|
+
return 1;
|
|
345
|
+
}
|
|
346
|
+
let body = opts.body;
|
|
347
|
+
if (opts.bodyFile !== undefined) {
|
|
348
|
+
try {
|
|
349
|
+
body = await loadBodyFile(opts.bodyFile);
|
|
350
|
+
}
|
|
351
|
+
catch (e) {
|
|
352
|
+
console.error(e instanceof Error ? e.message : String(e));
|
|
353
|
+
return 1;
|
|
354
|
+
}
|
|
355
|
+
}
|
|
356
|
+
const token = await ensureValidToken();
|
|
357
|
+
// Auto-inject Authorization unless caller already provided one — most tools
|
|
358
|
+
// declare an `Authorization` header parameter and would otherwise be called
|
|
359
|
+
// anonymously, which the downstream tool answers with 401 token expired.
|
|
360
|
+
const header = { ...(opts.header ?? {}) };
|
|
361
|
+
const hasAuth = Object.keys(header).some((k) => k.toLowerCase() === "authorization");
|
|
362
|
+
if (!hasAuth)
|
|
363
|
+
header.Authorization = `Bearer ${token.accessToken}`;
|
|
364
|
+
const fn = action === "execute" ? executeTool : debugTool;
|
|
365
|
+
const responseBody = await fn({
|
|
366
|
+
baseUrl: token.baseUrl,
|
|
367
|
+
accessToken: token.accessToken,
|
|
368
|
+
businessDomain: opts.businessDomain,
|
|
369
|
+
boxId: opts.boxId,
|
|
370
|
+
toolId: opts.toolId,
|
|
371
|
+
header,
|
|
372
|
+
query: opts.query,
|
|
373
|
+
body,
|
|
374
|
+
timeout: opts.timeout,
|
|
375
|
+
});
|
|
376
|
+
console.log(formatCallOutput(responseBody, opts.pretty));
|
|
377
|
+
return 0;
|
|
378
|
+
}
|
package/dist/index.d.ts
CHANGED
|
@@ -50,6 +50,8 @@ export { BknResource } from "./resources/bkn.js";
|
|
|
50
50
|
export { ConversationsResource } from "./resources/conversations.js";
|
|
51
51
|
export { ContextLoaderResource } from "./resources/context-loader.js";
|
|
52
52
|
export { SkillsResource } from "./resources/skills.js";
|
|
53
|
+
export { ToolboxesResource } from "./resources/toolboxes.js";
|
|
54
|
+
export type { InvokeToolArgs } from "./resources/toolboxes.js";
|
|
53
55
|
export type { SkillStatus, SkillSummary, SkillInfo, SkillFileSummary, SkillContentIndex, SkillFileReadResult, RegisterSkillResult, DeleteSkillResult, UpdateSkillStatusResult, SkillListResult, ListSkillsOptions, ListSkillMarketOptions, GetSkillOptions, RegisterSkillContentOptions, RegisterSkillZipOptions, UpdateSkillStatusOptions, ReadSkillFileOptions, DownloadSkillOptions, DownloadedSkillArchive, } from "./api/skills.js";
|
|
54
56
|
export { listSkills, listSkillMarket, getSkill, deleteSkill, updateSkillStatus, registerSkillContent, registerSkillZip, getSkillContentIndex, fetchSkillContent, readSkillFile, fetchSkillFile, downloadSkill, installSkillArchive, } from "./api/skills.js";
|
|
55
57
|
export type { ViewField, DataView, CreateDataViewOptions, GetDataViewOptions, ListDataViewsOptions, DeleteDataViewOptions, FindDataViewOptions, QueryDataViewOptions, DataViewQueryResult, } from "./api/dataviews.js";
|
|
@@ -57,6 +59,8 @@ export { parseDataView, createDataView, getDataView, listDataViews, deleteDataVi
|
|
|
57
59
|
export { DataViewsResource } from "./resources/dataviews.js";
|
|
58
60
|
export type { BusinessDomain, ListBusinessDomainsOptions } from "./api/business-domains.js";
|
|
59
61
|
export { listBusinessDomains } from "./api/business-domains.js";
|
|
62
|
+
export type { CreateToolboxOptions, DeleteToolboxOptions, SetToolboxStatusOptions, UploadToolOptions, SetToolStatusesOptions, ListToolboxesOptions, ListToolsOptions, InvokeToolOptions, } from "./api/toolboxes.js";
|
|
63
|
+
export { createToolbox, deleteToolbox, setToolboxStatus, uploadTool, setToolStatuses, listToolboxes, listTools, executeTool, debugTool, } from "./api/toolboxes.js";
|
|
60
64
|
export { HttpError, NetworkRequestError, fetchTextOrThrow } from "./utils/http.js";
|
|
61
65
|
export type { TokenConfig, ContextLoaderEntry, ContextLoaderConfig, } from "./config/store.js";
|
|
62
66
|
export type { UserProfile } from "./config/store.js";
|
package/dist/index.js
CHANGED
|
@@ -40,10 +40,12 @@ export { BknResource } from "./resources/bkn.js";
|
|
|
40
40
|
export { ConversationsResource } from "./resources/conversations.js";
|
|
41
41
|
export { ContextLoaderResource } from "./resources/context-loader.js";
|
|
42
42
|
export { SkillsResource } from "./resources/skills.js";
|
|
43
|
+
export { ToolboxesResource } from "./resources/toolboxes.js";
|
|
43
44
|
export { listSkills, listSkillMarket, getSkill, deleteSkill, updateSkillStatus, registerSkillContent, registerSkillZip, getSkillContentIndex, fetchSkillContent, readSkillFile, fetchSkillFile, downloadSkill, installSkillArchive, } from "./api/skills.js";
|
|
44
45
|
export { parseDataView, createDataView, getDataView, listDataViews, deleteDataView, findDataView, queryDataView, } from "./api/dataviews.js";
|
|
45
46
|
export { DataViewsResource } from "./resources/dataviews.js";
|
|
46
47
|
export { listBusinessDomains } from "./api/business-domains.js";
|
|
48
|
+
export { createToolbox, deleteToolbox, setToolboxStatus, uploadTool, setToolStatuses, listToolboxes, listTools, executeTool, debugTool, } from "./api/toolboxes.js";
|
|
47
49
|
// ── HTTP utilities ────────────────────────────────────────────────────────────
|
|
48
50
|
export { HttpError, NetworkRequestError, fetchTextOrThrow } from "./utils/http.js";
|
|
49
51
|
export { NO_AUTH_TOKEN, isNoAuth, saveNoAuthPlatform, autoSelectBusinessDomain, getConfigDir, getCurrentPlatform, getActiveUser, setActiveUser, listUsers, listUserProfiles, resolveUserId, extractUserId, } from "./config/store.js";
|
package/dist/resources/agents.js
CHANGED
|
@@ -11,11 +11,25 @@ export class AgentsResource {
|
|
|
11
11
|
const { keyword, ...rest } = opts;
|
|
12
12
|
const raw = await listAgents({ ...this.ctx.base(), name: keyword, ...rest });
|
|
13
13
|
const parsed = JSON.parse(raw);
|
|
14
|
-
const items =
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
14
|
+
const items = (() => {
|
|
15
|
+
if (Array.isArray(parsed))
|
|
16
|
+
return parsed;
|
|
17
|
+
if (!parsed || typeof parsed !== "object")
|
|
18
|
+
return [];
|
|
19
|
+
const obj = parsed;
|
|
20
|
+
if (Array.isArray(obj.entries))
|
|
21
|
+
return obj.entries;
|
|
22
|
+
if (Array.isArray(obj.data))
|
|
23
|
+
return obj.data;
|
|
24
|
+
if (obj.data && typeof obj.data === "object") {
|
|
25
|
+
const dataObj = obj.data;
|
|
26
|
+
if (Array.isArray(dataObj.records))
|
|
27
|
+
return dataObj.records;
|
|
28
|
+
if (Array.isArray(dataObj.entries))
|
|
29
|
+
return dataObj.entries;
|
|
30
|
+
}
|
|
31
|
+
return [];
|
|
32
|
+
})();
|
|
19
33
|
return items;
|
|
20
34
|
}
|
|
21
35
|
// ── Get by ID ────────────────────────────────────────────────────────────
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import type { ClientContext } from "../client.js";
|
|
2
|
+
export interface InvokeToolArgs {
|
|
3
|
+
/** Optional headers to forward to the downstream tool. Authorization is
|
|
4
|
+
* auto-injected from the client's access token when omitted; pass `{}` to
|
|
5
|
+
* send no headers. */
|
|
6
|
+
header?: Record<string, unknown>;
|
|
7
|
+
query?: Record<string, unknown>;
|
|
8
|
+
body?: unknown;
|
|
9
|
+
/** Per-call timeout in seconds (backend default applies when omitted). */
|
|
10
|
+
timeout?: number;
|
|
11
|
+
}
|
|
12
|
+
/** Toolbox / tool management on the agent-operator-integration service. */
|
|
13
|
+
export declare class ToolboxesResource {
|
|
14
|
+
private readonly ctx;
|
|
15
|
+
constructor(ctx: ClientContext);
|
|
16
|
+
list(opts?: {
|
|
17
|
+
keyword?: string;
|
|
18
|
+
limit?: number;
|
|
19
|
+
offset?: number;
|
|
20
|
+
}): Promise<string>;
|
|
21
|
+
listToolsIn(boxId: string): Promise<string>;
|
|
22
|
+
uploadTool(opts: {
|
|
23
|
+
boxId: string;
|
|
24
|
+
filePath: string;
|
|
25
|
+
metadataType?: "openapi";
|
|
26
|
+
}): Promise<string>;
|
|
27
|
+
setToolStatuses(opts: {
|
|
28
|
+
boxId: string;
|
|
29
|
+
updates: Array<{
|
|
30
|
+
toolId: string;
|
|
31
|
+
status: "enabled" | "disabled";
|
|
32
|
+
}>;
|
|
33
|
+
}): Promise<void>;
|
|
34
|
+
/** Execute a published+enabled tool through the toolbox proxy. */
|
|
35
|
+
execute(boxId: string, toolId: string, args?: InvokeToolArgs): Promise<string>;
|
|
36
|
+
/** Debug a tool through the toolbox proxy (works on draft/disabled tools too). */
|
|
37
|
+
debug(boxId: string, toolId: string, args?: InvokeToolArgs): Promise<string>;
|
|
38
|
+
private injectAuth;
|
|
39
|
+
}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { debugTool, executeTool, listTools, listToolboxes, setToolStatuses, uploadTool, } from "../api/toolboxes.js";
|
|
2
|
+
/** Toolbox / tool management on the agent-operator-integration service. */
|
|
3
|
+
export class ToolboxesResource {
|
|
4
|
+
ctx;
|
|
5
|
+
constructor(ctx) {
|
|
6
|
+
this.ctx = ctx;
|
|
7
|
+
}
|
|
8
|
+
async list(opts = {}) {
|
|
9
|
+
return listToolboxes({ ...this.ctx.base(), ...opts });
|
|
10
|
+
}
|
|
11
|
+
async listToolsIn(boxId) {
|
|
12
|
+
return listTools({ ...this.ctx.base(), boxId });
|
|
13
|
+
}
|
|
14
|
+
async uploadTool(opts) {
|
|
15
|
+
return uploadTool({
|
|
16
|
+
...this.ctx.base(),
|
|
17
|
+
boxId: opts.boxId,
|
|
18
|
+
filePath: opts.filePath,
|
|
19
|
+
metadataType: opts.metadataType,
|
|
20
|
+
});
|
|
21
|
+
}
|
|
22
|
+
async setToolStatuses(opts) {
|
|
23
|
+
await setToolStatuses({ ...this.ctx.base(), ...opts });
|
|
24
|
+
}
|
|
25
|
+
/** Execute a published+enabled tool through the toolbox proxy. */
|
|
26
|
+
async execute(boxId, toolId, args = {}) {
|
|
27
|
+
return executeTool({
|
|
28
|
+
...this.ctx.base(),
|
|
29
|
+
boxId,
|
|
30
|
+
toolId,
|
|
31
|
+
...this.injectAuth(args),
|
|
32
|
+
});
|
|
33
|
+
}
|
|
34
|
+
/** Debug a tool through the toolbox proxy (works on draft/disabled tools too). */
|
|
35
|
+
async debug(boxId, toolId, args = {}) {
|
|
36
|
+
return debugTool({
|
|
37
|
+
...this.ctx.base(),
|
|
38
|
+
boxId,
|
|
39
|
+
toolId,
|
|
40
|
+
...this.injectAuth(args),
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
// The forwarder requires every header the downstream tool expects to be set
|
|
44
|
+
// explicitly under `header`; most published tools declare an Authorization
|
|
45
|
+
// parameter and would otherwise see no token. Auto-inject the active
|
|
46
|
+
// session token unless the caller already provided one.
|
|
47
|
+
injectAuth(args) {
|
|
48
|
+
const header = { ...(args.header ?? {}) };
|
|
49
|
+
const hasAuth = Object.keys(header).some((k) => k.toLowerCase() === "authorization");
|
|
50
|
+
if (!hasAuth)
|
|
51
|
+
header.Authorization = `Bearer ${this.ctx.base().accessToken}`;
|
|
52
|
+
return { ...args, header };
|
|
53
|
+
}
|
|
54
|
+
}
|
package/package.json
CHANGED