Open Manual

<!-- nytrix-doc: {"audience":"user","featured":false,"group":"spec","order":180,"summary":"Recoverable results, compiler diagnostics, failure categories, and error propagation."} -->

Errors

Errors use assertions, panics, recoverable result values, and compiler

diagnostics.

Assertions

use std.core

def condition = true
def actual = [1, 2]
def expected = [1, 2]

assert(condition, "behavior")
assert_eq(actual, expected, "behavior")

Assertions fail the current execution with the supplied message. Assertion

messages name the behavior being checked.

Panic

use std.core

try {
   panic("message")
} catch err {
   assert_eq(repr(err), "\"message\"", "panic message")
}

panic aborts the current execution path. It is for unrecoverable states.

The abort is catchable by try/catch on the language/runtime path.

Choosing the failure form

ConditionForm
Programmer error, impossible state, or invalid index/receiverpanic or assert
Recoverable operation whose caller can handle failureStructured Result value
Language-level invalid sourceCompiler diagnostic
Boundary worth a machine-readable codeStructured error with error_kind

A panic aborts the current execution path and is catchable by try/catch.

A Result value flows through ordinary data. Prefer the recoverable form when

the caller has a real fallback, and panic when continuing would be wrong.

Structured errors

use std.core
use std.core.error

def e = exception(ERR_DIV_ZERO, "division by zero")
def w = warning(WARN_RUNTIME, "slow fallback")

assert_eq(error_kind(e), ERR_DIV_ZERO, "error kind")
assert_eq(error_message(e), "division by zero", "error message")
assert(is_error(e, ERR_DIV_ZERO), "error match")
assert_eq(error_kind(w), WARN_RUNTIME, "warning kind")

Structured errors and warnings are ordinary values with a kind and message.

Runtime panics produced by checked operations, such as division by zero or

invalid receiver/index access, can be captured by try/catch.

Error conventions

Use structured errors for recoverable library operations and diagnostics for

language failures. Keep messages compact and practical.

Recommended recoverable shape:

{"ok": false, "code": "invalid_graph", "message": "cycle at node 7", "at": 7}

Recommended success shape when a tagged result is useful:

{"ok": true, "value": result}

Rules:

Recoverable results

Standard-library APIs can return Result values for recoverable failure.

Callers inspect the success/error shape before using the payload when

compile-time type checking requires refinement.

use std.core

def r = ok(42)
def e = err("missing")

assert(is_ok(r), "ok result")
assert(is_err(e), "err result")
assert_eq(unwrap(r), 42, "unwrap")
assert_eq(unwrap_or(e, 0), 0, "fallback")

Use ok(value) for success and err(value) for failure. is_ok, is_err,

unwrap, and unwrap_or provide the common checks. Match arms can destructure

ok(v) and err(e) when typed result refinement matters.

Diagnostics

Diagnostics identify source location, severity, and message. Compact

diagnostics collect a dense error set. Rich diagnostics print wider source

context.

ny --diag-compact --collect-errors file.ny
ny --diag-rich file.ny

Common compile-time failures

FailureMeaning
Undefined symbolMissing import, wrong export name, or out-of-scope binding.
Unavailable receiver methodReceiver form is not available for that value/API.
Type-check failureDynamic shape was not refined enough.
Ownership failureA move, borrow, release, return, or contract violates --borrow-check.
Compile-time proof failureassert_compile, range proof, or index proof could not be proven.
Safe-mode raw memory failureA raw pointer access lacks a proven in-bounds byte range.
Native boundary failurePointer, handle, layout, or ABI shape is wrong.
Parser failureSource spelling is not a valid syntax form.

Diagnostic quality

Diagnostics should always:

Related