BoundaryML/baml · error · AccessError

Field not found: expected

Error message

Field not found: expected {expected}

What it means

AccessError::FieldNotFound is returned when accessing a named field on a heap object that does not have it. `expected` carries the field name; the object itself was valid and of the right kind, but lacks the requested member, e.g. after a script object shape change.

Solutions

  1. Check field existence (has_field / fields list) before access and return Option instead of Err
  2. Update the field name to match the current object layout/schema
  3. Fix object construction to always populate the required field
  4. Treat the error as recoverable and provide a default value at the call site

Example fix

// before
let v = heap.get_field(obj, "email")?; // field removed in new schema
// after
let v = match heap.get_field(obj, "email") {
    Ok(v) => v,
    Err(AccessError::FieldNotFound { .. }) => Value::nil(),
    Err(e) => return Err(e),
};
Defensive patterns

Strategy: try-catch

Validate before calling

if !heap.has_field(obj, "email") {
    return Ok(Value::nil()); // default instead of erroring
}

Try / catch

match heap.get_field(obj, "email") {
    Ok(v) => v,
    Err(AccessError::FieldNotFound { expected }) => { log::debug!("field {expected} absent"); Value::nil() },
    Err(e) => return Err(e),
}

Prevention

When it happens

Trigger: get_field(obj, "name") on a heap record/instance that defines no `name` field — typical after script/schema version changes or when indexing the wrong object kind.

Common situations: Refactored VM object layouts where a field was renamed or removed; dynamically-created objects missing optional fields; hardcoded field-name strings drifting from actual object shapes.

Related errors


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

Appendix: source

Thrown at baml_language/crates/bex_heap/src/accessor.rs:24

use baml_type::RuntimeTy;
use bex_external_types::{BexExternalAdt, BexExternalValue, WeakHeapRef};
use bex_vm_types::{HeapPtr, Object, PermitProof, Value};

use crate::BexHeap;

#[derive(Debug, PartialEq, thiserror::Error, Clone)]
pub enum AccessError {
    #[error("Invalid handle: expected {expected}")]
    InvalidHandle { expected: &'static str },

    #[error("Type mismatch: expected {expected}, got {actual}")]
    TypeMismatch {
        expected: &'static str,
        actual: String,
    },

    #[error("Field not found: expected {expected}")]
    FieldNotFound { expected: String },

    #[error("Function not found: {expected}")]
    FunctionNotFound { expected: String },

    #[error("Cannot convert to owned: {reason}")]
    CannotConvertToOwned { reason: String },
}

pub enum BexValue<'a> {
    ExternalValue(&'a BexExternalValue),
    HeapPtr(&'a HeapPtr),
    Value(&'a Value),
    OwnedValue(Value),
}

impl<'a> From<&'a BexExternalValue> for BexValue<'a> {
    fn from(value: &'a BexExternalValue) -> Self {

View on GitHub (pinned to bd85ce9dee)