Dynamic Typing
Variables hold any type at runtime. No annotations required — write expressive code without ceremony.
First-Class Functions
Functions are values. Pass them around, return them from other
functions, and capture variables in closures. Anonymous functions
support a concise => expression body:
fn(x) => x * 2.
Async / Await
Declare async functions and use await to
suspend execution. Includes Promise chaining with
.then() and .error().
BigInt Support
Arbitrary-precision integers using the n suffix —
100n + 2n. No overflow surprises with large numbers.
Object-Oriented
Class-based inheritance, constructors, static methods/properties,
and this binding.
Module System
Named and wildcard imports, core: built-ins,
lib: user libraries, and relative path imports.
Rich Data Structures
Dynamic arrays with methods (push, pop,
each, keep), and flexible key-value
objects with spread syntax.
Expressive Control Flow
if/for/while/do-while,
switch expressions,
try/catch, raise,
assert, and ternary forms.
Standard Library
Core modules for I/O, math, OS, paths, objects, arrays, dates, regex, promises, SQLite, Unicode, blobs, and HTTP.
HTTP Server
Express.js-style HTTP server via core:mongoose.
Register GET/POST/… routes, attach middleware, and serve JSON APIs —
all from ZayneScript.
Quick Start
Makefile — Linux / macOS (recommended):
# Debug build with AddressSanitizer (default)
make
# Super-optimised release build (clang + LTO)
make release
# Force architecture on native build
make 64
make 32
make 32i686
# Cross-compile Windows builds via MinGW
make win32 # auto arch
make win32-64
make win32-32
make win32-32i686
# Build then run immediately
make run
# Install to /usr/local/bin
make install
# Remove the binary
make clean
run.sh — Linux / macOS shell script (uses
gcc):
# Debug build + run
./run.sh
# Optimised release build + run
./run.sh --release
# Compile only (no run)
./run.sh --compile
# Format all source files with clang-format
./run.sh --format
# Debug a script with GDB
./run.sh --dbg tests/test_async.zs
Manual — any platform with GCC:
mkdir -p dist && gcc -O3 -DNDEBUG -Wno-pointer-sign \
main.c src/core/*.c src/*.c utf/*.c utf/utf8proc/*.c ./libbf/*.c \
-o dist/zscript.exe -lm -ldl -lpthread
hello.zs:
import { println } from "core:io";
println("Hello, ZayneScript!");
dist/):
./dist/zscript.exe --run hello.zs
A Taste of ZayneScript
The following snippet demonstrates variables, closures, classes, async/await, error handling, and the standard library:
import { println, format } from "core:io";
import { sqrt, pi } from "core:math";
// ----- Closures -----
fn makeCounter() {
local count = 0;
return fn() {
count += 1;
return count;
};
}
var tick = makeCounter();
println(tick(), tick(), tick()); // 1 2 3
// Expression-body function (implicit return)
const triple = fn(n) => n * 3;
println(triple(4)); // 12
// ----- Classes with inheritance -----
class Shape {
fn area() { return 0; }
}
class Circle (Shape) {
fn init(r) {
assert r > 0, "radius must be positive";
this.r = r;
}
fn area() { return pi * this.r * this.r; }
}
const c = new Circle(5);
println(format("Area: {}", c.area())); // Area: 78.539816...
// ----- Error handling: raise & try/catch -----
fn safeSqrt(x) {
if (x < 0) { raise "cannot take sqrt of negative number"; }
return sqrt(x);
}
try {
println(safeSqrt(9)); // 3
println(safeSqrt(-1)); // throws
} catch (e) {
println("Error:", e); // Error: cannot take sqrt of negative number
}
// ----- Async / Await -----
fn fetchData() async { return "payload"; }
fn main() async {
const data = await fetchData();
println("Got:", data); // Got: payload
}
main();
// ----- BigInt -----
println(2n ** 64n); // 18446744073709551616n
Building
The Makefile validates required programs before building and exits early with install hints if tools are missing.
Required tools
| Build type | Required programs |
|---|---|
| Native Linux / macOS builds |
clang, lld, cmake
|
| Windows cross-builds (MinGW) |
x86_64-w64-mingw32-gcc or
i686-w64-mingw32-gcc,
$(prefix)-windres, and CMake
($(prefix)-cmake if available, else plain
cmake), plus MinGW CMake toolchain files from
mingw-w64-cmake
|
Architecture selection
By default, BUILD_ARCH=auto detects the current host
machine. You can also force an architecture explicitly.
| Setting | Description | Typical command |
|---|---|---|
auto (default) |
Use host machine architecture | make |
64 |
64-bit x86_64 | make 64 |
32 |
32-bit x86_64 (x32 ABI on native builds) | make 32 |
32i686 |
32-bit i686 baseline | make 32i686 |
Makefile targets
| Target | Description |
|---|---|
make / make debug |
Debug build with AddressSanitizer & leak detection (clang -g3 -fsanitize=address,leak)
|
make release |
Super-optimised build (-O3 -march=native -flto=thin,
stripped binary)
|
make run |
Debug build then launch the interpreter |
make clean |
Remove dist/, win32/, and temporary
build directories
|
make install |
Install binary to /usr/local/bin/zscript and libs to
/usr/local/lib/zscript/
|
make uninstall |
Remove installed binary and library directory |
make amalgamate |
Bundle everything into a single source file via
amalgamate.py
|
Windows cross-compilation (MinGW)
| Target | Description | Output directory |
|---|---|---|
make win32 |
Cross-compile for Windows using auto architecture | win32/auto/ |
make win32-64 |
Cross-compile 64-bit Windows build | win32/64/ |
make win32-32 |
Cross-compile 32-bit Windows build (i686) | win32/32/ |
make win32-32i686 |
Cross-compile 32-bit Windows build (i686 baseline) | win32/32i686/ |
Each Windows output folder contains zscript.exe,
sqlite3.dll, libmariadb.dll,
libmariadb.dll.a, and copied
lib/ and tests/ directories.
Windows MariaDB binaries are built from
thirdparty/mariadb-connector-c/ using the MinGW CMake
toolchain file (for example
/usr/share/mingw/toolchain-i686-w64-mingw32.cmake), not
copied from a system DLL package.
run.sh flags (Linux / macOS)
| Flag | Description |
|---|---|
| (none) | Debug build then run the interpreter |
--release |
Release build then run |
--compile |
Compile only, no run |
--format |
Run clang-format over all src/ files
|
--dbg <file.zs> |
Launch gdb with auto run and
bt on the given script
|
Usage
| Command | Description |
|---|---|
./dist/zscript.exe --run <file.zs> |
Execute a script file |
./dist/zscript.exe --tests |
Run all scripts in the bundled tests/ directory
|
./dist/zscript.exe --help |
Print help text |
Project Structure
| Path | Contents |
|---|---|
src/ |
Interpreter core: lexer, parser, compiler, bytecode evaluator |
src/core/ |
Builtin core: modules: io (print/scan
and File disk I/O), math,
os, path, date,
regex, object, array,
blob, promise, sqlite,
utf8, mongoose
|
dist/ |
Compiler output: zscript.exe. On each build,
lib/ and tests/ are copied into
dist/ so lib:name imports resolve next to
the executable (for example lib:http,
lib:argparser).
|
tests/ |
Example .zs scripts demonstrating every feature
|
lib/ |
User-level libraries importable via lib: (for example
lib/http.zs, lib/argparser.zs)
|
utf/ |
UTF-8 processing helpers (utf8proc) |
libbf/ |
BigInt backend (libbf) |
main.c |
Interpreter entry point |