Files
vercel-labs--zerolang/skill-data/language.md
T
wehub-resource-sync e7738de6d2
CI / Deep Native Runtime Cases (1/6) (push) Has been skipped
CI / Native Preflight (push) Failing after 1s
CI / Native Runtime Cases (1/2) (push) Failing after 0s
CI / Native Runtime Cases (2/2) (push) Failing after 1s
CI / Native Metadata Reports (push) Failing after 0s
CI / Native Direct Backend Artifacts (push) Failing after 0s
CI / Native Sanitizer Smoke (push) Failing after 1s
CI / Command Contract Snapshots (push) Failing after 1s
CI / Deep Conformance Suite (push) Has been skipped
CI / Graph Build Perf (push) Failing after 1s
CI / Deep Native Preflight (push) Has been skipped
CI / Deep Native Runtime Cases (2/6) (push) Has been skipped
CI / Deep Native Runtime Cases (3/6) (push) Has been skipped
CI / Conformance Suite (push) Failing after 1s
CI / Workspace Checks (push) Failing after 0s
CI / Deep Native Runtime Cases (5/6) (push) Has been skipped
CI / Deep Native Runtime Cases (6/6) (push) Has been skipped
CI / Deep Native Runtime Cases (4/6) (push) Has been skipped
CI / Deep Graph Build Perf (push) Has been skipped
chore: import upstream snapshot with attribution
2026-07-13 12:29:30 +08:00

216 lines
6.4 KiB
Markdown

---
name: language
description: Compact zerolang syntax and semantics guide for agents.
---
# zerolang Language
Use this when reading or writing Zero source. `.0` files are the human-readable projection syntax, not the package compiler input: package commands compile from `zero.graph` and refresh it automatically after `.0` edits. Read one function with `zero view --fn <name>` instead of whole files.
## Minimal Program
```zero
pub fn main(world: World) -> Void raises {
check world.out.write("hello from zerolang\n")
}
```
`pub fn` exports a function. `World` carries runtime capabilities. `raises` marks a fallible function. `check` calls a fallible operation and propagates failure.
## Declarations
- `use std.mem` or `use helpers`
- `const answer: i32 = 42` (top-level consts work in functions and tests)
- `type Point { x: i32, y: i32, }`
- `enum Mode { fast, small, }`
- `choice Result { ok: i32, err: String, }`
- `fn answer() -> i32 { return 42 }`
- `pub fn main(world: World) -> Void raises { ... }`
- `test "name" { expect true }`
## Values, Mutation, And Control Flow
Use `let` by default and `var` only when a binding changes. Conditions are `Bool`; do not rely on truthy integers or strings. Operators are normal infix expressions: `a + b`, `a % b`, `a == b`, `a < b`, `a && b`. Comments start with `//`.
```zero
fn sum_odds(n: i32) -> i32 {
var i: i32 = 0
var total: i32 = 0
while i < n {
i = i + 1
if i % 2 == 0 {
continue
}
if total > 100 {
break
}
total = total + i
}
return total
}
```
`break` exits the nearest loop and `continue` skips to its next iteration.
## Types
Primitive and scalar types:
```text
Bool Void String char Type
i8 i16 i32 i64 isize
u8 u16 u32 u64 usize
f32 f64
```
Bare integer literals adopt the other operand's integer type when in range, so `i * 12` works for `i: usize`. Use suffixes such as `_u8` or `_usize` only when no operand gives context, and `as` for intentional casts.
Core capability, resource, and helper types recognized by the compiler:
```text
World WorldStream
Fs File ByteBuf
NullAlloc FixedBufAlloc PageAlloc GeneralAlloc
Vec Duration RandSource ProcStatus ProcChild
Address Net Conn Listener
HttpMethod HttpClient HttpServer HttpResult HttpError HttpHeaderValue
JsonDoc BufferedReader BufferedWriter FixedReader FixedWriter
Env Args Clock Rand Proc Alloc
Maybe<T> Span<T> MutSpan<T>
ref<T> mutref<T> owned<T>
```
## Shapes, Enums, And Choices
```zero
let point: Point = Point { x: 1, y: 2 }
let result: Result = Result.ok(42)
```
Matches must be exhaustive unless they use the fallback arm `_`:
```zero
match result {
.ok(value) {
expect value == 42
}
.err(message) {
expect true
}
}
```
## Errors
```zero
fn value(i: i32) -> i32 raises [Odd] {
if i % 2 == 0 {
return i
}
raise Odd
}
pub fn main(world: World) -> Void raises {
let item: i32 = rescue value(3) err 1
if item == 1 {
check world.out.write("fallible ok\n")
}
}
```
`raises [Error]` restricts the error set. Plain `raises` is open. Calling a fallible function requires `check` or `rescue`.
## Borrowing And Memory Views
- `ref<T>` is a read-only borrow, passed with `&value`.
- `mutref<T>` is a mutable borrow, passed with `&mut value`. Shape parameters such as `mutref<Point>` work, including field mutation and nested calls.
- `[N]T` is a fixed array; `Span<T>` is a read-only view; `MutSpan<T>` is a writable view.
- Returning a span backed by local fixed-array storage is rejected; return an owned value or keep the view local.
- `Maybe<T>` represents absence; read `.value` only inside a visible `.has` guard, or use `check` / `rescue`. `var name: Maybe<String> = null` declares an absent local to assign or return later.
- `owned<T>` marks explicit resource ownership.
- One function's fixed locals are limited to 128 KiB (MEM003). Split large buffers into smaller buffers in helper functions, or process data in fixed-size chunks.
```zero
fn bump(point: mutref<Point>) -> Void {
point.x = point.x + 1
}
pub fn main() -> Void {
var storage: [4]u8 = [1, 2, 3, 4]
let view: MutSpan<u8> = storage
let first: u8 = storage[0]
storage[0] = 9
}
```
Array and span indexing is bounds-checked at runtime; an out-of-range index traps with a signal exit and no output, so exercise boundary inputs before declaring a change done.
## Generics
```zero
type Box<T: Type> {
value: T,
}
fn id<T: Type>(value: T) -> T {
return value
}
type FixedVec<T: Type, static N: usize> {
len: usize,
items: [N]T,
}
```
## Standard Library Call Shapes
Load `zero skills get stdlib` for the full signature catalog. Beyond the `std.mem`/`std.parse`/`std.rand`/`std.json` helpers shown below, it ships ready-made validators: `std.time` (RFC 3339 date/time incl. the exact leap-second rule), `std.inet` (IPv4/IPv6/hostname), `std.regex` (ECMA subset), and `std.unicode` (strict UTF-8). Check the catalog before hand-writing parsing or validation logic. Target-neutral helpers follow these shapes:
```zero
pub fn main() -> Void {
let bytes: Span<u8> = std.mem.span("zero")
let n: usize = std.mem.len(bytes)
let same: Bool = std.mem.eql("zero", "zero")
let parsed: Maybe<u16> = std.parse.parseU16("8080")
if parsed.has {
expect parsed.value == 8080
}
var rng: RandSource = std.rand.seed(7_u32)
let random: u32 = std.rand.nextU32(&mut rng)
let count: Maybe<u32> = std.json.u32("{\"count\":42}", "count")
expect same && random == 1025555898_u32 && count.has
}
```
Hosted helpers are capability-gated by target. There is no stdin; hosted programs take input from `std.args` and files through `std.fs`:
```zero
pub fn main(world: World) -> Void raises {
let first: Maybe<String> = std.args.get(1)
if first.has {
check world.out.write(first.value)
}
var path_storage: [16]u8 = [0; 16]
let path: String = check std.path.join(path_storage, ".zero", "x")
let fs: Fs = std.fs.host()
var file: owned<File> = check std.fs.createOrRaise(fs, path)
check std.fs.writeAllOrRaise(&mut file, std.mem.span("hello\n"))
}
```
If unsure, run `zero check` instead of inventing syntax, and pair behavior changes with a `test` block:
```zero
fn point_sum(point: Point) -> i32 {
return point.x + point.y
}
test "shape" {
let point: Point = Point { x: 40, y: 2 }
expect point_sum(point) == 42
}
```