@aibyzero/byz 0.1.3 → 0.1.5

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 (33) hide show
  1. package/CHANGELOG.md +12 -0
  2. package/README.md +9 -3
  3. package/dist/cli.js +31 -22
  4. package/dist/fast.js +5 -2
  5. package/dist/runtime/bundle/chunks/{chunk-QY7DJQRI.js → chunk-WMLOZBQV.js} +7 -7
  6. package/dist/runtime/bundle/cli.js +1 -1
  7. package/dist/runtime/bundle/index.js +1 -1
  8. package/dist/runtime/bundle/rpc-entry.js +1 -1
  9. package/dist/runtime/core/agent-session.d.ts +4 -1
  10. package/dist/runtime/core/agent-session.d.ts.map +1 -1
  11. package/dist/runtime/core/agent-session.js +38 -11
  12. package/dist/runtime/core/agent-session.js.map +1 -1
  13. package/dist/runtime/core/extensions/runner.d.ts +11 -1
  14. package/dist/runtime/core/extensions/runner.d.ts.map +1 -1
  15. package/dist/runtime/core/extensions/runner.js +40 -9
  16. package/dist/runtime/core/extensions/runner.js.map +1 -1
  17. package/dist/runtime/core/extensions/types.d.ts +7 -0
  18. package/dist/runtime/core/extensions/types.d.ts.map +1 -1
  19. package/dist/runtime/core/extensions/types.js.map +1 -1
  20. package/dist/runtime/core/resource-loader.d.ts +16 -1
  21. package/dist/runtime/core/resource-loader.d.ts.map +1 -1
  22. package/dist/runtime/core/resource-loader.js +216 -2
  23. package/dist/runtime/core/resource-loader.js.map +1 -1
  24. package/dist/runtime/main.d.ts +2 -1
  25. package/dist/runtime/main.d.ts.map +1 -1
  26. package/dist/runtime/main.js +1 -0
  27. package/dist/runtime/main.js.map +1 -1
  28. package/dist/runtime/modes/interactive/interactive-mode.d.ts.map +1 -1
  29. package/dist/runtime/modes/interactive/interactive-mode.js +5 -0
  30. package/dist/runtime/modes/interactive/interactive-mode.js.map +1 -1
  31. package/dist/workflow-switch.js +95 -0
  32. package/dist/workflows.js +31 -16
  33. package/package.json +1 -1
@@ -0,0 +1,95 @@
1
+ import { parseArgs } from "./runtime/bundle/index.js";
2
+
3
+ const WORKFLOW_IDS = new Set(["cm", "cm-plugin", "none"]);
4
+ const NON_RUNTIME_COMMANDS = new Set(["auth", "config", "install", "list", "remove", "uninstall", "update"]);
5
+
6
+ export function getActiveByzOptionIndexes(args, optionName) {
7
+ const indexes = new Set();
8
+ const option = `--${optionName}`;
9
+ for (let index = 0; index < args.length; index++) {
10
+ const arg = args[index];
11
+ if (arg !== option && !arg.startsWith(`${option}=`)) continue;
12
+
13
+ let probeName = `__byz_${optionName}_probe_${index}`;
14
+ while (args.some((candidate) => candidate === `--${probeName}` || candidate.startsWith(`--${probeName}=`))) {
15
+ probeName += "_";
16
+ }
17
+ const equalsIndex = arg.indexOf("=");
18
+ const probeArgs = [...args];
19
+ probeArgs[index] = equalsIndex === -1 ? `--${probeName}` : `--${probeName}${arg.slice(equalsIndex)}`;
20
+ if (parseArgs(probeArgs).unknownFlags.has(probeName)) indexes.add(index);
21
+ }
22
+ return indexes;
23
+ }
24
+
25
+ export function shouldLoadWorkflow(args) {
26
+ const parsed = parseArgs(args);
27
+ if (parsed.help || parsed.version || parsed.export || parsed.listModels !== undefined) return false;
28
+ return !NON_RUNTIME_COMMANDS.has(args[0]);
29
+ }
30
+
31
+ export function shouldEnableWorkflowSwitch(args, { stdinIsTTY, stdoutIsTTY }) {
32
+ if (!stdinIsTTY || !stdoutIsTTY) return false;
33
+ const parsed = parseArgs(args);
34
+ return !parsed.print && parsed.mode !== "json" && parsed.mode !== "rpc";
35
+ }
36
+
37
+ export function createWorkflowSwitchExtension({ initialResources, initialWorkflowId, resolveResources }) {
38
+ let activeResources = initialResources;
39
+ let activeWorkflowId = initialWorkflowId;
40
+
41
+ return function workflowSwitchExtension(pi) {
42
+ pi.on("resources_discover", () => ({
43
+ promptPaths: activeResources.promptPaths,
44
+ skillPaths: activeResources.skillPaths,
45
+ }));
46
+
47
+ pi.registerCommand("workflow", {
48
+ description: "Show or switch the active BYZ workflow",
49
+ handler: async (args, ctx) => {
50
+ const targetWorkflowId = args.trim();
51
+ if (!targetWorkflowId) {
52
+ ctx.ui.notify(`BYZ workflow: ${activeWorkflowId}`, "info");
53
+ return;
54
+ }
55
+ if (!WORKFLOW_IDS.has(targetWorkflowId)) {
56
+ ctx.ui.notify("Usage: /workflow [cm|cm-plugin|none]", "error");
57
+ return;
58
+ }
59
+ if (!ctx.isIdle()) {
60
+ ctx.ui.notify("BYZ cannot switch workflows while the agent is running.", "warning");
61
+ return;
62
+ }
63
+ if (targetWorkflowId === activeWorkflowId) {
64
+ ctx.ui.notify(`BYZ workflow is already ${activeWorkflowId}.`, "info");
65
+ return;
66
+ }
67
+
68
+ let nextResources;
69
+ try {
70
+ nextResources = await resolveResources(targetWorkflowId);
71
+ } catch (error) {
72
+ ctx.ui.notify(error instanceof Error ? error.message : String(error), "error");
73
+ return;
74
+ }
75
+ if (!ctx.isIdle()) {
76
+ ctx.ui.notify("BYZ cannot switch workflows while the agent is running.", "warning");
77
+ return;
78
+ }
79
+
80
+ ctx.ui.notify(`Switching BYZ workflow to ${targetWorkflowId}...`, "info");
81
+ try {
82
+ await ctx.replaceByzWorkflowResources(nextResources);
83
+ } catch (error) {
84
+ ctx.ui.notify(
85
+ `BYZ workflow switch failed: ${error instanceof Error ? error.message : String(error)}`,
86
+ "error",
87
+ );
88
+ return;
89
+ }
90
+ activeResources = nextResources;
91
+ activeWorkflowId = targetWorkflowId;
92
+ },
93
+ });
94
+ };
95
+ }
package/dist/workflows.js CHANGED
@@ -2,6 +2,7 @@ import { readdir, readFile, realpath, stat } from "node:fs/promises";
2
2
  import { dirname, isAbsolute, relative, resolve, sep } from "node:path";
3
3
  import { fileURLToPath } from "node:url";
4
4
  import { loadSkillsFromDir } from "./runtime/bundle/index.js";
5
+ import { getActiveByzOptionIndexes } from "./workflow-switch.js";
5
6
 
6
7
  const lockPath = fileURLToPath(new URL("../workflows.lock.json", import.meta.url));
7
8
  const packageDir = dirname(lockPath);
@@ -175,6 +176,7 @@ function printStatus(status) {
175
176
 
176
177
  export function parseWorkflowOption(args) {
177
178
  const forwardedArgs = [];
179
+ const activeWorkflowOptions = getActiveByzOptionIndexes(args, "workflow");
178
180
  let selected;
179
181
  for (let index = 0; index < args.length; index++) {
180
182
  const arg = args[index];
@@ -182,14 +184,14 @@ export function parseWorkflowOption(args) {
182
184
  forwardedArgs.push(...args.slice(index));
183
185
  break;
184
186
  }
185
- if (arg === "--workflow") {
187
+ if (arg === "--workflow" && activeWorkflowOptions.has(index)) {
186
188
  if (selected !== undefined) throw new Error("--workflow may only be specified once.");
187
189
  const value = args[++index];
188
190
  if (!value || value.startsWith("-")) throw new Error("--workflow requires cm, cm-plugin, or none.");
189
191
  selected = value;
190
192
  continue;
191
193
  }
192
- if (arg.startsWith("--workflow=")) {
194
+ if (arg.startsWith("--workflow=") && activeWorkflowOptions.has(index)) {
193
195
  if (selected !== undefined) throw new Error("--workflow may only be specified once.");
194
196
  selected = arg.slice("--workflow=".length);
195
197
  continue;
@@ -203,31 +205,38 @@ export function parseWorkflowOption(args) {
203
205
  return { forwardedArgs, workflowId };
204
206
  }
205
207
 
206
- export async function prepareWorkflowRuntimeArgs(args, options = {}) {
207
- const { forwardedArgs, workflowId } = parseWorkflowOption(args);
208
- if (options.load === false || workflowId === "none") {
209
- return { args: forwardedArgs, workflowId };
208
+ export async function resolveWorkflowRuntimeResources(workflowId, args = []) {
209
+ if (workflowId === "none") {
210
+ return { promptPaths: [], skillPaths: [] };
210
211
  }
211
212
 
212
213
  const status = await checkWorkflow(await getWorkflow(workflowId));
213
- const terminatorIndex = forwardedArgs.indexOf("--");
214
- const optionArgs = forwardedArgs.slice(0, terminatorIndex === -1 ? forwardedArgs.length : terminatorIndex);
214
+ const terminatorIndex = args.indexOf("--");
215
+ const optionArgs = args.slice(0, terminatorIndex === -1 ? args.length : terminatorIndex);
215
216
  const noSkills = optionArgs.some((arg) => arg === "--no-skills" || arg === "-ns");
216
217
  const noPrompts = optionArgs.some((arg) => arg === "--no-prompt-templates" || arg === "-np");
217
- const workflowArgs = [];
218
- if (!noSkills) {
219
- workflowArgs.push(...status.skillsPaths.flatMap((skillPath) => ["--skill", resolve(status.root, skillPath)]));
220
- }
221
- if (!noPrompts) {
222
- workflowArgs.push("--prompt-template", resolve(status.root, status.promptsPath));
218
+ return {
219
+ promptPaths: noPrompts ? [] : [resolve(status.root, status.promptsPath)],
220
+ skillPaths: noSkills ? [] : status.skillsPaths.map((skillPath) => resolve(status.root, skillPath)),
221
+ };
222
+ }
223
+
224
+ export async function prepareWorkflowRuntimeArgs(args, options = {}) {
225
+ const { forwardedArgs, workflowId } = parseWorkflowOption(args);
226
+ if (options.load === false) {
227
+ return { args: forwardedArgs, workflowId };
223
228
  }
229
+
230
+ const resources = await resolveWorkflowRuntimeResources(workflowId, forwardedArgs);
231
+ const workflowArgs = resources.skillPaths.flatMap((skillPath) => ["--skill", skillPath]);
232
+ workflowArgs.push(...resources.promptPaths.flatMap((promptPath) => ["--prompt-template", promptPath]));
224
233
  return {
225
234
  workflowId,
226
235
  args: [...workflowArgs, ...forwardedArgs],
227
236
  };
228
237
  }
229
238
 
230
- export async function handleWorkflowCommand(args) {
239
+ export async function handleWorkflowCommand(args, options = {}) {
231
240
  if (args[0] !== "workflow") return false;
232
241
 
233
242
  try {
@@ -241,8 +250,14 @@ export async function handleWorkflowCommand(args) {
241
250
  }
242
251
 
243
252
  if (command === "status") {
253
+ const activeWorkflowId = options.workflowId ?? parseWorkflowOption([]).workflowId;
254
+ const targetWorkflowId = args[2] ?? activeWorkflowId;
255
+ if (targetWorkflowId === "none") {
256
+ console.log(`none: ${activeWorkflowId === "none" ? "active" : "available"}`);
257
+ return true;
258
+ }
244
259
  await assertDistinctRoots();
245
- printStatus(await getWorkflowStatus(await getWorkflow(args[2])));
260
+ printStatus(await getWorkflowStatus(await getWorkflow(targetWorkflowId)));
246
261
  return true;
247
262
  }
248
263
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aibyzero/byz",
3
- "version": "0.1.3",
3
+ "version": "0.1.5",
4
4
  "description": "Business-first coding agent built on Pi",
5
5
  "type": "module",
6
6
  "piConfig": {