nautechsystems/nautilus_trader · error

invalid `TriggerTypeOptional` enum string value, was '{value

Error message

invalid `TriggerTypeOptional` enum string value, was '{value}'

What it means

`trigger_type_from_cstr` parses a C string into `TriggerTypeOptional` (the optional-wrapped trigger type: DEFAULT, LAST, BID, ASK, etc.). Invalid strings panic inside `abort_on_panic` and abort the process, since the FFI layer treats unparseable enum values as unrecoverable programming errors. Only exact `TriggerTypeOptional::as_ref()` serializations are valid.

Source

Thrown at crates/model/src/ffi/enums.rs:931

pub extern "C" fn trigger_type_to_cstr(value: TriggerTypeOptional) -> *const c_char {
    str_to_cstr(value.as_ref())
}

/// Returns an enum from a C string.
///
/// # Safety
///
/// Assumes `ptr` is a valid C string pointer.
///
/// # Panics
///
/// Panics if the C string does not correspond to a valid `TriggerTypeOptional` variant.
#[unsafe(no_mangle)]
pub unsafe extern "C" fn trigger_type_from_cstr(ptr: *const c_char) -> TriggerTypeOptional {
    abort_on_panic(|| {
        let value = unsafe { cstr_as_str(ptr) };
        TriggerTypeOptional::from_str(value).unwrap_or_else(|_| {
            panic!("invalid `TriggerTypeOptional` enum string value, was '{value}'")
        })
    })
}

#[cfg(test)]
mod tests {
    use rstest::rstest;

    use super::*;
    use crate::enums::OrderSide;

    #[rstest]
    fn test_name() {
        assert_eq!(OrderSideOptional::NoOrderSide.as_ref(), "NO_ORDER_SIDE");
        assert_eq!(OrderSide::Buy.as_ref(), "BUY");
        assert_eq!(OrderSide::Sell.as_ref(), "SELL");
    }

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Correct the input string to an exact `TriggerTypeOptional` variant name.
  2. Use NOT_SET for absent values instead of empty strings or NULL.
  3. Generate valid strings via `trigger_type_to_cstr` round-tripping.
  4. Update adapter mappings so exchange trigger codes translate to canonical nautilus trigger names.

Example fix

// before
trigger_type_from_cstr(str_to_cstr("last_price"));
// after
trigger_type_from_cstr(str_to_cstr("LAST"));
Defensive patterns

Strategy: validation

Validate before calling

fn is_valid_trigger_type_optional(s: &str) -> bool {
    TriggerTypeOptional::from_str(s).is_ok()
}

Type guard

fn as_trigger_type(s: &str) -> Option<TriggerTypeOptional> {
    TriggerTypeOptional::from_str(s).ok()
}

Prevention

When it happens

Trigger: Calling the exported `trigger_type_from_cstr` with strings like "last_price", "MIDPOINT" (not a trigger variant), or an empty string instead of the NOT_SET sentinel.

Common situations: Exchange trigger-price conventions mapped 1:1 without translation; configs storing lowercase trigger names; confusion between TriggerType and TriggerTypeOptional serializations.

Understand the failure class

Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.

Related errors


AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08). Data as JSON: /api/errors/226807f72a4d99cb. Report an issue: GitHub.