@runtypelabs/cli 2.59.1 → 2.59.2

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.
Files changed (84) hide show
  1. package/dist/chunk-0-T9NWjH.js +3899 -0
  2. package/dist/chunk-0x7UKC1U.js +17 -0
  3. package/dist/chunk-2ySxXtcg.js +418 -0
  4. package/dist/chunk-3An_BRHv.js +501 -0
  5. package/dist/chunk-6uTxgdiY.js +16218 -0
  6. package/dist/chunk-87nRnNRG.js +1363 -0
  7. package/dist/chunk-B3wo8uRx.js +322 -0
  8. package/dist/chunk-BGp3ZdBy.js +560 -0
  9. package/dist/chunk-BJQv9Elp.js +107 -0
  10. package/dist/chunk-BOpO6xE-.js +6053 -0
  11. package/dist/chunk-BQXXCL8B.js +102 -0
  12. package/dist/chunk-BV-8isOd.js +34 -0
  13. package/dist/chunk-BVMhjGVe.js +826 -0
  14. package/dist/chunk-BW2fg46T.js +141 -0
  15. package/dist/chunk-BWJdY5Ag.js +36 -0
  16. package/dist/chunk-BYJOrLhh.js +302 -0
  17. package/dist/chunk-BYab8EVL.js +127 -0
  18. package/dist/chunk-BfEKvp7h.js +82 -0
  19. package/dist/chunk-BhgLSfH6.js +1123 -0
  20. package/dist/chunk-BirUxTtH.js +296 -0
  21. package/dist/chunk-BmB6UVZ9.js +1559 -0
  22. package/dist/chunk-BnWhIqW1.js +109 -0
  23. package/dist/chunk-Bpfnfk0t.js +123 -0
  24. package/dist/chunk-BrhgdnM3.js +108 -0
  25. package/dist/chunk-Bt0XAgX5.js +327 -0
  26. package/dist/chunk-Bu0FJr6S.js +84 -0
  27. package/dist/chunk-BvEoKpN3.js +255 -0
  28. package/dist/chunk-BxNJgYbE.js +28 -0
  29. package/dist/chunk-C1OFhd7F.js +6131 -0
  30. package/dist/chunk-C7e7WwbU.js +331 -0
  31. package/dist/chunk-CDTYP6bN.js +558 -0
  32. package/dist/chunk-CGDQoqDC.js +24 -0
  33. package/dist/chunk-CJraEBVd.js +127 -0
  34. package/dist/chunk-CQrNhOtv.js +40 -0
  35. package/dist/chunk-CW6AzBH6.js +128 -0
  36. package/dist/chunk-CXgL4w-9.js +317 -0
  37. package/dist/chunk-CZrqoPyf.js +233 -0
  38. package/dist/chunk-CcFCyqbB.js +83 -0
  39. package/dist/chunk-CdaIvO-y.js +485 -0
  40. package/dist/chunk-CehSXtgK.js +624 -0
  41. package/dist/chunk-Ciqkop65.js +218 -0
  42. package/dist/chunk-CoAWdSiE.js +43 -0
  43. package/dist/chunk-Crb4y7t4.js +830 -0
  44. package/dist/chunk-CrlqIfmb.js +337 -0
  45. package/dist/chunk-Cs4pwCQ-.js +324 -0
  46. package/dist/chunk-CwM_9y01.js +519 -0
  47. package/dist/chunk-CyRbIJg8.js +440 -0
  48. package/dist/chunk-D0OHsyMy.js +212 -0
  49. package/dist/chunk-D3y2bURs.js +1347 -0
  50. package/dist/chunk-D4_mJk03.js +2338 -0
  51. package/dist/chunk-D6C8rned.js +578 -0
  52. package/dist/chunk-D9ZbUnks.js +11 -0
  53. package/dist/chunk-DEPmLshX.js +834 -0
  54. package/dist/chunk-DFj1UPB2.js +330 -0
  55. package/dist/chunk-DGdFdZVf.js +197 -0
  56. package/dist/chunk-DGv7X9S_.js +63 -0
  57. package/dist/chunk-DJQ47WYZ.js +664 -0
  58. package/dist/chunk-DJw3O61j.js +1974 -0
  59. package/dist/chunk-DK4FbWVK.js +100 -0
  60. package/dist/chunk-DSRYhUus.js +993 -0
  61. package/dist/chunk-DajZ9Eg4.js +299 -0
  62. package/dist/chunk-Df4dunvU.js +195 -0
  63. package/dist/chunk-DjNTPhfO.js +481 -0
  64. package/dist/chunk-Dn8eaJuu.js +1042 -0
  65. package/dist/chunk-DwDWqSxM.js +637 -0
  66. package/dist/chunk-Dz7cEtxl.js +84 -0
  67. package/dist/chunk-E_0bgjrS.js +359 -0
  68. package/dist/chunk-KPYN2vUp.js +776 -0
  69. package/dist/chunk-KcqPQJBi.js +86 -0
  70. package/dist/chunk-N9H0JnoG.js +349 -0
  71. package/dist/chunk-NONFcXkn.js +728 -0
  72. package/dist/chunk-PrFjcpmH.js +256 -0
  73. package/dist/chunk-QSfNYiw9.js +11 -0
  74. package/dist/chunk-R265bzj9.js +226 -0
  75. package/dist/chunk-X9V_r6jM.js +166 -0
  76. package/dist/chunk-ZBtPUtyA.js +55 -0
  77. package/dist/chunk-ZCTfmOs7.js +4939 -0
  78. package/dist/chunk-h6oavj0t.js +97 -0
  79. package/dist/chunk-i7DwkvvD.js +42 -0
  80. package/dist/chunk-mG-4eZ6S.js +203 -0
  81. package/dist/chunk-o0ygUbCf.js +313 -0
  82. package/dist/chunk-ucu5lrDZ.js +5715 -0
  83. package/dist/index.js +11367 -73789
  84. package/package.json +4 -4
@@ -0,0 +1,86 @@
1
+ #!/usr/bin/env node
2
+ import { t as redactPiiText } from "./chunk-mG-4eZ6S.js";
3
+ // src/lib/local-harness/delivery/redaction.ts
4
+ const SENSITIVE_KEY = /^(?:authorization|password|secret|token|access[_-]?token|refresh[_-]?token|client[_-]?secret|credentials?|api[_-]?key|cookie|private[_-]?key|environment|env)$/i;
5
+ const MARKER = "[redacted]";
6
+ function redactHarnessValue(value, policy, secrets = []) {
7
+ let changed = false;
8
+ const text = (input) => {
9
+ let output = input;
10
+ for (const secret of secrets) if (secret.length >= 4) output = output.split(secret).join(MARKER);
11
+ output = output.replace(/\b(?:Bearer\s+\S+|(?:sk-|rt_|sst_)[A-Za-z0-9_-]{8,})/gi, MARKER);
12
+ output = output.replace(/(https?:\/\/)[^\s/@]+:[^\s/@]+@/gi, "$1[redacted]@");
13
+ output = output.replace(/([?&](?:key|token|secret|password|api_key|client[_-]?secret)=)[^&#\s]+/gi, "$1[redacted]");
14
+ if (policy === "redacted") output = redactPiiText(output, { mode: "redact" }).text;
15
+ if (output !== input) changed = true;
16
+ return output;
17
+ };
18
+ const walk = (input, depth) => {
19
+ if (depth > 24) {
20
+ changed = true;
21
+ return "[depth limit]";
22
+ }
23
+ if (typeof input === "string") {
24
+ if (/^\s*[[{]/.test(input)) try {
25
+ const parsed = JSON.parse(input);
26
+ return JSON.stringify(walk(parsed, depth + 1));
27
+ } catch {
28
+ return text(input);
29
+ }
30
+ return text(input);
31
+ }
32
+ if (input === null || typeof input === "boolean" || typeof input === "number") return input;
33
+ if (Array.isArray(input)) return input.map((entry) => walk(entry, depth + 1));
34
+ if (typeof input !== "object") return void 0;
35
+ return Object.fromEntries(Object.entries(input).map(([key, entry]) => {
36
+ if (SENSITIVE_KEY.test(key)) {
37
+ changed = true;
38
+ return [key, MARKER];
39
+ }
40
+ return [text(key), walk(entry, depth + 1)];
41
+ }));
42
+ };
43
+ return {
44
+ value: walk(value, 0),
45
+ changed
46
+ };
47
+ }
48
+ function redactObservation(observation, policy, secrets) {
49
+ if (policy === "metrics") {
50
+ const tool = observation.tool;
51
+ const removedContent = observation.native !== void 0 || observation.message !== void 0 || tool?.input !== void 0 || tool?.output !== void 0;
52
+ const result = redactHarnessValue({
53
+ kind: observation.kind,
54
+ nativeId: observation.nativeId,
55
+ nativeSessionId: observation.nativeSessionId,
56
+ nativeTurnId: observation.nativeTurnId,
57
+ parentId: observation.parentId,
58
+ nativeTime: observation.nativeTime,
59
+ ...tool ? { tool: {
60
+ id: tool.id,
61
+ name: tool.name,
62
+ nativeName: tool.nativeName,
63
+ mcpServer: tool.mcpServer,
64
+ mcpTool: tool.mcpTool,
65
+ status: tool.status,
66
+ startedAt: tool.startedAt,
67
+ endedAt: tool.endedAt,
68
+ durationMs: tool.durationMs
69
+ } } : {},
70
+ ...observation.usage ? { usage: observation.usage } : {},
71
+ ...observation.permission ? { permission: observation.permission } : {},
72
+ ...observation.lifecycle ? { lifecycle: { state: observation.lifecycle.state } } : {}
73
+ }, policy, secrets);
74
+ return {
75
+ observation: result.value,
76
+ changed: removedContent || result.changed
77
+ };
78
+ }
79
+ const result = redactHarnessValue(observation, policy, secrets);
80
+ return {
81
+ observation: result.value,
82
+ changed: result.changed
83
+ };
84
+ }
85
+ export { redactObservation as n, redactHarnessValue as t };
86
+
@@ -0,0 +1,349 @@
1
+ #!/usr/bin/env node
2
+ import { t as isTTY } from "./index.js";
3
+ import { ConfirmPrompt, DataList, EntityCard, MutationResult, React, render, useEffect, useState } from "./chunk-CoAWdSiE.js";
4
+ import { r as createCliClient } from "./chunk-BW2fg46T.js";
5
+ import { n as ensureAuth } from "./chunk-CJraEBVd.js";
6
+ import { a as printJson, i as printDetail, o as printList, r as getTotalCount, s as printNextCursorHint } from "./chunk-CcFCyqbB.js";
7
+ import { t as readJsonFile } from "./chunk-DGv7X9S_.js";
8
+ import { n as addExecutionInputOptions, r as resolveExecutionInput, t as runExecution } from "./chunk-Cs4pwCQ-.js";
9
+ import { c as buildEntityPullCommand, n as FLOW_ENSURE_SPEC, s as buildEntityEnsureCommand } from "./chunk-BirUxTtH.js";
10
+ import { Command } from "commander";
11
+ import chalk from "chalk";
12
+ // src/commands/flows.ts
13
+ /** Build the typed list params the SDK endpoint expects from the CLI's string flags. */
14
+ function flowsListParams(options) {
15
+ return {
16
+ limit: options.limit ? Number(options.limit) : void 0,
17
+ cursor: options.cursor
18
+ };
19
+ }
20
+ const flowsCommand = new Command("flows").description("Manage flows");
21
+ flowsCommand.addCommand(buildEntityEnsureCommand(FLOW_ENSURE_SPEC));
22
+ flowsCommand.addCommand(buildEntityPullCommand(FLOW_ENSURE_SPEC));
23
+ flowsCommand.command("list").description("List all flows").option("--limit <n>", "Limit results (defaults to the API page size)").option("--cursor <cursor>", "Pagination cursor for the next page").option("--json", "Output as JSON").option("--tty", "Force TTY mode").option("--no-tty", "Force non-TTY mode").action(async (options) => {
24
+ const apiKey = await ensureAuth();
25
+ if (!apiKey) return;
26
+ const client = createCliClient(apiKey);
27
+ const listParams = flowsListParams(options);
28
+ if (!isTTY(options) || options.json) {
29
+ try {
30
+ const data = await client.flows.list(listParams);
31
+ if (options.json) {
32
+ printJson(data);
33
+ return;
34
+ }
35
+ printList(data.data, {
36
+ title: "Your Flows",
37
+ columns: [{
38
+ key: "id",
39
+ color: "green"
40
+ }, { key: "name" }],
41
+ emptyMessage: "No flows found",
42
+ total: getTotalCount(data.pagination)
43
+ });
44
+ printNextCursorHint("runtype flows list", data.pagination);
45
+ } catch (error) {
46
+ const message = error instanceof Error ? error.message : "Unknown error";
47
+ console.error(chalk.red(`Failed to fetch flows: ${message}`));
48
+ process.exit(1);
49
+ }
50
+ return;
51
+ }
52
+ const App = () => {
53
+ const [items, setItems] = useState(null);
54
+ const [error, setError] = useState(null);
55
+ const [total, setTotal] = useState();
56
+ useEffect(() => {
57
+ client.flows.list(listParams).then((res) => {
58
+ setItems(res.data);
59
+ setTotal(getTotalCount(res.pagination));
60
+ }).catch((err) => setError(err instanceof Error ? err : new Error(String(err))));
61
+ }, []);
62
+ return React.createElement(DataList, {
63
+ title: "Your Flows",
64
+ items,
65
+ error,
66
+ loading: items === null && error === null,
67
+ total,
68
+ renderCard: (item) => {
69
+ const flow = item;
70
+ return React.createElement(EntityCard, { fields: [{
71
+ label: "ID",
72
+ value: flow.id,
73
+ color: "green"
74
+ }, {
75
+ label: "Name",
76
+ value: flow.name
77
+ }] });
78
+ },
79
+ emptyMessage: "No flows found"
80
+ });
81
+ };
82
+ const { waitUntilExit } = render(React.createElement(App));
83
+ await waitUntilExit();
84
+ });
85
+ flowsCommand.command("get <id>").description("Get flow details").option("--json", "Output as JSON").option("--tty", "Force TTY mode").option("--no-tty", "Force non-TTY mode").action(async (id, options) => {
86
+ const apiKey = await ensureAuth();
87
+ if (!apiKey) return;
88
+ const client = createCliClient(apiKey);
89
+ if (!isTTY(options) || options.json) {
90
+ try {
91
+ const data = await client.flows.get(id);
92
+ if (options.json) {
93
+ printJson(data);
94
+ return;
95
+ }
96
+ printDetail("Flow", [
97
+ {
98
+ label: "ID",
99
+ value: data.id
100
+ },
101
+ {
102
+ label: "Name",
103
+ value: data.name
104
+ },
105
+ {
106
+ label: "Steps",
107
+ value: data.stepCount ?? data.flowSteps?.length
108
+ }
109
+ ]);
110
+ } catch (error) {
111
+ const message = error instanceof Error ? error.message : "Unknown error";
112
+ console.error(chalk.red(`Failed to fetch flow: ${message}`));
113
+ process.exit(1);
114
+ }
115
+ return;
116
+ }
117
+ const App = () => {
118
+ const [items, setItems] = useState(null);
119
+ const [error, setError] = useState(null);
120
+ useEffect(() => {
121
+ client.flows.get(id).then((res) => setItems([res])).catch((err) => setError(err instanceof Error ? err : new Error(String(err))));
122
+ }, []);
123
+ return React.createElement(DataList, {
124
+ title: "Flow",
125
+ items,
126
+ error,
127
+ loading: items === null && error === null,
128
+ renderCard: (item) => {
129
+ const flow = item;
130
+ return React.createElement(EntityCard, { fields: [
131
+ {
132
+ label: "ID",
133
+ value: flow.id,
134
+ color: "green"
135
+ },
136
+ {
137
+ label: "Name",
138
+ value: flow.name
139
+ },
140
+ {
141
+ label: "Steps",
142
+ value: flow.stepCount ?? flow.flowSteps?.length
143
+ }
144
+ ] });
145
+ }
146
+ });
147
+ };
148
+ const { waitUntilExit } = render(React.createElement(App));
149
+ await waitUntilExit();
150
+ });
151
+ addExecutionInputOptions(flowsCommand.command("run <id>").description("Execute a flow via dispatch").option("-r, --record <id>", "Record ID to run with").option("-m, --message <text>", "Message to send").option("--stream", "Stream the response (default)", true).option("--no-stream", "Wait for complete response").option("--json", "Output one final JSON result").option("--jsonl", "Output stream events and a terminal execution_summary as JSON lines")).action(async (flowId, options) => {
152
+ await runExecution(options, () => ({
153
+ ...resolveExecutionInput(options),
154
+ flow: { id: flowId },
155
+ options: { streamResponse: options.stream }
156
+ }), (client, payload) => options.stream ? client.dispatch.executeStream(payload) : client.dispatch.execute(payload), "flow");
157
+ });
158
+ flowsCommand.command("create").description("Create a new flow").requiredOption("-n, --name <name>", "Flow name").option("-d, --description <desc>", "Flow description").option("--from-file <file>", "Import flow from JSON file").option("--json", "Output as JSON").option("--tty", "Force TTY mode").option("--no-tty", "Force non-TTY mode").action(async (options) => {
159
+ const apiKey = await ensureAuth();
160
+ if (!apiKey) return;
161
+ const client = createCliClient(apiKey);
162
+ let body = {
163
+ name: options.name,
164
+ description: options.description
165
+ };
166
+ if (options.fromFile) {
167
+ body = { ...readJsonFile(options.fromFile, {
168
+ label: "flow file",
169
+ unwrapKey: "flow"
170
+ }) };
171
+ if (options.name !== void 0) body.name = options.name;
172
+ if (options.description !== void 0) body.description = options.description;
173
+ }
174
+ if (!isTTY(options) || options.json) {
175
+ try {
176
+ const data = await client.post("/flows", body);
177
+ if (options.json) {
178
+ printJson(data);
179
+ return;
180
+ }
181
+ console.log(` ID: ${chalk.green(data.id)}`);
182
+ console.log(` Name: ${data.name}`);
183
+ } catch (error) {
184
+ const message = error instanceof Error ? error.message : "Unknown error";
185
+ console.error(chalk.red(`Failed to create flow: ${message}`));
186
+ process.exit(1);
187
+ }
188
+ return;
189
+ }
190
+ const App = () => {
191
+ const [loading, setLoading] = useState(true);
192
+ const [success, setSuccess] = useState(null);
193
+ const [error, setError] = useState(null);
194
+ const [result, setResult] = useState(null);
195
+ useEffect(() => {
196
+ client.post("/flows", body).then((data) => {
197
+ setResult(data);
198
+ setSuccess(true);
199
+ setLoading(false);
200
+ }).catch((err) => {
201
+ setError(err instanceof Error ? err : new Error(String(err)));
202
+ setSuccess(false);
203
+ setLoading(false);
204
+ });
205
+ }, []);
206
+ return React.createElement(MutationResult, {
207
+ loading,
208
+ loadingLabel: "Creating flow...",
209
+ success,
210
+ successMessage: "Flow created",
211
+ error,
212
+ result: result ? React.createElement(EntityCard, { fields: [{
213
+ label: "ID",
214
+ value: result.id,
215
+ color: "green"
216
+ }, {
217
+ label: "Name",
218
+ value: result.name
219
+ }] }) : void 0
220
+ });
221
+ };
222
+ const { waitUntilExit } = render(React.createElement(App));
223
+ await waitUntilExit();
224
+ });
225
+ flowsCommand.command("update <id>").description("Update a flow").option("-n, --name <name>", "New flow name").option("-d, --description <desc>", "New flow description").option("--from-file <file>", "Update flow from JSON file (full body)").option("--json", "Output as JSON").option("--tty", "Force TTY mode").option("--no-tty", "Force non-TTY mode").action(async (id, options) => {
226
+ const apiKey = await ensureAuth();
227
+ if (!apiKey) return;
228
+ const client = createCliClient(apiKey);
229
+ let body = {};
230
+ if (options.fromFile) body = readJsonFile(options.fromFile, {
231
+ label: "flow file",
232
+ unwrapKey: "flow"
233
+ });
234
+ if (options.name !== void 0) body.name = options.name;
235
+ if (options.description !== void 0) body.description = options.description;
236
+ if (Object.keys(body).length === 0) {
237
+ console.error(chalk.red("Error: provide at least one of --name, --description, or --from-file"));
238
+ process.exit(1);
239
+ }
240
+ if (!isTTY(options) || options.json) {
241
+ try {
242
+ const data = await client.put(`/flows/${id}`, body);
243
+ if (options.json) {
244
+ printJson(data);
245
+ return;
246
+ }
247
+ console.log(chalk.green("Flow updated"));
248
+ console.log(` ID: ${chalk.green(data.id)}`);
249
+ console.log(` Name: ${data.name}`);
250
+ } catch (error) {
251
+ const message = error instanceof Error ? error.message : "Unknown error";
252
+ console.error(chalk.red(`Failed to update flow: ${message}`));
253
+ process.exit(1);
254
+ }
255
+ return;
256
+ }
257
+ const App = () => {
258
+ const [loading, setLoading] = useState(true);
259
+ const [success, setSuccess] = useState(null);
260
+ const [error, setError] = useState(null);
261
+ const [result, setResult] = useState(null);
262
+ useEffect(() => {
263
+ client.put(`/flows/${id}`, body).then((data) => {
264
+ setResult(data);
265
+ setSuccess(true);
266
+ setLoading(false);
267
+ }).catch((err) => {
268
+ setError(err instanceof Error ? err : new Error(String(err)));
269
+ setSuccess(false);
270
+ setLoading(false);
271
+ });
272
+ }, []);
273
+ return React.createElement(MutationResult, {
274
+ loading,
275
+ loadingLabel: "Updating flow...",
276
+ success,
277
+ successMessage: "Flow updated",
278
+ error,
279
+ result: result ? React.createElement(EntityCard, { fields: [{
280
+ label: "ID",
281
+ value: result.id,
282
+ color: "green"
283
+ }, {
284
+ label: "Name",
285
+ value: result.name
286
+ }] }) : void 0
287
+ });
288
+ };
289
+ const { waitUntilExit } = render(React.createElement(App));
290
+ await waitUntilExit();
291
+ });
292
+ flowsCommand.command("delete <id>").description("Delete a flow").option("--tty", "Force TTY mode").option("--no-tty", "Force non-TTY mode").action(async (id, options) => {
293
+ const apiKey = await ensureAuth();
294
+ if (!apiKey) return;
295
+ const client = createCliClient(apiKey);
296
+ if (!isTTY(options)) {
297
+ try {
298
+ await client.flows.delete(id);
299
+ console.log(JSON.stringify({
300
+ status: "deleted",
301
+ id
302
+ }, null, 2));
303
+ } catch (error) {
304
+ const message = error instanceof Error ? error.message : "Unknown error";
305
+ console.error(chalk.red(`Failed to delete flow: ${message}`));
306
+ process.exit(1);
307
+ }
308
+ return;
309
+ }
310
+ const App = () => {
311
+ const [confirmed, setConfirmed] = useState(null);
312
+ const [loading, setLoading] = useState(false);
313
+ const [success, setSuccess] = useState(null);
314
+ const [error, setError] = useState(null);
315
+ useEffect(() => {
316
+ if (confirmed !== true) return void 0;
317
+ setLoading(true);
318
+ client.flows.delete(id).then(() => {
319
+ setSuccess(true);
320
+ setLoading(false);
321
+ }).catch((err) => {
322
+ setError(err instanceof Error ? err : new Error(String(err)));
323
+ setSuccess(false);
324
+ setLoading(false);
325
+ });
326
+ }, [confirmed]);
327
+ if (confirmed === null) return React.createElement(ConfirmPrompt, {
328
+ message: `Delete flow ${id}?`,
329
+ onConfirm: (val) => setConfirmed(val)
330
+ });
331
+ if (confirmed === false) return React.createElement(MutationResult, {
332
+ loading: false,
333
+ success: true,
334
+ successMessage: "Cancelled",
335
+ error: null
336
+ });
337
+ return React.createElement(MutationResult, {
338
+ loading,
339
+ loadingLabel: "Deleting flow...",
340
+ success,
341
+ successMessage: "Flow deleted",
342
+ error
343
+ });
344
+ };
345
+ const { waitUntilExit } = render(React.createElement(App));
346
+ await waitUntilExit();
347
+ });
348
+ export { flowsCommand };
349
+