Skip to main content

wavekat_flow/
lib.rs

1//! `wavekat-flow` — the call-flow ("Receptionist") document model for the
2//! WaveKat voice platform.
3//!
4//! The types in this crate are **generated at build time** from the
5//! normative JSON Schema at `schema/flow.v1.schema.json` — the single
6//! source of truth shared with the `@wavekat/flow-schema` npm package.
7//! See `build.rs`.
8//!
9//! Phase 2 (this milestone) adds the semantic validator ([`validate`]), the
10//! hours/timezone math ([`hours`]), and the interpreter ([`engine`] + its
11//! [`trace`] output) alongside the generated model, adapted to the generated
12//! types and pinned by the shared conformance corpus. The engine owns the
13//! [`engine::FlowEffects`] trait *definition*; the daemon keeps its live impl
14//! in its own codebase. Comment-preserving mutation stays TS-only.
15
16/// The generated document model (`Flow`, `Node`, `Prompt`, …), emitted
17/// from the schema by `typify` into `OUT_DIR/flow_types.rs`.
18///
19/// `Node` is an internally-tagged enum (`#[serde(tag = "kind")]`): the
20/// `build.rs` schema normalization inlines the per-node `oneOf` branches
21/// and rewrites the `kind` `const` to a single-valued `enum` so typify
22/// discriminates on `kind` instead of emitting an `#[serde(untagged)]` enum
23/// that would mis-deserialize (a menu as a greeting).
24pub mod model {
25    #![allow(clippy::all)]
26    include!(concat!(env!("OUT_DIR"), "/flow_types.rs"));
27}
28
29/// Hand-written helpers layered on the generated model (logic, not shape).
30mod model_ext;
31
32pub mod book;
33pub mod engine;
34pub mod hours;
35pub mod trace;
36pub mod validate;
37
38pub use model::*;
39pub use model_ext::{required_assets, NodeId};
40
41/// The normative JSON Schema (draft 2020-12) for format version 1, as a
42/// string, bundled so consumers can run structural validation without
43/// reaching outside the crate. The crate-local copies are synced from the
44/// repo-root schemas by `build.rs` (and are what ship in the published
45/// package).
46pub const FLOW_V1_SCHEMA: &str = include_str!("../schema/flow.v1.schema.json");
47
48/// Format version 2 — version 1 plus the `book` component. This is also
49/// the file the model types are generated from, being the newest.
50pub const FLOW_V2_SCHEMA: &str = include_str!("../schema/flow.v2.schema.json");
51
52/// The schema for a declared version, or `None` if this build has none.
53pub fn flow_schema(version: u32) -> Option<&'static str> {
54    match version {
55        1 => Some(FLOW_V1_SCHEMA),
56        2 => Some(FLOW_V2_SCHEMA),
57        _ => None,
58    }
59}
60
61/// Schema versions this crate's model describes. Twin:
62/// `packages/flow-schema/src/model.ts` `SUPPORTED_SCHEMA_VERSIONS`.
63///
64/// This is what a daemon advertises and the platform refuses to serve
65/// past: a device that only knows version 1 must never be handed a
66/// document that uses a component it has no code for.
67pub const SUPPORTED_SCHEMA_VERSIONS: &[u32] = &[1, 2];
68
69/// The newest version this build authors. Reading stays broad
70/// ([`SUPPORTED_SCHEMA_VERSIONS`]); writing is deliberately one number.
71/// Twin: `model.ts` `CURRENT_SCHEMA_VERSION`.
72pub const CURRENT_SCHEMA_VERSION: u32 = 2;