Router & Middleware
Built-in HTTP router with path parameters, middleware chains, and composable request handling.
A Zig library for writing Cloudflare Workers. First-class bindings for the entire Workers runtime — compiled to ~15KB of WebAssembly.
cf-workerz brings Zig's performance and safety to the Cloudflare Workers platform. Write your edge functions in Zig, compile to WebAssembly, and deploy with the standard Cloudflare toolchain. The resulting WASM binary is typically 10-15KB — orders of magnitude smaller than equivalent JavaScript bundles.
The library provides idiomatic Zig bindings for the entire Workers runtime API: storage (KV, R2, D1), caching, message queues, Workers AI, Durable Objects, WebSockets, and Web Crypto. It includes a built-in Router with middleware support, and uses JSPI (JavaScript Promise Integration) for ergonomic async operations.
Built-in HTTP router with path parameters, middleware chains, and composable request handling.
Full Workers KV bindings — get, put, delete, and list operations with metadata support.
Bindings for Cloudflare R2 — put, get, delete, list objects with S3-compatible semantics.
SQL database bindings for Cloudflare D1 — prepared statements, batch operations, and result iteration.
Workers Cache API bindings for programmatic HTTP caching at the edge.
Message queue producer and consumer bindings for asynchronous task processing.
Bindings for Cloudflare's Workers AI — run inference on machine learning models at the edge.
Stateful serverless — Durable Object bindings with transactional storage and alarm scheduling.
Full WebSocket support — server and client connections with message handling and binary frames.
Web Crypto API bindings — hashing, HMAC, encryption/decryption, and key generation.
Outbound fetch with headers, redirects, and Cloudflare-specific options. Streaming request and response bodies.
JavaScript Promise Integration for ergonomic async/await patterns in Zig — no callback gymnastics.
const std = @import("std");
const cf = @import("cf-workerz");
const Router = cf.Router;
fn onRequest(allocator: std.mem.Allocator, ctx: *cf.FetchContext) !*cf.Response {
var router = Router.init(allocator, ctx);
router.get("/api/hello", handleHello);
router.get("/api/user/:id", handleUser);
return router.serve();
}
fn handleHello(ctx: *FetchContext) void {
// Use ctx.param() shorthand for path parameters
const name = ctx.param("name") orelse "World";
// ctx.json() with anonymous struct
ctx.json(.{
.message = "Hello!",
.name = name,
}, 200);
}