12. Errors and testing
Capy reports type and syntax errors before a unit runs. Runtime failures include the original Capy source location.
Handle expected missing data
Use a fallback when absence is valid:
function display_name(profile : dval) string {
-> string(profile.name, {fallback: "guest"})
}
function RENDER(request : dval) {
print(display_name({}), "\n")
}
Output
guest
The fallback handles both none and failed string conversion. It does not hide a compiler error or an unrelated runtime trap.
Compiler errors
The compiler rejects invalid syntax, unknown names, and incompatible types. For example, this assignment is invalid:
function RENDER(request : dval) {
var count := 1
count = "one"
}count has type s64. Assignment cannot change its type to string.
Read the first diagnostic and its source location. Later messages can be consequences of the first error.
Runtime traps
Use strict access when missing data violates the program contract:
function RENDER(request : dval) {
var profile := {}
if !has(profile, "name") { trap() }
var name := get(profile, "name")
print(name)
}
This traps if name is missing or the access path is unusable. Other traps include division by zero, invalid typed-array indexes, failed host operations, and an explicit trap().
Do not use a fallback for data that the program requires. A clear trap at the boundary is safer than incorrect work with a fabricated value.
Test through Bearer
Run one page through the local CLI socket:
scripts/bearer-cli /path/to/page.capyThe CLI helper exposes the response body and runtime errors. Use an HTTP client or a repository HTTP test helper when a test must verify status and headers. Include failure cases for missing input, invalid conversions, and boundary errors.
The repository test suites exercise the compiler, Wasm runtime, source maps, components, units, tasks, and documentation examples:
scripts/test_capy_native.sh
scripts/test_capy_phase1.sh
scripts/test_capy_reference.shRun the focused test while editing. Run the broader gate before deployment.
Keep code direct
Prefer a small typed helper over repeated dynamic conversion. Keep request parsing near the request boundary. Convert a dval to a static type once the required shape is known.
Use one name for one thing. Remove wrappers that only rename another function. Keep comments for behavior that the code cannot make clear.
Find API details
The language guide explains how Capy code fits together. The API reference gives exact standard-library signatures and failure behavior. Use the generated Capy signature on each API page.
Read failures as contracts
A compile error usually means the source does not match the type contract. Fix that error before you inspect later messages.
A runtime trap usually means the input did not match the application contract. Test required data with has() before you call get(). Use constructors with fallbacks when absence is valid.
Write tests for both paths. A success test proves the expected shape works. A failure test proves bad input cannot silently continue.