Skip to content

Standard Library

Masterplanner25 edited this page Sep 9, 2026 · 3 revisions

Standard Library

Stdlib modules are imported using the std: prefix:

import "std:strings"
import { repeat, join } from "std:strings"
import "std:math" as math

Built-in functions are always available — no import needed.


Built-in Functions

Function Description
print(x) Print value to stdout. Accepts exactly one argument — use string interpolation or str() to combine values.
str(x) Convert any value to its string representation
type(x) Return type name: "nil", "bool", "float", "int", "string", "list", "map", "record", "function", "error". A bare numeric literal is "float", not "number"
len(x) Length of list or string. Returns an int — it returned a float in v3, changed in v4.0
has_key(map, key) true if key is present in map (O(1))
keys(map) List of all keys in a map
values(map) List of all values in a map
list_push(list, v) Append v to list in place; returns the same list. xs = list_push(xs, v) reads functional and is not — use the bare form
copy(value) Deep copy of a list, map or record (5.13.0). Preserves shared structure rather than expanding it, terminates on a cycle, and refuses a value holding a function, channel, coroutine or task
list_pop(list) Remove and return the last element
input(prompt) Read a line from stdin (blocked by sandbox by default)
clock() Current time in milliseconds since epoch
read_file(path) Read file contents as string
write_file(path, content) Write string to file
append_file(path, content) Append string to file
exists(path) true if path exists
mkdir(path) Create directory
list_dir(path) List filenames in directory

type() returns "number" for float values (42, 3.14) and "int" for integer literals (42i). type() returns "error" for err records returned by stdlib functions.

std:runtime.typeof(value) returns even more granular types: "int" vs "float".

Containers alias — assignment binds, it does not copy. let b = a gives a second name for one list, map or record: mutating through either is visible through both, at any depth and across a call boundary. copy(value) is how you hand a container somewhere without it being changed underneath you. A workflow state cell is the exception — it owns its value, so writing a container into a cell stores a copy and reading one hands a copy back.


std:strings

import "std:strings" as strings
Function Description
upper(s) Convert to uppercase
lower(s) Convert to lowercase
trim(s) Strip leading/trailing whitespace
split(s, delim) Split string into list
join(list, delim) Join list into string
contains(s, sub) Check if substring present
replace(s, old, new) Replace all occurrences of old with new
repeat(s, n) Repeat string n times
is_blank(s) True if empty or only whitespace
import "std:strings" as s
print(s.upper("hello"))           // "HELLO"
print(s.split("a,b,c", ","))      // ["a", "b", "c"]
print(s.join(["a", "b"], "-"))    // "a-b"
print(s.repeat("ha", 3))         // "hahaha"

std:collections

import "std:collections" as col
Function Description
map(list, fn) Apply function to each element, return new list
filter(list, fn) Keep elements where fn returns truthy
reduce(list, fn, initial) Accumulate with binary function
push(list, value) Append to list in-place; returns the list
pop(list) Remove and return last element
first(list) First element
last(list) Last element
list_sum(list) Sum of all numbers
import "std:collections" as col
let nums = [1, 2, 3, 4, 5]
print(col.map(nums, fn(x) { return x * 2 }))     // [2, 4, 6, 8, 10]
print(col.filter(nums, fn(x) { return x > 2 }))  // [3, 4, 5]
print(col.reduce(nums, fn(a, x) { return a + x }, 0))  // 15

std:json

import "std:json" as json
Function Description
parse(s) Decode JSON string — JSON objects become maps, arrays become lists
stringify(value) Encode Nodus value to JSON string
parse_int(s) Parse a decimal string as an integer

Important: json.parse returns a map (not a record) for JSON objects. Use bracket notation to access fields:

import "std:json" as json
let data = json.parse('{"name": "Alice", "age": 30}')
print(data["name"])    // "Alice"  ← bracket notation required
print(data["age"])     // 30

std:math

import "std:math" as math
Function Description
abs(x) Absolute value
min(a, b) Minimum of two values
max(a, b) Maximum of two values
floor(x) Floor (round down). Returns an int
ceil(x) Ceiling (round up). Returns an int
sqrt(x) Square root
pow(base, exp) Exponentiation
random() Random float in [0, 1)
is_int(x) True if value is an integer
is_float(x) True if value is a float
is_numeric(x) True if value is int or float
import "std:math" as math
print(math.abs(-5))     // 5
print(math.sqrt(16))    // 4.0
print(math.max(3, 7))   // 7

std:fs

import "std:fs" as fs
Function Description
read(path) Read file contents as string
write(path, content) Write string to file
append(path, content) Append string to file
exists(path) Returns true if path exists
listdir(path) Returns list of filenames in directory
ensure_dir(path) Create the directory if it does not exist, idempotently; returns the path. An existing directory succeeds and missing parents are created. A file at the target is io_error. Before 5.13.0 it reported success for every failure
import "std:fs" as fs
if (fs.exists("data.json")) {
    let content = fs.read("data.json")
    print(content)
}

std:path

Path manipulation helpers. These are global builtins, not module functions.

Built-in Description
path_join(a, b) Join two path segments
path_dirname(p) Directory part of path
path_basename(p) Filename part of path
path_ext(p) File extension
path_stem(p) Filename without extension

std:memory

import "std:memory" as mem

Shared runtime key-value store. Without a session it is process-local; in server sessions it is session-local.

Function Description
get(key) Read value or nil
put(key, value) Store JSON-safe value; returns it
delete(key) Remove key; returns true if existed
keys() List all keys
has(key) true if get(key) != nil
share(ns, key, val) Store in namespace ns (key prefixed {ns}::)
recall_from(ns, key) Read from namespace ns
recall_all(ns) All keys and values in namespace ns
import "std:memory" as mem
mem.put("count", 0)
mem.put("count", mem.get("count") + 1)
mem.share("session", "user_id", "alice")
print(mem.recall_from("session", "user_id"))    // "alice"

std:runtime

import "std:runtime" as rt
Function Description
fn_name(fn) Function name string
fn_arity(fn) Parameter count
fn_module(fn) Defining module path
fields(record) List of record field names
has(record_or_module, name) Field/export existence check
module_fields(module) List of exported names
stack_depth() Current call stack depth
stack_frame(index) Frame record with name, module, path, line, column
typeof(value) Granular type: "int", "float", "string", etc.
tasks() List of tracked coroutine tasks
scheduler() Scheduler counters and queue sizes
time_ms() Runtime clock in milliseconds
import "std:runtime" as rt
fn add(a, b) { return a + b }
print(rt.fn_name(add))      // "add"
print(rt.fn_arity(add))     // 2
print(rt.typeof(42))        // "float"
print(rt.typeof(42i))       // "int"

std:async

import "std:async" as async

Coroutine and channel helpers. See Coroutines and Channels for detailed usage.

Function Description
sleep(ms) Suspend current coroutine for ms ms
parallel(tasks) Spawn all and run event loop
series(tasks) Run tasks sequentially
queue() New channel
worker_pool(worker, count) Channel serviced by N workers
pipeline(stages) {input, output} channel pipeline

std:tool

import "std:tool" as tool

MCP-compatible tool registry. Tool names must use dotted namespacing (e.g. "myapp.search"). A plain name like "search" returns a registration error.

Function Description
register(opts) Register a tool. opts map: name (required, dotted), handler (required), description, schema, effects, returns_schema, version, tags
invoke(name, args) Call a registered tool by name
lookup(name) Return tool metadata map or err
list_tools(filter?) List registered tools (optional filter string)
has(name) true if tool is registered
unregister(name) Remove a registered tool
import "std:tool" as tool

tool.register({
    "name": "myapp.greet",
    "handler": fn(args) { return "hello " + args["name"] },
    "description": "Greet a user"
})

let result = tool.invoke("myapp.greet", {"name": "Alice"})
print(result)    // "hello Alice"

std:http

import "std:http" as http

HTTP client. Requires httpx (included in nodus-lang dependencies).

Function Description
get(url, opts?) HTTP GET
post(url, opts?) HTTP POST
put(url, opts?) HTTP PUT
delete(url, opts?) HTTP DELETE
patch(url, opts?) HTTP PATCH
request(method, url, opts?) Generic HTTP request

Response records have fields: status, body, headers, url, method, ok, is_redirect, is_client_error, is_server_error, plus method fields json(), header(name).

Options: json, text, bytes (body), headers, query, auth_bearer, auth_basic, timeout_ms, follow_redirects, verify_tls.

import "std:http" as http
let r = http.get("https://api.example.com/data")
if (r.ok) {
    let data = r.json()
    print(data["result"])
}

Errors return an err record with kind: "http_error" and a category field: network, timeout, client_error, server_error, decode_error, or redirect_error.


std:subprocess

import "std:subprocess" as proc
Function Description
run(argv, opts?) Run process synchronously; returns result record
shell(command, opts?) Run shell command synchronously
spawn(argv, opts?) Spawn process; returns handle with channels
shell_quote(string) Platform-safe shell quoting

Result record fields: stdout, stderr, exit_code, duration_ms, command. Err records use kind: "subprocess_error".

import "std:subprocess" as proc
let r = proc.run(["ls", "-la"])
print(r.stdout)

std:time

import "std:time" as time

Datetime and duration library.

Function Description
now() Current datetime in local timezone
now_in(zone) Current datetime in named timezone
at(year, month, day, ...) Construct datetime
from_epoch_ms(ms) Datetime from epoch milliseconds
from_iso8601(s) Parse ISO 8601 string
to_epoch_ms(dt) Convert datetime to epoch milliseconds
to_iso8601(dt) Format datetime as ISO 8601
duration_between(a, b) Duration between two datetimes

std:hash

import "std:hash" as hash

Cryptographic hashing. Hash functions return a hash record — call .to_hex() to get a hex string.

Function Description
sha256(data) SHA-256 hash record
sha512(data) SHA-512 hash record
md5(data) MD5 hash record
hmac_sha256(key, data) HMAC-SHA256 hash record
compare(a, b) Constant-time comparison of two hash values
import "std:hash" as hash
let h = hash.sha256("hello world")
print(h.to_hex())        // "b94d27b9..."
print(h.to_base64())     // base64 encoding

std:encoding

import "std:encoding" as enc
Function Description
base64_encode(s) Base64-encode a string
base64_decode(s) Decode a base64 string
hex_encode(s) Hex-encode a string (lowercase)
hex_decode(s) Decode a hex string
url_encode(s) URL percent-encode

std:secrets

import "std:secrets" as secrets
Function Description
random_bytes(n) n cryptographically random bytes
token_hex(n) n-byte token as hex string
token_base64(n) n-byte token as base64
uuid_v4() Random UUID v4 string
uuid_v7() Time-ordered UUID v7 string

std:test

import "std:test" as test

Full test framework. Run tests with nodus test [path].

Function Description
test.suite(name, fn) Declare a test suite
test.case(name, fn) Declare a test case
test.assert(val) Assert truthy
test.assert_eq(a, b) Assert equality
test.assert_err(val) Assert value is an err record
test.assert_ok(val) Assert value is not an err record
test.assert_throws(fn) Assert function throws
test.skip(name, fn) Skip a test case
test.advance_clock(ms) Advance virtual clock (async tests)
test.flush_async() Flush pending async tasks

std:bool

import "std:bool" as bool
Function Description
equal(x, bool_value) Strict boolean equality (x must match the exact boolean value)

Use bool.equal(x, true) when you need strict boolean checking instead of truthiness.


AI-Native Modules (v4.0)

std:identity

import "std:identity" as identity

Execution identity and trace propagation.

Function Description
trace_id() Current trace ID (nil if not set)
session_id() Current session ID
execution_unit_id() Unique ID for this VM instance

Set the trace ID from the host: NodusRuntime.set_trace_id(id).


std:effects

import "std:effects" as effects

Exactly-once effect tracking.

Function Description
effect_action_id(type, payload, scope) Compute deterministic action ID
effect_pending(id, hash) Mark effect as pending
effect_resolve(id) Check if effect was already completed
effect_complete(id, status, result) Mark effect as complete
effect_store_size() Number of tracked effects

std:sys

import "std:sys" as sys

Versioned syscall dispatch. Provides a uniform {status, data, error, trace_id} envelope.

Function Description
call(name, payload) Dispatch a registered syscall by name
list() List all registered syscall names

Built-in syscalls: sys.v1.memory.get, sys.v1.memory.put, sys.v1.memory.delete, sys.v1.memory.recall_from.


std:retry

import "std:retry" as retry

Requires nodus-retry (included as a required dependency since v4.0).

Function Description
call(fn, policy) Call fn with retry policy. Policy map: max_attempts, delay_ms, backoff, retry_on

std:circuit_breaker

import "std:circuit_breaker" as cb

Requires nodus-circuit-breaker (optional; returns {kind: "dependency_error"} map when not installed).

Function Description
create(name, opts?) Create a circuit breaker
call(name, fn) Call fn through the named circuit breaker
state(name) Return current state: "closed", "open", "half_open"
reset(name) Force circuit breaker to closed state

std:agent

import "std:agent" as agent

AI agent dispatch wrapper. Register agent handlers via the embedding API.

Function Description
call(name, payload) Call a registered agent handler
available() List registered agent names
describe(name) Agent metadata or nil

Import Shorthand

All stdlib modules support both full and destructured imports:

// full namespace
import "std:strings" as s
s.upper("hello")

// selective
import { upper, lower } from "std:strings"
upper("hello")

Clone this wiki locally