@ryuhq/sdk 0.1.13 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +19 -6
- package/dist/agent-plugin.cjs +46 -0
- package/dist/agent-plugin.d.cts +42 -32
- package/dist/agent-plugin.d.ts +42 -32
- package/dist/agent-plugin.js +1 -1
- package/dist/agent.cjs +9 -0
- package/dist/agent.d.cts +377 -1
- package/dist/agent.d.ts +377 -1
- package/dist/agent.js +4 -2
- package/dist/app-Bkw7LlCK.d.ts +129 -0
- package/dist/app-DNaGmLVf.d.cts +129 -0
- package/dist/builder.cjs +1095 -0
- package/dist/builder.d.cts +212 -0
- package/dist/builder.d.ts +212 -0
- package/dist/builder.js +28 -0
- package/dist/chunk-A3RGEPDG.js +250 -0
- package/dist/chunk-FZSFZOIN.js +200 -0
- package/dist/{chunk-ODFEUVPW.js → chunk-HACAGK65.js} +1 -18
- package/dist/{chunk-AO2KJRDD.js → chunk-IEUQ3CDG.js} +125 -2
- package/dist/chunk-IKEDLLFY.js +19 -0
- package/dist/chunk-IOLP5FFE.js +354 -0
- package/dist/{chunk-G6FLVEC4.js → chunk-JX6DDRXV.js} +46 -0
- package/dist/chunk-T5676WL2.js +240 -0
- package/dist/chunk-TLDPEGC7.js +21 -0
- package/dist/chunk-TXSHHZF2.js +0 -0
- package/dist/{chunk-MTUBUPIV.js → chunk-ULSVL7EC.js} +8 -227
- package/dist/chunk-VLIRNNAE.js +154 -0
- package/dist/chunk-W3KPP4WN.js +135 -0
- package/dist/cli.cjs +258 -14
- package/dist/cli.js +96 -16
- package/dist/client-D5U6ssPc.d.cts +84 -0
- package/dist/client-D5U6ssPc.d.ts +84 -0
- package/dist/index.cjs +519 -5
- package/dist/index.d.cts +16 -632
- package/dist/index.d.ts +16 -632
- package/dist/index.js +63 -695
- package/dist/manifest.cjs +129 -3
- package/dist/manifest.d.cts +105 -2
- package/dist/manifest.d.ts +105 -2
- package/dist/manifest.js +7 -1
- package/dist/mcp/client.cjs +180 -0
- package/dist/mcp/client.d.cts +49 -0
- package/dist/mcp/client.d.ts +49 -0
- package/dist/mcp/client.js +10 -0
- package/dist/mcp/server.cjs +370 -0
- package/dist/mcp/server.d.cts +126 -0
- package/dist/mcp/server.d.ts +126 -0
- package/dist/mcp/server.js +9 -0
- package/dist/mcp.cjs +376 -0
- package/dist/mcp.d.cts +2 -0
- package/dist/mcp.d.ts +2 -0
- package/dist/mcp.js +17 -0
- package/dist/model.cjs +141 -0
- package/dist/model.d.cts +33 -0
- package/dist/model.d.ts +33 -0
- package/dist/model.js +18 -0
- package/dist/plugin.cjs +46 -0
- package/dist/plugin.d.cts +215 -0
- package/dist/plugin.d.ts +215 -0
- package/dist/plugin.js +8 -0
- package/dist/runnable.cjs +1230 -0
- package/dist/runnable.d.cts +271 -0
- package/dist/runnable.d.ts +271 -0
- package/dist/runnable.js +28 -0
- package/dist/{index-B6SkaAjJ.d.ts → tool-DSx2bFx8.d.ts} +35 -458
- package/dist/{index-BvAB5eMk.d.cts → tool-u-VR0fLF.d.cts} +35 -458
- package/package.json +38 -2
- package/src/agent/loop.test.ts +4 -4
- package/src/agent/tools.ts +3 -3
- package/src/agent-plugin.test.ts +58 -0
- package/src/agent-plugin.ts +108 -35
- package/src/cli/dev.test.ts +26 -47
- package/src/cli/dev.ts +10 -2
- package/src/cli.ts +98 -15
- package/src/exports-lockstep.test.ts +92 -0
- package/src/generated/plugin-manifest.ts +243 -27
- package/src/index.ts +35 -0
- package/src/manifest-schema.test.ts +30 -1
- package/src/manifest.fixtures.test.ts +13 -3
- package/src/manifest.test.ts +96 -10
- package/src/manifest.ts +334 -187
- package/src/mcp/index.ts +18 -0
- package/src/model/index.ts +22 -0
- package/src/plugin/ryu-plugin.ts +82 -0
- package/src/runnable/app.test.ts +2 -0
- package/src/runnable/app.ts +5 -2
- package/src/runnable/index.ts +2 -0
- package/src/runnable/primitives.ts +57 -0
- package/src/runnable/tool.ts +1 -1
- package/src/runnable/turn-hook.ts +4 -1
package/dist/index.js
CHANGED
|
@@ -1,7 +1,36 @@
|
|
|
1
|
+
import {
|
|
2
|
+
toDisposable
|
|
3
|
+
} from "./chunk-TLDPEGC7.js";
|
|
4
|
+
import {
|
|
5
|
+
defineAgent,
|
|
6
|
+
defineSkill,
|
|
7
|
+
defineTool,
|
|
8
|
+
defineWorkflow,
|
|
9
|
+
inlineToolRunnable
|
|
10
|
+
} from "./chunk-T5676WL2.js";
|
|
11
|
+
import {
|
|
12
|
+
AgentBuilder,
|
|
13
|
+
AppBuilder,
|
|
14
|
+
PluginBuilder,
|
|
15
|
+
SkillBuilder,
|
|
16
|
+
ToolBuilder,
|
|
17
|
+
WorkflowBuilder,
|
|
18
|
+
agent,
|
|
19
|
+
app,
|
|
20
|
+
skill,
|
|
21
|
+
tool,
|
|
22
|
+
workflow
|
|
23
|
+
} from "./chunk-IOLP5FFE.js";
|
|
24
|
+
import {
|
|
25
|
+
appToolId,
|
|
26
|
+
defineApp
|
|
27
|
+
} from "./chunk-W3KPP4WN.js";
|
|
1
28
|
import {
|
|
2
29
|
AppDependencySchema,
|
|
3
30
|
CapabilityReqSchema,
|
|
4
31
|
CompanionSurfaceSchema,
|
|
32
|
+
McpServerAuthSchema,
|
|
33
|
+
McpServerDeclSchema,
|
|
5
34
|
PluginManifestSchema,
|
|
6
35
|
RequiresSchema,
|
|
7
36
|
RunnableKindSchema,
|
|
@@ -12,699 +41,38 @@ import {
|
|
|
12
41
|
coreManifestJsonSchema,
|
|
13
42
|
validateManifestStrict,
|
|
14
43
|
validatePluginId
|
|
15
|
-
} from "./chunk-
|
|
44
|
+
} from "./chunk-IEUQ3CDG.js";
|
|
16
45
|
import {
|
|
17
46
|
Agent,
|
|
18
|
-
PRIMITIVE_BINDINGS,
|
|
19
47
|
createAgent,
|
|
20
|
-
createPrimitives,
|
|
21
|
-
httpPrimitiveTransport,
|
|
22
48
|
query,
|
|
23
49
|
ryuTool
|
|
24
|
-
} from "./chunk-
|
|
50
|
+
} from "./chunk-ULSVL7EC.js";
|
|
51
|
+
import {
|
|
52
|
+
PRIMITIVE_BINDINGS,
|
|
53
|
+
createPrimitives,
|
|
54
|
+
httpPrimitiveTransport
|
|
55
|
+
} from "./chunk-A3RGEPDG.js";
|
|
25
56
|
import {
|
|
26
|
-
DEFAULT_GATEWAY_URL,
|
|
27
57
|
ModelClient,
|
|
58
|
+
defineModel
|
|
59
|
+
} from "./chunk-HACAGK65.js";
|
|
60
|
+
import {
|
|
61
|
+
DEFAULT_GATEWAY_URL,
|
|
28
62
|
assertAllowedEgressUrl,
|
|
29
|
-
defineModel,
|
|
30
63
|
resolveGatewayToken,
|
|
31
64
|
resolveGatewayUrl
|
|
32
|
-
} from "./chunk-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
return out;
|
|
44
|
-
}
|
|
45
|
-
function appToolId(server, name) {
|
|
46
|
-
return `${server}__${name}`;
|
|
47
|
-
}
|
|
48
|
-
function defineApp(options) {
|
|
49
|
-
const server = options.server ?? options.slug;
|
|
50
|
-
const uri = `ui://widget/${options.slug}.html`;
|
|
51
|
-
const mime = options.mime ?? DEFAULT_APP_WIDGET_MIME;
|
|
52
|
-
const displayMode = options.displayMode ?? DEFAULT_APP_DISPLAY_MODE;
|
|
53
|
-
const hasCompanions = options.tools.some((t) => t.accessible === true);
|
|
54
|
-
const runnables = [];
|
|
55
|
-
const widgets = [];
|
|
56
|
-
for (const spec of options.tools) {
|
|
57
|
-
const isRender = spec.accessible !== true;
|
|
58
|
-
const id = appToolId(server, spec.name);
|
|
59
|
-
const config = {
|
|
60
|
-
slug: id,
|
|
61
|
-
description: spec.description,
|
|
62
|
-
widget: isRender,
|
|
63
|
-
widget_accessible: isRender ? hasCompanions : true,
|
|
64
|
-
...spec.inputSchema ? { input_schema: spec.inputSchema } : {},
|
|
65
|
-
...spec.invoking ? { invoking: spec.invoking } : {},
|
|
66
|
-
...spec.invoked ? { invoked: spec.invoked } : {}
|
|
67
|
-
};
|
|
68
|
-
runnables.push({
|
|
69
|
-
id,
|
|
70
|
-
name: spec.name,
|
|
71
|
-
kind: "tool",
|
|
72
|
-
config
|
|
73
|
-
});
|
|
74
|
-
if (isRender) {
|
|
75
|
-
widgets.push({
|
|
76
|
-
tool_id: id,
|
|
77
|
-
uri,
|
|
78
|
-
ui_entry: options.uiEntry,
|
|
79
|
-
mime,
|
|
80
|
-
default_display_mode: displayMode
|
|
81
|
-
});
|
|
82
|
-
}
|
|
83
|
-
}
|
|
84
|
-
const contributes = {
|
|
85
|
-
turn_hooks: [],
|
|
86
|
-
// This builder synthesises an app from its runnables; an app that emits
|
|
87
|
-
// events declares them in a hand-authored `manifest.json`, same as
|
|
88
|
-
// `lsp_servers` below.
|
|
89
|
-
hook_events: [],
|
|
90
|
-
composer_controls: [],
|
|
91
|
-
settings_tabs: [],
|
|
92
|
-
slash_commands: [],
|
|
93
|
-
sidebar_sections: [],
|
|
94
|
-
sidebar_buttons: [],
|
|
95
|
-
dock_panels: [],
|
|
96
|
-
// Empty for the same reason as every sibling family above: this builder
|
|
97
|
-
// synthesises `widgets` from the app's own runnables and nothing else, and
|
|
98
|
-
// takes no `contributes` passthrough. An app that wants to declare language
|
|
99
|
-
// servers writes them in a hand-authored `manifest.json`.
|
|
100
|
-
lsp_servers: {},
|
|
101
|
-
// Same reason again: a danger-zone category, a Pi extension and an output
|
|
102
|
-
// style are all hand-authored declarations, not something derivable from
|
|
103
|
-
// runnables. An output style in particular points at a Markdown file next
|
|
104
|
-
// to the manifest, which this builder never writes.
|
|
105
|
-
data_categories: [],
|
|
106
|
-
pi_extensions: [],
|
|
107
|
-
output_styles: [],
|
|
108
|
-
widgets
|
|
109
|
-
};
|
|
110
|
-
const raw = {
|
|
111
|
-
id: options.id,
|
|
112
|
-
name: options.title,
|
|
113
|
-
version: options.version,
|
|
114
|
-
runnables,
|
|
115
|
-
// An app that synthesises widgets MUST hold `widget:render`, so this
|
|
116
|
-
// builder declares it rather than leaving the author to discover it.
|
|
117
|
-
//
|
|
118
|
-
// Core gates widget promotion on declared-AND-enabled-AND-granted, and a
|
|
119
|
-
// missing grant fails as `DeniedNoGrant` — which is an `info!` log and
|
|
120
|
-
// nothing else. The widget silently renders as plain text, with no error
|
|
121
|
-
// in the UI and nothing pointing at the manifest. Every app scaffolded
|
|
122
|
-
// through `defineApp` hit that, because the only fix was a grant string
|
|
123
|
-
// the templates never mention and the builder never added; the one
|
|
124
|
-
// working example on disk hand-writes it.
|
|
125
|
-
//
|
|
126
|
-
// Added only when there is a widget to render, and unioned rather than
|
|
127
|
-
// overwritten so an author's own `grants` list survives and re-declaring
|
|
128
|
-
// it is not an error.
|
|
129
|
-
permission_grants: withWidgetRenderGrant(options.grants ?? [], widgets),
|
|
130
|
-
activation_events: options.activationEvents ?? ["*"],
|
|
131
|
-
contributes,
|
|
132
|
-
// `targets: []` means EVERY surface, so an app that declares none is
|
|
133
|
-
// unrestricted — the backward-compatible default.
|
|
134
|
-
targets: options.targets ?? [],
|
|
135
|
-
// `requires` stays ABSENT (not `{apps:[],grants:[]}`) when undeclared, so the
|
|
136
|
-
// emitted manifest carries no key at all — matching Core's
|
|
137
|
-
// `Option<Requires>` + `skip_serializing_if = "Option::is_none"`.
|
|
138
|
-
...options.requires ? {
|
|
139
|
-
requires: {
|
|
140
|
-
apps: options.requires.apps ?? [],
|
|
141
|
-
capabilities: options.requires.capabilities ?? [],
|
|
142
|
-
grants: options.requires.grants ?? []
|
|
143
|
-
}
|
|
144
|
-
} : {}
|
|
145
|
-
};
|
|
146
|
-
const result = PluginManifestSchema.safeParse(raw);
|
|
147
|
-
if (!result.success) {
|
|
148
|
-
const first = result.error.issues[0];
|
|
149
|
-
const field = first?.path.join(".") ?? "unknown";
|
|
150
|
-
const message = first?.message ?? "validation failed";
|
|
151
|
-
throw new Error(
|
|
152
|
-
`manifest.json validation failed at '${field}': ${message}`
|
|
153
|
-
);
|
|
154
|
-
}
|
|
155
|
-
return result.data;
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
// src/builder.ts
|
|
159
|
-
var RunnableBuilder = class {
|
|
160
|
-
_id = "";
|
|
161
|
-
_name = "";
|
|
162
|
-
id(value) {
|
|
163
|
-
this._id = value;
|
|
164
|
-
return this;
|
|
165
|
-
}
|
|
166
|
-
name(value) {
|
|
167
|
-
this._name = value;
|
|
168
|
-
return this;
|
|
169
|
-
}
|
|
170
|
-
};
|
|
171
|
-
var AgentBuilder = class extends RunnableBuilder {
|
|
172
|
-
build() {
|
|
173
|
-
const result = RunnableMetaSchema.safeParse({
|
|
174
|
-
id: this._id,
|
|
175
|
-
name: this._name,
|
|
176
|
-
kind: "agent"
|
|
177
|
-
});
|
|
178
|
-
if (!result.success) {
|
|
179
|
-
throw new Error(
|
|
180
|
-
`Invalid agent runnable: ${result.error.issues.map((i) => i.message).join("; ")}`
|
|
181
|
-
);
|
|
182
|
-
}
|
|
183
|
-
return result.data;
|
|
184
|
-
}
|
|
185
|
-
};
|
|
186
|
-
var WorkflowBuilder = class extends RunnableBuilder {
|
|
187
|
-
build() {
|
|
188
|
-
const result = RunnableMetaSchema.safeParse({
|
|
189
|
-
id: this._id,
|
|
190
|
-
name: this._name,
|
|
191
|
-
kind: "workflow"
|
|
192
|
-
});
|
|
193
|
-
if (!result.success) {
|
|
194
|
-
throw new Error(
|
|
195
|
-
`Invalid workflow runnable: ${result.error.issues.map((i) => i.message).join("; ")}`
|
|
196
|
-
);
|
|
197
|
-
}
|
|
198
|
-
return result.data;
|
|
199
|
-
}
|
|
200
|
-
};
|
|
201
|
-
var ToolBuilder = class extends RunnableBuilder {
|
|
202
|
-
build() {
|
|
203
|
-
const result = RunnableMetaSchema.safeParse({
|
|
204
|
-
id: this._id,
|
|
205
|
-
name: this._name,
|
|
206
|
-
kind: "tool"
|
|
207
|
-
});
|
|
208
|
-
if (!result.success) {
|
|
209
|
-
throw new Error(
|
|
210
|
-
`Invalid tool runnable: ${result.error.issues.map((i) => i.message).join("; ")}`
|
|
211
|
-
);
|
|
212
|
-
}
|
|
213
|
-
return result.data;
|
|
214
|
-
}
|
|
215
|
-
};
|
|
216
|
-
var SkillBuilder = class extends RunnableBuilder {
|
|
217
|
-
build() {
|
|
218
|
-
const result = RunnableMetaSchema.safeParse({
|
|
219
|
-
id: this._id,
|
|
220
|
-
name: this._name,
|
|
221
|
-
kind: "skill"
|
|
222
|
-
});
|
|
223
|
-
if (!result.success) {
|
|
224
|
-
throw new Error(
|
|
225
|
-
`Invalid skill runnable: ${result.error.issues.map((i) => i.message).join("; ")}`
|
|
226
|
-
);
|
|
227
|
-
}
|
|
228
|
-
return result.data;
|
|
229
|
-
}
|
|
230
|
-
};
|
|
231
|
-
var agent = () => new AgentBuilder();
|
|
232
|
-
var workflow = () => new WorkflowBuilder();
|
|
233
|
-
var tool = () => new ToolBuilder();
|
|
234
|
-
var skill = () => new SkillBuilder();
|
|
235
|
-
var PluginBuilder = class {
|
|
236
|
-
_id = "";
|
|
237
|
-
_name = "";
|
|
238
|
-
_version = "";
|
|
239
|
-
_runnables = [];
|
|
240
|
-
_grants = [];
|
|
241
|
-
_companion = void 0;
|
|
242
|
-
_dependencies = [];
|
|
243
|
-
_requiredCapabilities = [];
|
|
244
|
-
_requiredGrants = [];
|
|
245
|
-
_targets = [];
|
|
246
|
-
/** Set the reverse-domain app id (e.g. `"com.example.my-app"`). */
|
|
247
|
-
id(value) {
|
|
248
|
-
this._id = value;
|
|
249
|
-
return this;
|
|
250
|
-
}
|
|
251
|
-
/** Set the human-readable display name. */
|
|
252
|
-
name(value) {
|
|
253
|
-
this._name = value;
|
|
254
|
-
return this;
|
|
255
|
-
}
|
|
256
|
-
/** Set the semver version string (e.g. `"1.0.0"`). */
|
|
257
|
-
version(value) {
|
|
258
|
-
this._version = value;
|
|
259
|
-
return this;
|
|
260
|
-
}
|
|
261
|
-
/** Append a pre-built `RunnableMeta` (from any per-kind builder). */
|
|
262
|
-
runnable(meta) {
|
|
263
|
-
this._runnables.push(meta);
|
|
264
|
-
return this;
|
|
265
|
-
}
|
|
266
|
-
/** Declare a permission grant (e.g. `"mcp:web_search"`). */
|
|
267
|
-
grant(permission) {
|
|
268
|
-
this._grants.push(permission);
|
|
269
|
-
return this;
|
|
270
|
-
}
|
|
271
|
-
/** Set an optional Companion surface descriptor. */
|
|
272
|
-
companion(surface) {
|
|
273
|
-
this._companion = surface;
|
|
274
|
-
return this;
|
|
275
|
-
}
|
|
276
|
-
/**
|
|
277
|
-
* Declare a **plugin-to-plugin dependency**: `id` must be installed and is
|
|
278
|
-
* auto-enabled (in dependency order) before this plugin enables.
|
|
279
|
-
*
|
|
280
|
-
* `minVersion` is a MINIMUM — a bare `"1.2.0"` means `">=1.2.0"`, so an
|
|
281
|
-
* installed `2.0.0` satisfies it (comparator syntax like `">=1.2, <2"` is
|
|
282
|
-
* honoured verbatim).
|
|
283
|
-
*/
|
|
284
|
-
dependsOn(id, minVersion) {
|
|
285
|
-
this._dependencies.push(
|
|
286
|
-
minVersion ? { id, min_version: minVersion } : { id }
|
|
287
|
-
);
|
|
288
|
-
return this;
|
|
289
|
-
}
|
|
290
|
-
/**
|
|
291
|
-
* Declare a permission grant implied by this plugin's dependencies
|
|
292
|
-
* (`requires.grants`). Declaration only — the Gateway remains the sole
|
|
293
|
-
* authority on what a grant allows. Use {@link PluginBuilder.grant} for the
|
|
294
|
-
* grants this plugin needs in its own right.
|
|
295
|
-
*/
|
|
296
|
-
requiredGrant(permission) {
|
|
297
|
-
this._requiredGrants.push(permission);
|
|
298
|
-
return this;
|
|
299
|
-
}
|
|
300
|
-
/**
|
|
301
|
-
* Declare an abstract **capability** edge (`requires.capabilities`) the broker
|
|
302
|
-
* resolves to a bound provider at enable time — e.g. `requiresCapability("rag")`.
|
|
303
|
-
* Distinct from a specific-plugin dependency: a capability edge lets the
|
|
304
|
-
* binding registry choose the provider. `minVersion` is a MINIMUM (`"1.2.0"`
|
|
305
|
-
* = `">=1.2.0"`).
|
|
306
|
-
*/
|
|
307
|
-
requiresCapability(capability, minVersion) {
|
|
308
|
-
this._requiredCapabilities.push(
|
|
309
|
-
minVersion ? { capability, min_version: minVersion } : { capability }
|
|
310
|
-
);
|
|
311
|
-
return this;
|
|
312
|
-
}
|
|
313
|
-
/**
|
|
314
|
-
* Restrict this plugin to a host surface (`"desktop"`, `"island"`, …).
|
|
315
|
-
* Declaring NO target is the default and means **every** surface.
|
|
316
|
-
*/
|
|
317
|
-
target(surface) {
|
|
318
|
-
this._targets.push(surface);
|
|
319
|
-
return this;
|
|
320
|
-
}
|
|
321
|
-
/**
|
|
322
|
-
* Validate and return the assembled `PluginManifest`. Throws an `Error` with
|
|
323
|
-
* the failing field name and message when validation fails.
|
|
324
|
-
*/
|
|
325
|
-
build() {
|
|
326
|
-
const hasRequires = this._dependencies.length > 0 || this._requiredCapabilities.length > 0 || this._requiredGrants.length > 0;
|
|
327
|
-
const raw = {
|
|
328
|
-
id: this._id,
|
|
329
|
-
name: this._name,
|
|
330
|
-
version: this._version,
|
|
331
|
-
runnables: this._runnables,
|
|
332
|
-
permission_grants: this._grants,
|
|
333
|
-
companion: this._companion,
|
|
334
|
-
targets: this._targets,
|
|
335
|
-
...hasRequires ? {
|
|
336
|
-
requires: {
|
|
337
|
-
apps: this._dependencies,
|
|
338
|
-
capabilities: this._requiredCapabilities,
|
|
339
|
-
grants: this._requiredGrants
|
|
340
|
-
}
|
|
341
|
-
} : {}
|
|
342
|
-
};
|
|
343
|
-
const result = PluginManifestSchema.safeParse(raw);
|
|
344
|
-
if (!result.success) {
|
|
345
|
-
const first = result.error.issues[0];
|
|
346
|
-
const field = first?.path.join(".") ?? "unknown";
|
|
347
|
-
const message = first?.message ?? "validation failed";
|
|
348
|
-
throw new Error(
|
|
349
|
-
`manifest.json validation failed at '${field}': ${message}`
|
|
350
|
-
);
|
|
351
|
-
}
|
|
352
|
-
return result.data;
|
|
353
|
-
}
|
|
354
|
-
};
|
|
355
|
-
var AppBuilder = class {
|
|
356
|
-
_id = "";
|
|
357
|
-
_title = "";
|
|
358
|
-
_version = "";
|
|
359
|
-
_slug = "";
|
|
360
|
-
_server = void 0;
|
|
361
|
-
_displayMode = void 0;
|
|
362
|
-
_mime = void 0;
|
|
363
|
-
_uiEntry = "";
|
|
364
|
-
_grants = [];
|
|
365
|
-
_activationEvents = [];
|
|
366
|
-
_tools = [];
|
|
367
|
-
_dependencies = [];
|
|
368
|
-
_requiredCapabilities = [];
|
|
369
|
-
_requiredGrants = [];
|
|
370
|
-
_targets = [];
|
|
371
|
-
/** Set the reverse-domain app id (e.g. `"com.example.checklist"`). */
|
|
372
|
-
id(value) {
|
|
373
|
-
this._id = value;
|
|
374
|
-
return this;
|
|
375
|
-
}
|
|
376
|
-
/** Set the human-readable display name. */
|
|
377
|
-
title(value) {
|
|
378
|
-
this._title = value;
|
|
379
|
-
return this;
|
|
380
|
-
}
|
|
381
|
-
/** Set the semver version string (e.g. `"1.0.0"`). */
|
|
382
|
-
version(value) {
|
|
383
|
-
this._version = value;
|
|
384
|
-
return this;
|
|
385
|
-
}
|
|
386
|
-
/** Set the app slug (drives `ui://widget/<slug>.html` and the server default). */
|
|
387
|
-
slug(value) {
|
|
388
|
-
this._slug = value;
|
|
389
|
-
return this;
|
|
390
|
-
}
|
|
391
|
-
/** Override the MCP server namespace for tool ids (defaults to the slug). */
|
|
392
|
-
server(value) {
|
|
393
|
-
this._server = value;
|
|
394
|
-
return this;
|
|
395
|
-
}
|
|
396
|
-
/** Set the default widget display mode (`inline` | `fullscreen` | `pip`). */
|
|
397
|
-
displayMode(value) {
|
|
398
|
-
this._displayMode = value;
|
|
399
|
-
return this;
|
|
400
|
-
}
|
|
401
|
-
/** Override the widget MIME dialect (defaults to `text/html+skybridge`). */
|
|
402
|
-
mime(value) {
|
|
403
|
-
this._mime = value;
|
|
404
|
-
return this;
|
|
405
|
-
}
|
|
406
|
-
/** Set the widget UI source entry `ryu pack` bundles into `ui_code`. */
|
|
407
|
-
uiEntry(value) {
|
|
408
|
-
this._uiEntry = value;
|
|
409
|
-
return this;
|
|
410
|
-
}
|
|
411
|
-
/** Declare a permission grant (e.g. `"mcp:web_search"`). */
|
|
412
|
-
grant(permission) {
|
|
413
|
-
this._grants.push(permission);
|
|
414
|
-
return this;
|
|
415
|
-
}
|
|
416
|
-
/** Add a VS-Code-style activation event (empty = eager `["*"]`). */
|
|
417
|
-
activationEvent(event) {
|
|
418
|
-
this._activationEvents.push(event);
|
|
419
|
-
return this;
|
|
420
|
-
}
|
|
421
|
-
/** Append a tool spec (render tool unless `accessible:true`). */
|
|
422
|
-
tool(spec) {
|
|
423
|
-
this._tools.push(spec);
|
|
424
|
-
return this;
|
|
425
|
-
}
|
|
426
|
-
/**
|
|
427
|
-
* Declare a **plugin-to-plugin dependency** (auto-enabled, in dependency order,
|
|
428
|
-
* before this app). `minVersion` is a MINIMUM (`"1.2.0"` = `">=1.2.0"`).
|
|
429
|
-
*/
|
|
430
|
-
dependsOn(id, minVersion) {
|
|
431
|
-
this._dependencies.push(
|
|
432
|
-
minVersion ? { id, min_version: minVersion } : { id }
|
|
433
|
-
);
|
|
434
|
-
return this;
|
|
435
|
-
}
|
|
436
|
-
/** Declare a grant implied by this app's dependencies (`requires.grants`). */
|
|
437
|
-
requiredGrant(permission) {
|
|
438
|
-
this._requiredGrants.push(permission);
|
|
439
|
-
return this;
|
|
440
|
-
}
|
|
441
|
-
/**
|
|
442
|
-
* Declare an abstract **capability** edge (`requires.capabilities`) the broker
|
|
443
|
-
* resolves to a bound provider at enable time — e.g. `requiresCapability("rag")`.
|
|
444
|
-
* Distinct from a specific-plugin dependency: a capability edge lets the
|
|
445
|
-
* binding registry choose the provider. `minVersion` is a MINIMUM (`"1.2.0"`
|
|
446
|
-
* = `">=1.2.0"`).
|
|
447
|
-
*/
|
|
448
|
-
requiresCapability(capability, minVersion) {
|
|
449
|
-
this._requiredCapabilities.push(
|
|
450
|
-
minVersion ? { capability, min_version: minVersion } : { capability }
|
|
451
|
-
);
|
|
452
|
-
return this;
|
|
453
|
-
}
|
|
454
|
-
/** Restrict this app to a host surface. No target = every surface. */
|
|
455
|
-
target(surface) {
|
|
456
|
-
this._targets.push(surface);
|
|
457
|
-
return this;
|
|
458
|
-
}
|
|
459
|
-
/**
|
|
460
|
-
* Validate and return the assembled `PluginManifest`. Throws an `Error` naming
|
|
461
|
-
* the failing field when validation fails.
|
|
462
|
-
*/
|
|
463
|
-
build() {
|
|
464
|
-
const hasRequires = this._dependencies.length > 0 || this._requiredCapabilities.length > 0 || this._requiredGrants.length > 0;
|
|
465
|
-
const options = {
|
|
466
|
-
id: this._id,
|
|
467
|
-
title: this._title,
|
|
468
|
-
version: this._version,
|
|
469
|
-
slug: this._slug,
|
|
470
|
-
uiEntry: this._uiEntry,
|
|
471
|
-
tools: this._tools,
|
|
472
|
-
grants: this._grants,
|
|
473
|
-
...this._server ? { server: this._server } : {},
|
|
474
|
-
...this._displayMode ? { displayMode: this._displayMode } : {},
|
|
475
|
-
...this._mime ? { mime: this._mime } : {},
|
|
476
|
-
...this._activationEvents.length > 0 ? { activationEvents: this._activationEvents } : {},
|
|
477
|
-
...hasRequires ? {
|
|
478
|
-
requires: {
|
|
479
|
-
apps: this._dependencies,
|
|
480
|
-
capabilities: this._requiredCapabilities,
|
|
481
|
-
grants: this._requiredGrants
|
|
482
|
-
}
|
|
483
|
-
} : {},
|
|
484
|
-
...this._targets.length > 0 ? { targets: this._targets } : {}
|
|
485
|
-
};
|
|
486
|
-
return defineApp(options);
|
|
487
|
-
}
|
|
488
|
-
};
|
|
489
|
-
var app = () => new AppBuilder();
|
|
490
|
-
|
|
491
|
-
// src/runnable/agent.ts
|
|
492
|
-
var CAPABILITY_SLOTS = ["rag", "memory", "tts", "stt"];
|
|
493
|
-
function lowerChatSlot(chat) {
|
|
494
|
-
if (chat === void 0) {
|
|
495
|
-
return {};
|
|
496
|
-
}
|
|
497
|
-
if (typeof chat === "string") {
|
|
498
|
-
return { model: chat };
|
|
499
|
-
}
|
|
500
|
-
return {
|
|
501
|
-
model: chat.model,
|
|
502
|
-
engine: chat.engine,
|
|
503
|
-
persona: chat.persona,
|
|
504
|
-
modelPrefKey: chat.modelPrefKey
|
|
505
|
-
};
|
|
506
|
-
}
|
|
507
|
-
function lowerCapabilitySlot(capability, slot, card) {
|
|
508
|
-
if (slot === void 0 || slot === false) {
|
|
509
|
-
return;
|
|
510
|
-
}
|
|
511
|
-
if (slot === true) {
|
|
512
|
-
card.capabilities.push({ capability });
|
|
513
|
-
return;
|
|
514
|
-
}
|
|
515
|
-
if (typeof slot === "string") {
|
|
516
|
-
card.capabilities.push({ capability });
|
|
517
|
-
card.providers[capability] = slot;
|
|
518
|
-
return;
|
|
519
|
-
}
|
|
520
|
-
card.capabilities.push(
|
|
521
|
-
slot.minVersion ? { capability, min_version: slot.minVersion } : { capability }
|
|
522
|
-
);
|
|
523
|
-
if (slot.provider) {
|
|
524
|
-
card.providers[capability] = slot.provider;
|
|
525
|
-
}
|
|
526
|
-
}
|
|
527
|
-
function lowerSlots(options) {
|
|
528
|
-
const card = {
|
|
529
|
-
...lowerChatSlot(options.chat),
|
|
530
|
-
capabilities: [],
|
|
531
|
-
providers: {},
|
|
532
|
-
tools: []
|
|
533
|
-
};
|
|
534
|
-
for (const capability of CAPABILITY_SLOTS) {
|
|
535
|
-
lowerCapabilitySlot(capability, options[capability], card);
|
|
536
|
-
}
|
|
537
|
-
for (const t of options.tools ?? []) {
|
|
538
|
-
card.tools.push(typeof t === "string" ? t : t.id);
|
|
539
|
-
}
|
|
540
|
-
return card;
|
|
541
|
-
}
|
|
542
|
-
function defaultRun(card) {
|
|
543
|
-
return async (input, ctx) => {
|
|
544
|
-
const content = typeof input === "string" ? input : JSON.stringify(input ?? "");
|
|
545
|
-
const messages = card.persona ? [
|
|
546
|
-
{ role: "system", content: card.persona },
|
|
547
|
-
{ role: "user", content }
|
|
548
|
-
] : [{ role: "user", content }];
|
|
549
|
-
const result = await ctx.gateway.chat(messages);
|
|
550
|
-
return result.content;
|
|
551
|
-
};
|
|
552
|
-
}
|
|
553
|
-
function cardConfig(card) {
|
|
554
|
-
const config = {};
|
|
555
|
-
if (card.model) {
|
|
556
|
-
config.model = card.model;
|
|
557
|
-
}
|
|
558
|
-
if (card.engine) {
|
|
559
|
-
config.engine = card.engine;
|
|
560
|
-
}
|
|
561
|
-
if (card.persona) {
|
|
562
|
-
config.persona = card.persona;
|
|
563
|
-
}
|
|
564
|
-
if (card.modelPrefKey) {
|
|
565
|
-
config.model_pref_key = card.modelPrefKey;
|
|
566
|
-
}
|
|
567
|
-
if (Object.keys(card.providers).length > 0) {
|
|
568
|
-
config.capability_providers = card.providers;
|
|
569
|
-
}
|
|
570
|
-
if (card.tools.length > 0) {
|
|
571
|
-
config.tools = card.tools;
|
|
572
|
-
}
|
|
573
|
-
return config;
|
|
574
|
-
}
|
|
575
|
-
function agentToManifest(agent2, options) {
|
|
576
|
-
const config = cardConfig(agent2.card);
|
|
577
|
-
const meta = {
|
|
578
|
-
id: agent2.id,
|
|
579
|
-
name: agent2.name,
|
|
580
|
-
kind: "agent",
|
|
581
|
-
...Object.keys(config).length > 0 ? { config } : {}
|
|
582
|
-
};
|
|
583
|
-
const hasRequires = agent2.card.capabilities.length > 0 || (options.grants?.length ?? 0) > 0;
|
|
584
|
-
const raw = {
|
|
585
|
-
id: options.id,
|
|
586
|
-
name: options.name ?? agent2.name,
|
|
587
|
-
version: options.version,
|
|
588
|
-
runnables: [meta],
|
|
589
|
-
...hasRequires ? {
|
|
590
|
-
requires: {
|
|
591
|
-
apps: [],
|
|
592
|
-
capabilities: agent2.card.capabilities,
|
|
593
|
-
grants: options.grants ?? []
|
|
594
|
-
}
|
|
595
|
-
} : {}
|
|
596
|
-
};
|
|
597
|
-
const result = PluginManifestSchema.safeParse(raw);
|
|
598
|
-
if (!result.success) {
|
|
599
|
-
const first = result.error.issues[0];
|
|
600
|
-
const field = first?.path.join(".") ?? "unknown";
|
|
601
|
-
const message = first?.message ?? "validation failed";
|
|
602
|
-
throw new Error(
|
|
603
|
-
`agent manifest validation failed at '${field}': ${message}`
|
|
604
|
-
);
|
|
605
|
-
}
|
|
606
|
-
return result.data;
|
|
607
|
-
}
|
|
608
|
-
function defineAgent(options) {
|
|
609
|
-
const { id, name } = options;
|
|
610
|
-
const card = lowerSlots(options);
|
|
611
|
-
const run = options.run ?? defaultRun(card);
|
|
612
|
-
return {
|
|
613
|
-
id,
|
|
614
|
-
name,
|
|
615
|
-
kind: "agent",
|
|
616
|
-
run,
|
|
617
|
-
card,
|
|
618
|
-
toManifest(manifestOptions) {
|
|
619
|
-
return agentToManifest(this, manifestOptions);
|
|
620
|
-
}
|
|
621
|
-
};
|
|
622
|
-
}
|
|
623
|
-
|
|
624
|
-
// src/runnable/skill.ts
|
|
625
|
-
function defineSkill(options) {
|
|
626
|
-
const { id, name, run } = options;
|
|
627
|
-
return {
|
|
628
|
-
id,
|
|
629
|
-
name,
|
|
630
|
-
kind: "skill",
|
|
631
|
-
run
|
|
632
|
-
};
|
|
633
|
-
}
|
|
634
|
-
|
|
635
|
-
// src/runnable/tool.ts
|
|
636
|
-
function validateInput(input, schema, toolId) {
|
|
637
|
-
if (typeof input !== "object" || input === null || Array.isArray(input)) {
|
|
638
|
-
throw new Error(
|
|
639
|
-
`[ryu-sdk] Tool "${toolId}" input must be an object, got ${JSON.stringify(input)}`
|
|
640
|
-
);
|
|
641
|
-
}
|
|
642
|
-
const record = input;
|
|
643
|
-
for (const requiredKey of schema.required ?? []) {
|
|
644
|
-
if (!(requiredKey in record)) {
|
|
645
|
-
throw new Error(
|
|
646
|
-
`[ryu-sdk] Tool "${toolId}" input missing required field "${requiredKey}"`
|
|
647
|
-
);
|
|
648
|
-
}
|
|
649
|
-
}
|
|
650
|
-
for (const [key, prop] of Object.entries(schema.properties)) {
|
|
651
|
-
if (!(key in record)) {
|
|
652
|
-
continue;
|
|
653
|
-
}
|
|
654
|
-
const value = record[key];
|
|
655
|
-
if (!checkType(value, prop.type)) {
|
|
656
|
-
throw new Error(
|
|
657
|
-
`[ryu-sdk] Tool "${toolId}" input field "${key}" expected type "${prop.type}", got ${JSON.stringify(value)}`
|
|
658
|
-
);
|
|
659
|
-
}
|
|
660
|
-
}
|
|
661
|
-
}
|
|
662
|
-
function checkType(value, type) {
|
|
663
|
-
switch (type) {
|
|
664
|
-
case "string":
|
|
665
|
-
return typeof value === "string";
|
|
666
|
-
case "number":
|
|
667
|
-
case "integer":
|
|
668
|
-
return typeof value === "number";
|
|
669
|
-
case "boolean":
|
|
670
|
-
return typeof value === "boolean";
|
|
671
|
-
case "array":
|
|
672
|
-
return Array.isArray(value);
|
|
673
|
-
case "object":
|
|
674
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
675
|
-
default:
|
|
676
|
-
return false;
|
|
677
|
-
}
|
|
678
|
-
}
|
|
679
|
-
function defineTool(options) {
|
|
680
|
-
const { id, name, schema, run } = options;
|
|
681
|
-
const code = `return await (${run.toString()})(input, host);`;
|
|
682
|
-
return {
|
|
683
|
-
id,
|
|
684
|
-
name,
|
|
685
|
-
kind: "tool",
|
|
686
|
-
schema,
|
|
687
|
-
code,
|
|
688
|
-
run(input, ctx) {
|
|
689
|
-
validateInput(input, schema, id);
|
|
690
|
-
return run(input, ctx);
|
|
691
|
-
}
|
|
692
|
-
};
|
|
693
|
-
}
|
|
694
|
-
function inlineToolRunnable(tool2, options) {
|
|
695
|
-
return {
|
|
696
|
-
id: tool2.id,
|
|
697
|
-
name: tool2.name,
|
|
698
|
-
kind: "tool",
|
|
699
|
-
config: {
|
|
700
|
-
slug: tool2.id,
|
|
701
|
-
backend: "inline_deno",
|
|
702
|
-
code: tool2.code,
|
|
703
|
-
input_schema: tool2.schema,
|
|
704
|
-
...options?.description ? { description: options.description } : {}
|
|
705
|
-
}
|
|
706
|
-
};
|
|
707
|
-
}
|
|
65
|
+
} from "./chunk-IKEDLLFY.js";
|
|
66
|
+
import "./chunk-TXSHHZF2.js";
|
|
67
|
+
import {
|
|
68
|
+
McpServer,
|
|
69
|
+
unwrapContent
|
|
70
|
+
} from "./chunk-FZSFZOIN.js";
|
|
71
|
+
import {
|
|
72
|
+
MCP_PROTOCOL_VERSION,
|
|
73
|
+
callTool,
|
|
74
|
+
listTools
|
|
75
|
+
} from "./chunk-VLIRNNAE.js";
|
|
708
76
|
|
|
709
77
|
// src/runnable/turn-hook.ts
|
|
710
78
|
function defineTurnHook(options) {
|
|
@@ -721,6 +89,7 @@ function definePlugin(options) {
|
|
|
721
89
|
turn_hooks: options.turnHooks ?? [],
|
|
722
90
|
hook_events: options.hookEvents ?? [],
|
|
723
91
|
composer_controls: options.composerControls ?? [],
|
|
92
|
+
chat_features: [],
|
|
724
93
|
settings_tabs: options.settingsTabs ?? [],
|
|
725
94
|
slash_commands: options.slashCommands ?? [],
|
|
726
95
|
lsp_servers: options.lspServers ?? {},
|
|
@@ -732,9 +101,11 @@ function definePlugin(options) {
|
|
|
732
101
|
sidebar_sections: [],
|
|
733
102
|
sidebar_buttons: [],
|
|
734
103
|
dock_panels: [],
|
|
104
|
+
live_activities: [],
|
|
735
105
|
data_categories: [],
|
|
736
106
|
pi_extensions: [],
|
|
737
|
-
output_styles: []
|
|
107
|
+
output_styles: [],
|
|
108
|
+
message_actions: []
|
|
738
109
|
};
|
|
739
110
|
const tools = options.tools ?? [];
|
|
740
111
|
const runnables = tools.map((t) => inlineToolRunnable(t));
|
|
@@ -763,17 +134,6 @@ function definePlugin(options) {
|
|
|
763
134
|
} : {}
|
|
764
135
|
};
|
|
765
136
|
}
|
|
766
|
-
|
|
767
|
-
// src/runnable/workflow.ts
|
|
768
|
-
function defineWorkflow(options) {
|
|
769
|
-
const { id, name, run } = options;
|
|
770
|
-
return {
|
|
771
|
-
id,
|
|
772
|
-
name,
|
|
773
|
-
kind: "workflow",
|
|
774
|
-
run
|
|
775
|
-
};
|
|
776
|
-
}
|
|
777
137
|
export {
|
|
778
138
|
Agent,
|
|
779
139
|
AgentBuilder,
|
|
@@ -782,6 +142,10 @@ export {
|
|
|
782
142
|
CapabilityReqSchema,
|
|
783
143
|
CompanionSurfaceSchema,
|
|
784
144
|
DEFAULT_GATEWAY_URL,
|
|
145
|
+
MCP_PROTOCOL_VERSION,
|
|
146
|
+
McpServer,
|
|
147
|
+
McpServerAuthSchema,
|
|
148
|
+
McpServerDeclSchema,
|
|
785
149
|
ModelClient,
|
|
786
150
|
PRIMITIVE_BINDINGS,
|
|
787
151
|
PluginBuilder,
|
|
@@ -799,6 +163,7 @@ export {
|
|
|
799
163
|
app,
|
|
800
164
|
appToolId,
|
|
801
165
|
assertAllowedEgressUrl,
|
|
166
|
+
callTool,
|
|
802
167
|
coreManifestJsonSchema,
|
|
803
168
|
createAgent,
|
|
804
169
|
createPrimitives,
|
|
@@ -812,12 +177,15 @@ export {
|
|
|
812
177
|
defineWorkflow,
|
|
813
178
|
httpPrimitiveTransport,
|
|
814
179
|
inlineToolRunnable,
|
|
180
|
+
listTools,
|
|
815
181
|
query,
|
|
816
182
|
resolveGatewayToken,
|
|
817
183
|
resolveGatewayUrl,
|
|
818
184
|
ryuTool,
|
|
819
185
|
skill,
|
|
186
|
+
toDisposable,
|
|
820
187
|
tool,
|
|
188
|
+
unwrapContent,
|
|
821
189
|
validateManifestStrict,
|
|
822
190
|
validatePluginId,
|
|
823
191
|
workflow
|