BoundaryML/baml · error

`{BAML_JSON_JSON}` is declared by the stdlib

Error message

`{BAML_JSON_JSON}` is declared by the stdlib

What it means

Panic in `json_alias_ty` when the stdlib type alias `BAML_JSON_JSON` (the `json.JSON` alias) is missing from the VM's declaration table. The function resolves the declaration head for the alias to build a `RealizedTy::TypeAlias`, and assumes the stdlib always declares it. If the lookup fails, the VM environment is incomplete or corrupted.

Source

Thrown at baml_language/crates/bex_vm/src/package_baml/json.rs:40

/// FQN of the recursive `json` type alias declared in `baml.json`.
/// Mirrors `baml_base::qualified_name::BAML_JSON_JSON`; inlined here to
/// avoid dragging the whole `baml_base` crate into `bex_vm` deps.
const BAML_JSON_JSON: &str = "baml.json.json";

/// The runtime type of an untyped `json` value: the recursive `baml.json.json`
/// alias (`null | bool | int | float | string | json[] | map<string, json>`).
/// Recursive aliases stay opaque in `RealizedTy`, so this is the most precise
/// element/value type available for containers parsed from untyped JSON.
/// The `baml.json.json` alias type, headed at its declaration.
///
/// A stdlib FQN constant resolving to a head — one of the three sanctioned
/// name-to-head boundaries. The alias is compiled, so the tag is
/// content-addressed and the pointer comes off the declaration itself.
pub(super) fn json_alias_ty(vm: &BexVm) -> RealizedTy {
    let qtn = TypeName::from_dotted_path(BAML_JSON_JSON);
    let head = vm
        .declaration_head(&qtn)
        .unwrap_or_else(|| unreachable!("`{BAML_JSON_JSON}` is declared by the stdlib"));
    RealizedTy::TypeAlias(head, baml_type::TyAttr::default())
}

/// Run `f` with `seg` appended to `path`, then restore `path` to its prior
/// length. Used to track the JSON pointer during recursive (de)serialization
/// without mutating the buffer's owner contract.
fn with_path_segment<F, R>(path: &mut String, seg: std::fmt::Arguments<'_>, f: F) -> R
where
    F: FnOnce(&mut String) -> R,
{
    use std::fmt::Write;
    let saved_len = path.len();
    let _ = write!(path, "{seg}");
    let r = f(path);
    path.truncate(saved_len);
    r
}

View on GitHub (pinned to bd85ce9dee)

Solutions

  1. Ensure BexVm is initialized with the complete stdlib (baml_builtins2) including the json package.
  2. Check feature flags / build configuration so the JSON stdlib declarations are not compiled out.
  3. Align VM and stdlib versions — rebuild with matching baml_language crates.
  4. Inspect the declaration table (vm.declaration_head for the dotted path) at startup and fail fast if the alias is absent.

Example fix

// before
let vm = BexVm::new_minimal();
// after
let vm = BexVm::new_with_stdlib(); // registers baml_builtins2 incl. json.JSON
Defensive patterns

Strategy: validation

Validate before calling

fn stdlib_json_ready(vm: &BexVm) -> bool {
    vm.declaration_head(&TypeName::from_dotted_path(BAML_JSON_JSON)).is_some()
}

Try / catch

// Fail fast at VM startup instead of panicking during serialization:
assert!(stdlib_json_ready(&vm), "stdlib json.JSON alias missing");

Prevention

When it happens

Trigger: Running the VM without the stdlib (`baml_builtins2`) loaded, with a stripped/partial stdlib build, or with a declaration table that dropped the JSON alias; triggered through `serde_to_value` whenever a JSON value must be realized as the stdlib alias type.

Common situations: Custom VM embeddings that initialize BexVm without registering the full stdlib, builds with feature flags that exclude the JSON package, or version mismatches between the VM and the bundled baml_builtins2 artifacts.

Understand the failure class

Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.

Related errors


AI-assisted analysis of BoundaryML/baml@bd85ce9dee (2026-09-12). Data as JSON: /api/errors/cd79ea66e642738e. Report an issue: GitHub.