@oxygen-agent/cli 1.1011.681 → 1.1011.767

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 (36) hide show
  1. package/README.md +1 -1
  2. package/dist/column-run-notices.js +2 -0
  3. package/dist/help.d.ts +2 -0
  4. package/dist/help.js +5 -0
  5. package/dist/index.js +139 -91
  6. package/dist/workflow-run-list-flags.d.ts +3 -0
  7. package/dist/workflow-run-list-flags.js +21 -0
  8. package/node_modules/@oxygen/shared/dist/capability-discovery.js +42 -13
  9. package/node_modules/@oxygen/shared/dist/contracts/crm-enrichment-read.js +1 -1
  10. package/node_modules/@oxygen/shared/dist/contracts/crm-support.d.ts +1 -0
  11. package/node_modules/@oxygen/shared/dist/contracts/crm-support.js +1 -0
  12. package/node_modules/@oxygen/shared/dist/contracts/customer-operations.js +8 -6
  13. package/node_modules/@oxygen/shared/dist/contracts/schema.d.ts +8 -0
  14. package/node_modules/@oxygen/shared/dist/contracts/schema.js +6 -0
  15. package/node_modules/@oxygen/shared/dist/contracts/sequence-analytics-read.d.ts +38 -0
  16. package/node_modules/@oxygen/shared/dist/contracts/sequence-analytics-read.js +22 -0
  17. package/node_modules/@oxygen/shared/dist/contracts/table-list.d.ts +31 -0
  18. package/node_modules/@oxygen/shared/dist/contracts/table-list.js +22 -0
  19. package/node_modules/@oxygen/shared/dist/contracts/table-operations.d.ts +58 -0
  20. package/node_modules/@oxygen/shared/dist/contracts/table-operations.js +30 -0
  21. package/node_modules/@oxygen/shared/dist/contracts/workflow-run-list.d.ts +79 -0
  22. package/node_modules/@oxygen/shared/dist/contracts/workflow-run-list.js +38 -0
  23. package/node_modules/@oxygen/shared/dist/copilot-journeys.d.ts +2 -2
  24. package/node_modules/@oxygen/shared/dist/copilot-journeys.generated.d.ts +2 -2
  25. package/node_modules/@oxygen/shared/dist/copilot-journeys.generated.js +2 -2
  26. package/node_modules/@oxygen/shared/dist/copilot-playbooks.generated.d.ts +3 -3
  27. package/node_modules/@oxygen/shared/dist/copilot-playbooks.generated.js +3 -3
  28. package/node_modules/@oxygen/shared/dist/hosted-ai.js +24 -0
  29. package/node_modules/@oxygen/shared/dist/recipes.d.ts +1 -1
  30. package/node_modules/@oxygen/shared/dist/recipes.js +4 -9
  31. package/node_modules/@oxygen/shared/dist/version.generated.d.ts +1 -1
  32. package/node_modules/@oxygen/shared/dist/version.generated.js +1 -1
  33. package/node_modules/@oxygen/workflows/dist/graph/expression.d.ts +1 -0
  34. package/node_modules/@oxygen/workflows/dist/graph/expression.js +15 -0
  35. package/node_modules/@oxygen/workflows/dist/graph/lint.js +8 -2
  36. package/package.json +1 -1
@@ -1,15 +1,15 @@
1
1
  export declare const COPILOT_PLAYBOOKS_GENERATED: readonly [{
2
2
  readonly slug: "icp-to-account-map";
3
3
  readonly title: "TAM sourcing";
4
- readonly prompt: "Turn our ICP into a scored list of target accounts, with the evidence behind each score, so I can see which segments fit best.";
4
+ readonly prompt: "Find about 25 companies that look like our best customers, grade how well each one fits and why, and show me which kinds fit best. If I share a list, portfolio page or event list, grade that instead.";
5
5
  }, {
6
6
  readonly slug: "founder-posting-system";
7
7
  readonly title: "LinkedIn content strategy";
8
- readonly prompt: "Help me post on LinkedIn consistently in my own voice: draft posts from our positioning and ICP, let me approve each one, and track how they perform.";
8
+ readonly prompt: "Help me post on LinkedIn regularly in my own voice: draft a few posts about what we do and who we help, or plan a whole week, let me approve each one before it goes out, and show me how they do.";
9
9
  }, {
10
10
  readonly slug: "inbound-led-outbound";
11
11
  readonly title: "Inbound-led outbound";
12
- readonly prompt: "Turn the people who react to and comment on LinkedIn posts I pick into pipeline: score them against our ICP and message only the good fits from a capped sequence.";
12
+ readonly prompt: "Turn the people paying attention to us on LinkedIn into pipeline: people reacting to my posts or posts I pick, my followers and connections, or my profile viewers. Score them against our ideal customer and send a short LinkedIn message only to the good fits, a few a day.";
13
13
  }, {
14
14
  readonly slug: "daily-warm-lead-queue";
15
15
  readonly title: "Signal-based outbound";
@@ -6,17 +6,17 @@ export const COPILOT_PLAYBOOKS_GENERATED = [
6
6
  {
7
7
  slug: "icp-to-account-map",
8
8
  title: "TAM sourcing",
9
- prompt: "Turn our ICP into a scored list of target accounts, with the evidence behind each score, so I can see which segments fit best.",
9
+ prompt: "Find about 25 companies that look like our best customers, grade how well each one fits and why, and show me which kinds fit best. If I share a list, portfolio page or event list, grade that instead.",
10
10
  },
11
11
  {
12
12
  slug: "founder-posting-system",
13
13
  title: "LinkedIn content strategy",
14
- prompt: "Help me post on LinkedIn consistently in my own voice: draft posts from our positioning and ICP, let me approve each one, and track how they perform.",
14
+ prompt: "Help me post on LinkedIn regularly in my own voice: draft a few posts about what we do and who we help, or plan a whole week, let me approve each one before it goes out, and show me how they do.",
15
15
  },
16
16
  {
17
17
  slug: "inbound-led-outbound",
18
18
  title: "Inbound-led outbound",
19
- prompt: "Turn the people who react to and comment on LinkedIn posts I pick into pipeline: score them against our ICP and message only the good fits from a capped sequence.",
19
+ prompt: "Turn the people paying attention to us on LinkedIn into pipeline: people reacting to my posts or posts I pick, my followers and connections, or my profile viewers. Score them against our ideal customer and send a short LinkedIn message only to the good fits, a few a day.",
20
20
  },
21
21
  {
22
22
  slug: "daily-warm-lead-queue",
@@ -240,6 +240,23 @@ export const LEGACY_MANAGED_AI_COLUMN_MODELS = {
240
240
  "deepseek/deepseek-v4-pro": "medium",
241
241
  "moonshotai/kimi-k2.6": "high",
242
242
  };
243
+ /**
244
+ * Managed model ids OXYGEN ran that never sat in the registry above, mapped to
245
+ * the tier they read as. Labeling only: unlike LEGACY_MANAGED_AI_COLUMN_MODELS,
246
+ * none of these is a valid managed column pin. The credit ledger keeps every id
247
+ * it ever recorded, so `billing usage` and `billing audit --group-by model`
248
+ * returned them raw (OXP-1.6.96, 2026-10-04): in production 25 workspaces hold
249
+ * managed openai/gpt-4.1-mini spend from before the July registry, billed at the
250
+ * low tier; gpt-4.1-nano ran on dev only; deepseek/deepseek-chat is the spintax
251
+ * generator's fixed model.
252
+ */
253
+ const UNREGISTERED_MANAGED_MODEL_LEVELS = {
254
+ "openai/gpt-4.1-mini": "low",
255
+ "openai/gpt-4.1-nano": "low",
256
+ "deepseek/deepseek-chat": "low",
257
+ };
258
+ /** Dev throughput probe pin (tenant-db `resolveManagedAiModelTier` bills it at low). */
259
+ const PERF_TEST_MODEL_ENV = "OXYGEN_OPENROUTER_MODEL_PERF_TEST";
243
260
  /** The tier a retired managed AI-column model id billed at, or null. */
244
261
  export function legacyManagedAiColumnLevel(model) {
245
262
  return Object.prototype.hasOwnProperty.call(LEGACY_MANAGED_AI_COLUMN_MODELS, model)
@@ -442,6 +459,13 @@ function managedModelLabels(preferredUseCase, env = typeof process === "undefine
442
459
  if (!labels.has(model))
443
460
  labels.set(model, MANAGED_AI_TIER_LABELS[level]);
444
461
  }
462
+ for (const [model, level] of Object.entries(UNREGISTERED_MANAGED_MODEL_LEVELS)) {
463
+ if (!labels.has(model))
464
+ labels.set(model, MANAGED_AI_TIER_LABELS[level]);
465
+ }
466
+ const perfTestModel = readTrimmedEnv(env, PERF_TEST_MODEL_ENV);
467
+ if (perfTestModel && !labels.has(perfTestModel))
468
+ labels.set(perfTestModel, MANAGED_AI_TIER_LABELS.low);
445
469
  for (const useCase of ordered) {
446
470
  for (const spec of Object.values(HOSTED_AI_MODEL_REGISTRY[useCase])) {
447
471
  for (const fallback of spec.fallbackModels) {
@@ -13,7 +13,7 @@ export declare const RECIPE_PRIMITIVES: readonly ["knowledge-graph", "recipes",
13
13
  export type RecipePrimitive = typeof RECIPE_PRIMITIVES[number];
14
14
  export declare const RECIPE_PREREQUISITE_KINDS: readonly ["sender", "mailbox", "domain", "integration", "knowledge", "asset", "plan", "data"];
15
15
  export type RecipePrerequisiteKind = typeof RECIPE_PREREQUISITE_KINDS[number];
16
- export declare const RECIPE_BODY_SECTIONS: readonly ["The Play", "What You Get", "When To Run (And When Not To)", "Before You Start", "Steps", "Ready Assets", "Calibrate", "Troubleshooting", "Operator Notes", "Related"];
16
+ export declare const RECIPE_BODY_SECTIONS: readonly ["The Play", "Before You Start", "Steps", "If It Goes Wrong"];
17
17
  export declare const RECIPE_SLUG_PATTERN: RegExp;
18
18
  export declare function recipeWikiSlug(recipeSlug: string): string;
19
19
  export declare const RECIPE_KIT_MAX_STAGES = 6;
@@ -67,19 +67,14 @@ export const RECIPE_PREREQUISITE_KINDS = [
67
67
  "plan",
68
68
  "data",
69
69
  ];
70
- // The ten body sections every recipe carries, in order. The catalog lint
71
- // enforces exact H2 headings so the fleet of authors cannot drift.
70
+ // The four body sections every recipe carries, in order and no others
71
+ // (founder, 2026-10-04): a production audit found lost founders' agents
72
+ // stalling in ten-section essays. The catalog lint enforces exact H2 headings.
72
73
  export const RECIPE_BODY_SECTIONS = [
73
74
  "The Play",
74
- "What You Get",
75
- "When To Run (And When Not To)",
76
75
  "Before You Start",
77
76
  "Steps",
78
- "Ready Assets",
79
- "Calibrate",
80
- "Troubleshooting",
81
- "Operator Notes",
82
- "Related",
77
+ "If It Goes Wrong",
83
78
  ];
84
79
  export const RECIPE_SLUG_PATTERN = /^[a-z0-9][a-z0-9-]{0,119}$/;
85
80
  // Wiki slug an install writes: slots into the starter wiki's seeded
@@ -1 +1 @@
1
- export declare const OXYGEN_BUILD_VERSION = "1.1011.681";
1
+ export declare const OXYGEN_BUILD_VERSION = "1.1011.767";
@@ -1,2 +1,2 @@
1
1
  // GENERATED by scripts/ci/version-stamp.mjs from VERSION + git history. Do not edit; do not commit.
2
- export const OXYGEN_BUILD_VERSION = "1.1011.681";
2
+ export const OXYGEN_BUILD_VERSION = "1.1011.767";
@@ -32,6 +32,7 @@ export declare class WorkflowValueCoercionError extends Error {
32
32
  export declare class WorkflowValueRefUnresolvedError extends Error {
33
33
  readonly path: string;
34
34
  readonly code = "workflow_value_ref_unresolved";
35
+ readonly nextStep: string;
35
36
  constructor(path: string);
36
37
  }
37
38
  /** Apply one explicit scalar conversion without lossy truthiness or truncation. */
@@ -40,14 +40,29 @@ function unresolvedRefRemedy(path) {
40
40
  const skeleton = parts.slice(2).reduceRight((inner, key) => ({ [key]: inner }), "…");
41
41
  return ` Supply it with --input-json '${JSON.stringify(skeleton)}'.`;
42
42
  }
43
+ /**
44
+ * The caller-facing repair, short enough to survive the run-fault collapse
45
+ * (`next_step` is the one free-text field it keeps). An absent optional input
46
+ * is the common case: lint and publish accept the ref, and only the run fails.
47
+ */
48
+ function unresolvedRefNextStep(path) {
49
+ const parts = path.split(".");
50
+ const coalesce = `bind it as a formula, COALESCE(${path}, ""), so a missing value is allowed`;
51
+ if (parts.length >= 3 && parts[0] === "trigger" && parts[1] === "input") {
52
+ return `'${path}' was not in the run input. Pass it in --input-json, list it in input_schema.required, or ${coalesce}.`;
53
+ }
54
+ return `'${path}' was not produced by an earlier step. Check that step's output, or ${coalesce}.`;
55
+ }
43
56
  /** A direct mapping named data the run does not carry; sending undefined is never intentional. */
44
57
  export class WorkflowValueRefUnresolvedError extends Error {
45
58
  path;
46
59
  code = "workflow_value_ref_unresolved";
60
+ nextStep;
47
61
  constructor(path) {
48
62
  super(`Mapped field '${path}' did not resolve in this run.${unresolvedRefRemedy(path)}`);
49
63
  this.path = path;
50
64
  this.name = "WorkflowValueRefUnresolvedError";
65
+ this.nextStep = unresolvedRefNextStep(path);
51
66
  }
52
67
  }
53
68
  /** Apply one explicit scalar conversion without lossy truthiness or truncation. */
@@ -138,7 +138,11 @@ export function assertWorkflowGraphManifest(value, options = {}) {
138
138
  if (result.ok)
139
139
  return;
140
140
  const first = result.issues[0];
141
- throw new Error(first ? `${first.code}: ${first.message}` : "Invalid workflow graph manifest.");
141
+ // The path is the only pointer to the offending node once a caller turns
142
+ // this throw into a typed error (the CLI's local compile keeps the message).
143
+ throw new Error(first
144
+ ? `${first.code}: ${first.message}${first.path ? ` (at ${first.path})` : ""}`
145
+ : "Invalid workflow graph manifest.");
142
146
  }
143
147
  /**
144
148
  * Validate one nested oxygen-js-v1 envelope without requiring its surrounding
@@ -1484,7 +1488,9 @@ value, path, add, scope, depth = 0) {
1484
1488
  if (value.type === "compare") {
1485
1489
  validateValueRef(value.left, `${path}.left`, add, scope);
1486
1490
  if (!isCompareOp(value.op)) {
1487
- add(`${path}.op`, "invalid_condition", "Condition compare op is invalid.");
1491
+ // Blind evals reached for `is_true`, a Tables filter op: name the valid
1492
+ // workflow ops and the boolean spelling instead of only saying "invalid".
1493
+ add(`${path}.op`, "invalid_condition", `Condition op ${JSON.stringify(value.op)?.slice(0, 40) ?? "(missing)"} is not a workflow operator. Use one of: ${[...WORKFLOW_COMPARE_OPS].join(", ")}. For a boolean, compare eq with a literal true.`);
1488
1494
  return;
1489
1495
  }
1490
1496
  if (isUnaryCompareOp(value.op)) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@oxygen-agent/cli",
3
- "version": "1.1011.681",
3
+ "version": "1.1011.767",
4
4
  "private": false,
5
5
  "license": "UNLICENSED",
6
6
  "type": "module",