@voicelayer/sdk 0.1.7 → 0.1.8

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/index.js CHANGED
@@ -137,6 +137,9 @@ var init_flow = __esm({
137
137
  "llm",
138
138
  "rag",
139
139
  "memory",
140
+ // Call-wide voice/turn-taking capability (barge-in + endpointing tuning);
141
+ // managed in the Capabilities panel like `memory`, never a graph step.
142
+ "speech",
140
143
  "classify",
141
144
  // Agentic router: per-turn, selects 1-of-N skills by their plain-language
142
145
  // descriptions and takes that port (the resident routing surface / hub).
@@ -335,6 +338,19 @@ var init_agents = __esm({
335
338
  }).optional(),
336
339
  // Tool capabilities compiled from tool nodes (maps to AgentConfig.tools).
337
340
  tools: z.array(ProcessToolDTO).max(32).optional(),
341
+ // Voice turn-taking compiled from the flow's speech capability node (maps to
342
+ // AgentConfig.speech → applySpeechTurnHandling). Absent = platform defaults.
343
+ speech: z.object({
344
+ interruption: z.object({
345
+ enabled: z.boolean().optional(),
346
+ minWords: z.number().int().min(0).max(10).optional(),
347
+ minDuration: z.number().int().min(0).max(5e3).optional()
348
+ }).optional(),
349
+ endpointing: z.object({
350
+ minDelay: z.number().int().min(0).max(5e3).optional(),
351
+ maxDelay: z.number().int().min(0).max(15e3).optional()
352
+ }).optional()
353
+ }).optional(),
338
354
  // Graph-preserving compiled program. When present and the flow-runtime graph
339
355
  // mode is enabled, the worker executes this node-graph deterministically
340
356
  // (the interpreter) instead of the flat goals+rails form above. Embedded here
@@ -494,7 +510,7 @@ var init_consultation = __esm({
494
510
  });
495
511
  }
496
512
  });
497
- var CALL_CONTROL_PUBSUB_CHANNEL, CallEventKind, SayCommand, HangupCommand, DtmfCommand, InstructCommand, CallControlCommand;
513
+ var CALL_CONTROL_PUBSUB_CHANNEL, CallEventKind, OP_CALL_EVENT_KIND, OpCallEventKind, SayCommand, HangupCommand, DtmfCommand, InstructCommand, CallControlCommand;
498
514
  var init_call_events = __esm({
499
515
  "../contracts/src/call-events.ts"() {
500
516
  init_consultation();
@@ -520,6 +536,8 @@ var init_call_events = __esm({
520
536
  "dtmf.received",
521
537
  "dtmf.sent"
522
538
  ]);
539
+ OP_CALL_EVENT_KIND = /^(tool|handoff|lookup|record|notify)\.[a-z0-9_]{1,48}(\.[a-z0-9_]{1,48})?$/;
540
+ OpCallEventKind = z.string().regex(OP_CALL_EVENT_KIND);
523
541
  z.object({
524
542
  reason: z.string().optional(),
525
543
  durationMs: z.number().int().min(0).optional(),
@@ -557,7 +575,8 @@ var init_call_events = __esm({
557
575
  seq: z.number().int().min(0),
558
576
  callId: z.string().uuid(),
559
577
  projectId: z.string().min(1),
560
- kind: CallEventKind,
578
+ // Closed lifecycle kinds OR the namespaced operational vocabulary.
579
+ kind: z.union([CallEventKind, OpCallEventKind]),
561
580
  payload: z.unknown(),
562
581
  ts: z.string().datetime()
563
582
  });
@@ -1914,7 +1933,20 @@ function nodeConfigFor(node) {
1914
1933
  ...typeof data.connectionRef === "string" ? { connectionRef: data.connectionRef } : {},
1915
1934
  // Registry reference: run the project HTTP tool with this NAME via the
1916
1935
  // server-side proxy instead of the inline url/method/auth above.
1917
- ...typeof data.toolRef === "string" && data.toolRef ? { toolRef: data.toolRef } : {}
1936
+ ...typeof data.toolRef === "string" && data.toolRef ? { toolRef: data.toolRef } : {},
1937
+ // Promote result fields into NAMED slots on success:
1938
+ // { slotName: "data.path" }. Later nodes then read {{ slotName }}
1939
+ // directly instead of {{ tool.<nodeId>.data.path }} via a set node.
1940
+ ...(() => {
1941
+ if (!data.outputAs || typeof data.outputAs !== "object") return {};
1942
+ const outputAs = {};
1943
+ for (const [slot, path] of Object.entries(data.outputAs)) {
1944
+ if (typeof path === "string" && path.trim() && /^[a-zA-Z_][\w.]*$/.test(slot)) {
1945
+ outputAs[slot] = path.trim();
1946
+ }
1947
+ }
1948
+ return Object.keys(outputAs).length ? { outputAs } : {};
1949
+ })()
1918
1950
  };
1919
1951
  }
1920
1952
  case "gate":
@@ -1927,7 +1959,10 @@ function nodeConfigFor(node) {
1927
1959
  ...typeof data.fallback === "string" ? { fallback: data.fallback } : {},
1928
1960
  ...typeof data.on === "string" ? { on: data.on } : {},
1929
1961
  // Per-node warm (conference brief) / cold (blind REFER) override.
1930
- ...data.mode === "warm" || data.mode === "cold" ? { mode: data.mode } : {}
1962
+ ...data.mode === "warm" || data.mode === "cold" ? { mode: data.mode } : {},
1963
+ // What the joining human HEARS (warm mode speaks it verbatim once they
1964
+ // answer). {{ }}-interpolated at runtime against the slot scope.
1965
+ ...typeof data.briefing === "string" && data.briefing.trim() ? { briefing: data.briefing } : {}
1931
1966
  };
1932
1967
  case "end":
1933
1968
  return {
@@ -2091,7 +2126,7 @@ var init_flow_compile = __esm({
2091
2126
  HISTORY_POLICIES = /* @__PURE__ */ new Set(["full", "last-turn", "slots-only"]);
2092
2127
  ADHERENCE_MODES = /* @__PURE__ */ new Set(["off", "observe", "enforce"]);
2093
2128
  UNSUPPORTED_NODE_TYPES = /* @__PURE__ */ new Set([]);
2094
- CAPABILITY_NODE_TYPES = /* @__PURE__ */ new Set(["memory", "trigger"]);
2129
+ CAPABILITY_NODE_TYPES = /* @__PURE__ */ new Set(["memory", "trigger", "speech"]);
2095
2130
  ANNOTATION_NODE_TYPES = /* @__PURE__ */ new Set(["note"]);
2096
2131
  }
2097
2132
  });
@@ -3141,7 +3176,7 @@ var init_executors = __esm({
3141
3176
  if (msg) await speak(interpolate(msg, scopeFor(state, deps)), deps);
3142
3177
  return { kind: "end" };
3143
3178
  };
3144
- handoffExecutor = async (node, _state, deps) => {
3179
+ handoffExecutor = async (node, state, deps) => {
3145
3180
  const cfg = node.config;
3146
3181
  const target = str(cfg.to) || str(cfg.fallback);
3147
3182
  if (!target) {
@@ -3150,9 +3185,14 @@ var init_executors = __esm({
3150
3185
  }
3151
3186
  const reason = str(cfg.reason) || `flow:${node.id}`;
3152
3187
  const mode = cfg.mode === "warm" || cfg.mode === "cold" ? cfg.mode : void 0;
3188
+ const briefing = str(cfg.briefing) ? interpolate(str(cfg.briefing), scopeFor(state, deps)) : void 0;
3153
3189
  deps.events.note("handoff.start", { node: node.id, to: target, ...mode ? { mode } : {} });
3154
3190
  try {
3155
- await deps.ctx.handoff(target, { reason, ...mode ? { mode } : {} });
3191
+ await deps.ctx.handoff(target, {
3192
+ reason,
3193
+ ...mode ? { mode } : {},
3194
+ ...briefing ? { briefing } : {}
3195
+ });
3156
3196
  } catch (err) {
3157
3197
  deps.events.note("handoff.failed", {
3158
3198
  node: node.id,
@@ -3206,7 +3246,18 @@ ${collected}`);
3206
3246
  const cfg = node.config;
3207
3247
  const name = str(cfg.name) || node.id;
3208
3248
  const routeByOutcome = () => {
3209
- const ok = state.toolResults[node.id]?.ok === true;
3249
+ const result = state.toolResults[node.id];
3250
+ const ok = result?.ok === true;
3251
+ if (ok && cfg.outputAs && typeof cfg.outputAs === "object") {
3252
+ for (const [slot, path] of Object.entries(cfg.outputAs)) {
3253
+ if (typeof path !== "string" || !path.trim()) continue;
3254
+ const value = resolvePath(result, path.trim());
3255
+ if (value !== void 0 && value !== null) {
3256
+ deps.processRt.captureField(slot, value);
3257
+ deps.events.note("tool.output_captured", { node: node.id, slot });
3258
+ }
3259
+ }
3260
+ }
3210
3261
  return routeByPort(node, deps, ok ? "ok" : "fail");
3211
3262
  };
3212
3263
  const toolRef = str(cfg.toolRef);
@@ -5262,12 +5313,15 @@ var CallsClient = class {
5262
5313
  );
5263
5314
  }
5264
5315
  /**
5265
- * Append a structured call event. Today the API accepts consultation
5266
- * lifecycle kinds only — see apps/api/src/routes/calls.ts AppendEventBody.
5316
+ * Append a structured call event — consultation lifecycle kinds, or the
5317
+ * operational vocabulary the call-detail Timeline renders between
5318
+ * transcript rows (tool.* / handoff.* / lookup.* / record.* / notify.*).
5319
+ * See apps/api/src/routes/calls.ts AppendEventBody for the accepted shapes.
5267
5320
  *
5268
5321
  * The agent SDK's built-in `ask_host` tool calls this on consultation start
5269
- * / end so the MCP host (via SSE) and dashboard see the "let me check" UX
5270
- * in real time.
5322
+ * / end; the handoff runtime and graph interpreter emit op events through it
5323
+ * so the operational story (dial → answered → briefed → dropped, tool calls)
5324
+ * is visible in the dashboard, not just the spoken transcript.
5271
5325
  */
5272
5326
  async appendEvent(callId, input) {
5273
5327
  await this.transport.request(
@@ -5686,6 +5740,18 @@ init_conditions();
5686
5740
  init_interpreter();
5687
5741
 
5688
5742
  // src/runtime/graph/events.ts
5743
+ var OP_EVENT_NOTE = /^(tool|handoff|lookup|record|notify)\./;
5744
+ function withOpEventFanout(events, notify) {
5745
+ return {
5746
+ enter: (nodeId, type) => events.enter(nodeId, type),
5747
+ traverse: (from, to, via) => events.traverse(from, to, via),
5748
+ note(kind, data) {
5749
+ events.note(kind, data);
5750
+ if (OP_EVENT_NOTE.test(kind)) notify(kind, data ?? {});
5751
+ },
5752
+ currentNodeId: () => events.currentNodeId()
5753
+ };
5754
+ }
5689
5755
  function createGraphEvents(processRt) {
5690
5756
  let current = null;
5691
5757
  return {
@@ -8214,13 +8280,33 @@ function processSchemaToAgentParts(schema, opts = {}) {
8214
8280
  );
8215
8281
  }
8216
8282
  }
8283
+ let speech;
8284
+ if (schema.speech) {
8285
+ const i = schema.speech.interruption;
8286
+ const e = schema.speech.endpointing;
8287
+ const interruption = i ? {
8288
+ ...i.enabled !== void 0 ? { enabled: i.enabled } : {},
8289
+ ...i.minWords !== void 0 ? { minWords: i.minWords } : {},
8290
+ ...i.minDuration !== void 0 ? { minDuration: i.minDuration } : {}
8291
+ } : void 0;
8292
+ const endpointing = e ? {
8293
+ ...e.minDelay !== void 0 ? { minDelay: e.minDelay } : {},
8294
+ ...e.maxDelay !== void 0 ? { maxDelay: e.maxDelay } : {}
8295
+ } : void 0;
8296
+ speech = {
8297
+ ...interruption && Object.keys(interruption).length ? { interruption } : {},
8298
+ ...endpointing && Object.keys(endpointing).length ? { endpointing } : {}
8299
+ };
8300
+ if (Object.keys(speech).length === 0) speech = void 0;
8301
+ }
8217
8302
  return {
8218
8303
  prompt,
8219
8304
  process: process2,
8220
8305
  ...triggers ? { triggers } : {},
8221
8306
  ...handoff ? { handoff } : {},
8222
8307
  ...memory ? { memory } : {},
8223
- ...tools ? { tools } : {}
8308
+ ...tools ? { tools } : {},
8309
+ ...speech ? { speech } : {}
8224
8310
  };
8225
8311
  }
8226
8312
  var BrainConfigError = class extends Error {
@@ -10877,17 +10963,28 @@ async function executeHandoff(args, config, deps) {
10877
10963
  const briefing = args.briefing ?? await buildBriefing(config, deps) ?? `Handoff to ${args.to}`;
10878
10964
  const mode = args.mode ?? config?.mode ?? "warm";
10879
10965
  const sipOps = deps.sipOps ?? buildDefaultSipOps();
10966
+ const notify = deps.notify ?? (() => {
10967
+ });
10880
10968
  if (mode === "warm" && sipOps && sipOps.canConference) {
10881
10969
  try {
10882
10970
  await sayFixed(deps, "One moment \u2014 I'm bringing our on-call engineer onto the line now. Stay with me.");
10971
+ notify("handoff.dialing", { to: args.to, mode: "warm" });
10883
10972
  await sipOps.addParticipant(deps.roomName, normalizeSipTarget(args.to));
10973
+ notify("handoff.answered", { to: args.to });
10884
10974
  await sayFixed(deps, briefing);
10975
+ notify("handoff.briefed", { to: args.to, briefing });
10885
10976
  await sayFixed(deps, "You're both connected now \u2014 I'll drop off.");
10886
10977
  await quiesce(deps);
10887
10978
  await deps.disconnect();
10979
+ notify("handoff.agent_dropped", { to: args.to });
10888
10980
  return { ok: true, via: "conference", target: args.to };
10889
10981
  } catch (err) {
10890
10982
  console.error("[handoff] conference bridge failed, falling back to REFER", err);
10983
+ notify("handoff.failed", {
10984
+ to: args.to,
10985
+ via: "conference",
10986
+ error: err instanceof Error ? err.message : String(err)
10987
+ });
10891
10988
  }
10892
10989
  }
10893
10990
  if (sipOps) {
@@ -10896,9 +10993,15 @@ async function executeHandoff(args, config, deps) {
10896
10993
  }
10897
10994
  try {
10898
10995
  await sipOps.refer(deps.roomName, deps.callerIdentity, normalizeSipTarget(args.to));
10996
+ notify("handoff.refer", { to: args.to });
10899
10997
  return { ok: true, via: "sip", target: args.to };
10900
10998
  } catch (err) {
10901
10999
  console.error("[handoff] SIP REFER failed, falling back to disconnect", err);
11000
+ notify("handoff.failed", {
11001
+ to: args.to,
11002
+ via: "refer",
11003
+ error: err instanceof Error ? err.message : String(err)
11004
+ });
10902
11005
  }
10903
11006
  }
10904
11007
  try {
@@ -12645,7 +12748,11 @@ var Agent = class {
12645
12748
  ...parts.triggers ? { triggers: parts.triggers } : {},
12646
12749
  ...parts.handoff ? { handoff: parts.handoff } : {},
12647
12750
  ...parts.memory ? { memory: parts.memory } : {},
12648
- ...parts.tools ? { tools: { ...effectiveConfig.tools ?? {}, ...parts.tools } } : {}
12751
+ ...parts.tools ? { tools: { ...effectiveConfig.tools ?? {}, ...parts.tools } } : {},
12752
+ // Flow-authored turn-taking (schema.speech). Merged over any
12753
+ // worker-level speech config; applySpeechTurnHandling reads this
12754
+ // off effectiveConfig at session build.
12755
+ ...parts.speech ? { speech: { ...effectiveConfig.speech ?? {}, ...parts.speech } } : {}
12649
12756
  };
12650
12757
  console.log("[agent] booted from flow", {
12651
12758
  agentId: flowAgentId,
@@ -12706,7 +12813,13 @@ var Agent = class {
12706
12813
  const processRt = createProcessRuntime(effectiveConfig.process);
12707
12814
  seedCallPrefill(processRt, dispatchMdEarly);
12708
12815
  await seedProjectVariables(processRt);
12709
- const graphEvents = graphMode ? createGraphEvents(processRt) : null;
12816
+ let opEventCallId = null;
12817
+ const emitOpEvent = (kind, payload) => {
12818
+ if (!sdkClient || !opEventCallId) return;
12819
+ void sdkClient.calls.appendEvent(opEventCallId, { kind, payload }).catch(() => {
12820
+ });
12821
+ };
12822
+ const graphEvents = graphMode ? withOpEventFanout(createGraphEvents(processRt), emitOpEvent) : null;
12710
12823
  const isOutbound = stringValue(dispatchMdEarly["direction"]) === "outbound";
12711
12824
  const perCallAmd = stringValue(dispatchMdEarly["amd"]);
12712
12825
  const amdMode = perCallAmd === "off" || perCallAmd === "detect" || perCallAmd === "detectMessageEnd" ? perCallAmd : effectiveConfig.outbound?.amd ?? "off";
@@ -12798,6 +12911,7 @@ var Agent = class {
12798
12911
  });
12799
12912
  }
12800
12913
  }
12914
+ opEventCallId = consultationCallId;
12801
12915
  let agentSpeechState = "initializing";
12802
12916
  const idleWaiters = /* @__PURE__ */ new Set();
12803
12917
  const waitUntilAgentIdle = async (timeoutMs) => {
@@ -12981,7 +13095,8 @@ ${callIntent}`
12981
13095
  }
12982
13096
  },
12983
13097
  getProcessData: () => processRt.getData(),
12984
- transcript
13098
+ transcript,
13099
+ notify: (kind, payload) => emitOpEvent(kind, payload)
12985
13100
  });
12986
13101
  const triggersRt = createTriggersRuntime(effectiveConfig.triggers, handoffRt);
12987
13102
  const audioExperience = new AudioExperiencePrimitive();
@@ -1,3 +1,3 @@
1
- export { a6 as GraphTraceEvent, q as RunTextSessionOptions, r as RunTextTranscriptOptions, T as TextSession, O as TextTranscriptResult, a3 as runTextSession, a4 as runTextTranscript } from '../text-session-B8-jhQzv.js';
1
+ export { a6 as GraphTraceEvent, q as RunTextSessionOptions, r as RunTextTranscriptOptions, T as TextSession, O as TextTranscriptResult, a3 as runTextSession, a4 as runTextTranscript } from '../text-session-BoUmDEX9.js';
2
2
  import '@livekit/agents';
3
3
  import 'zod';
@@ -97,6 +97,9 @@ var init_flow = __esm({
97
97
  "llm",
98
98
  "rag",
99
99
  "memory",
100
+ // Call-wide voice/turn-taking capability (barge-in + endpointing tuning);
101
+ // managed in the Capabilities panel like `memory`, never a graph step.
102
+ "speech",
100
103
  "classify",
101
104
  // Agentic router: per-turn, selects 1-of-N skills by their plain-language
102
105
  // descriptions and takes that port (the resident routing surface / hub).
@@ -295,6 +298,19 @@ var init_agents = __esm({
295
298
  }).optional(),
296
299
  // Tool capabilities compiled from tool nodes (maps to AgentConfig.tools).
297
300
  tools: z.array(ProcessToolDTO).max(32).optional(),
301
+ // Voice turn-taking compiled from the flow's speech capability node (maps to
302
+ // AgentConfig.speech → applySpeechTurnHandling). Absent = platform defaults.
303
+ speech: z.object({
304
+ interruption: z.object({
305
+ enabled: z.boolean().optional(),
306
+ minWords: z.number().int().min(0).max(10).optional(),
307
+ minDuration: z.number().int().min(0).max(5e3).optional()
308
+ }).optional(),
309
+ endpointing: z.object({
310
+ minDelay: z.number().int().min(0).max(5e3).optional(),
311
+ maxDelay: z.number().int().min(0).max(15e3).optional()
312
+ }).optional()
313
+ }).optional(),
298
314
  // Graph-preserving compiled program. When present and the flow-runtime graph
299
315
  // mode is enabled, the worker executes this node-graph deterministically
300
316
  // (the interpreter) instead of the flat goals+rails form above. Embedded here
@@ -452,7 +468,7 @@ var init_consultation = __esm({
452
468
  });
453
469
  }
454
470
  });
455
- var CallEventKind, SayCommand, HangupCommand, DtmfCommand, InstructCommand;
471
+ var CallEventKind, OP_CALL_EVENT_KIND, OpCallEventKind, SayCommand, HangupCommand, DtmfCommand, InstructCommand;
456
472
  var init_call_events = __esm({
457
473
  "../contracts/src/call-events.ts"() {
458
474
  init_consultation();
@@ -477,6 +493,8 @@ var init_call_events = __esm({
477
493
  "dtmf.received",
478
494
  "dtmf.sent"
479
495
  ]);
496
+ OP_CALL_EVENT_KIND = /^(tool|handoff|lookup|record|notify)\.[a-z0-9_]{1,48}(\.[a-z0-9_]{1,48})?$/;
497
+ OpCallEventKind = z.string().regex(OP_CALL_EVENT_KIND);
480
498
  z.object({
481
499
  reason: z.string().optional(),
482
500
  durationMs: z.number().int().min(0).optional(),
@@ -514,7 +532,8 @@ var init_call_events = __esm({
514
532
  seq: z.number().int().min(0),
515
533
  callId: z.string().uuid(),
516
534
  projectId: z.string().min(1),
517
- kind: CallEventKind,
535
+ // Closed lifecycle kinds OR the namespaced operational vocabulary.
536
+ kind: z.union([CallEventKind, OpCallEventKind]),
518
537
  payload: z.unknown(),
519
538
  ts: z.string().datetime()
520
539
  });
@@ -2645,7 +2664,7 @@ var init_executors = __esm({
2645
2664
  if (msg) await speak(interpolate(msg, scopeFor(state, deps)), deps);
2646
2665
  return { kind: "end" };
2647
2666
  };
2648
- handoffExecutor = async (node, _state, deps) => {
2667
+ handoffExecutor = async (node, state, deps) => {
2649
2668
  const cfg = node.config;
2650
2669
  const target = str(cfg.to) || str(cfg.fallback);
2651
2670
  if (!target) {
@@ -2654,9 +2673,14 @@ var init_executors = __esm({
2654
2673
  }
2655
2674
  const reason = str(cfg.reason) || `flow:${node.id}`;
2656
2675
  const mode = cfg.mode === "warm" || cfg.mode === "cold" ? cfg.mode : void 0;
2676
+ const briefing = str(cfg.briefing) ? interpolate(str(cfg.briefing), scopeFor(state, deps)) : void 0;
2657
2677
  deps.events.note("handoff.start", { node: node.id, to: target, ...mode ? { mode } : {} });
2658
2678
  try {
2659
- await deps.ctx.handoff(target, { reason, ...mode ? { mode } : {} });
2679
+ await deps.ctx.handoff(target, {
2680
+ reason,
2681
+ ...mode ? { mode } : {},
2682
+ ...briefing ? { briefing } : {}
2683
+ });
2660
2684
  } catch (err) {
2661
2685
  deps.events.note("handoff.failed", {
2662
2686
  node: node.id,
@@ -2710,7 +2734,18 @@ ${collected}`);
2710
2734
  const cfg = node.config;
2711
2735
  const name = str(cfg.name) || node.id;
2712
2736
  const routeByOutcome = () => {
2713
- const ok = state.toolResults[node.id]?.ok === true;
2737
+ const result = state.toolResults[node.id];
2738
+ const ok = result?.ok === true;
2739
+ if (ok && cfg.outputAs && typeof cfg.outputAs === "object") {
2740
+ for (const [slot, path] of Object.entries(cfg.outputAs)) {
2741
+ if (typeof path !== "string" || !path.trim()) continue;
2742
+ const value = resolvePath(result, path.trim());
2743
+ if (value !== void 0 && value !== null) {
2744
+ deps.processRt.captureField(slot, value);
2745
+ deps.events.note("tool.output_captured", { node: node.id, slot });
2746
+ }
2747
+ }
2748
+ }
2714
2749
  return routeByPort(node, deps, ok ? "ok" : "fail");
2715
2750
  };
2716
2751
  const toolRef = str(cfg.toolRef);
@@ -90,7 +90,7 @@ declare const FlowProgram: z.ZodObject<{
90
90
  entry: z.ZodArray<z.ZodString, "many">;
91
91
  nodes: z.ZodRecord<z.ZodString, z.ZodObject<{
92
92
  id: z.ZodString;
93
- type: z.ZodEnum<["start", "say", "ask", "confirm", "tool", "decision", "handoff", "end", "trigger", "gate", "playbook", "menu", "code", "set", "subflow", "llm", "rag", "memory", "classify", "router", "note"]>;
93
+ type: z.ZodEnum<["start", "say", "ask", "confirm", "tool", "decision", "handoff", "end", "trigger", "gate", "playbook", "menu", "code", "set", "subflow", "llm", "rag", "memory", "speech", "classify", "router", "note"]>;
94
94
  config: z.ZodRecord<z.ZodString, z.ZodUnknown>;
95
95
  out: z.ZodArray<z.ZodObject<{
96
96
  to: z.ZodString;
@@ -99,34 +99,34 @@ declare const FlowProgram: z.ZodObject<{
99
99
  label: z.ZodOptional<z.ZodString>;
100
100
  }, "strip", z.ZodTypeAny, {
101
101
  to: string;
102
+ condition?: string | undefined;
102
103
  sourceHandle?: string | undefined;
103
104
  label?: string | undefined;
104
- condition?: string | undefined;
105
105
  }, {
106
106
  to: string;
107
+ condition?: string | undefined;
107
108
  sourceHandle?: string | undefined;
108
109
  label?: string | undefined;
109
- condition?: string | undefined;
110
110
  }>, "many">;
111
111
  }, "strip", z.ZodTypeAny, {
112
- type: "code" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "set" | "subflow" | "llm" | "rag" | "memory" | "classify" | "router" | "note";
112
+ type: "code" | "set" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "subflow" | "llm" | "rag" | "memory" | "speech" | "classify" | "router" | "note";
113
113
  id: string;
114
114
  config: Record<string, unknown>;
115
115
  out: {
116
116
  to: string;
117
+ condition?: string | undefined;
117
118
  sourceHandle?: string | undefined;
118
119
  label?: string | undefined;
119
- condition?: string | undefined;
120
120
  }[];
121
121
  }, {
122
- type: "code" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "set" | "subflow" | "llm" | "rag" | "memory" | "classify" | "router" | "note";
122
+ type: "code" | "set" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "subflow" | "llm" | "rag" | "memory" | "speech" | "classify" | "router" | "note";
123
123
  id: string;
124
124
  config: Record<string, unknown>;
125
125
  out: {
126
126
  to: string;
127
+ condition?: string | undefined;
127
128
  sourceHandle?: string | undefined;
128
129
  label?: string | undefined;
129
- condition?: string | undefined;
130
130
  }[];
131
131
  }>>;
132
132
  completionGate: z.ZodObject<{
@@ -152,18 +152,18 @@ declare const FlowProgram: z.ZodObject<{
152
152
  }, "strip", z.ZodTypeAny, {
153
153
  v: 1;
154
154
  id: string;
155
+ entry: string[];
155
156
  nodes: Record<string, {
156
- type: "code" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "set" | "subflow" | "llm" | "rag" | "memory" | "classify" | "router" | "note";
157
+ type: "code" | "set" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "subflow" | "llm" | "rag" | "memory" | "speech" | "classify" | "router" | "note";
157
158
  id: string;
158
159
  config: Record<string, unknown>;
159
160
  out: {
160
161
  to: string;
162
+ condition?: string | undefined;
161
163
  sourceHandle?: string | undefined;
162
164
  label?: string | undefined;
163
- condition?: string | undefined;
164
165
  }[];
165
166
  }>;
166
- entry: string[];
167
167
  completionGate: {
168
168
  requiredFields: string[];
169
169
  };
@@ -175,18 +175,18 @@ declare const FlowProgram: z.ZodObject<{
175
175
  }, {
176
176
  v: 1;
177
177
  id: string;
178
+ entry: string[];
178
179
  nodes: Record<string, {
179
- type: "code" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "set" | "subflow" | "llm" | "rag" | "memory" | "classify" | "router" | "note";
180
+ type: "code" | "set" | "start" | "say" | "ask" | "confirm" | "tool" | "decision" | "handoff" | "end" | "trigger" | "gate" | "playbook" | "menu" | "subflow" | "llm" | "rag" | "memory" | "speech" | "classify" | "router" | "note";
180
181
  id: string;
181
182
  config: Record<string, unknown>;
182
183
  out: {
183
184
  to: string;
185
+ condition?: string | undefined;
184
186
  sourceHandle?: string | undefined;
185
187
  label?: string | undefined;
186
- condition?: string | undefined;
187
188
  }[];
188
189
  }>;
189
- entry: string[];
190
190
  completionGate: {
191
191
  requiredFields: string[];
192
192
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@voicelayer/sdk",
3
- "version": "0.1.7",
3
+ "version": "0.1.8",
4
4
  "description": "Official SDK for VoiceLayer — define, run, and orchestrate voice AI agents on the VoiceLayer control plane.",
5
5
  "license": "Apache-2.0",
6
6
  "author": "VoiceLayer",
@@ -79,9 +79,9 @@
79
79
  "tsup": "^8.5.1",
80
80
  "typescript": "^5.6.0",
81
81
  "vitest": "^4.1.5",
82
+ "@voicelayer/contracts": "0.1.0",
82
83
  "@voicelayer/observability": "0.1.0",
83
84
  "@voicelayer/primitive-audio-experience": "0.1.0",
84
- "@voicelayer/contracts": "0.1.0",
85
85
  "@voicelayer/primitive-audio-routing": "0.1.0",
86
86
  "@voicelayer/primitive-process-schema": "0.1.0",
87
87
  "@voicelayer/primitive-security": "0.1.0",