What the PilserLabs Serverless Engine actually is
This handbook documents the engine that powers pilserlabs.com: a single embeddable serverless platform, written in Rust, hosting many independent apps as isolated tenants.
The one-sentence version
A serverless engine is a program that lets you create many small applications — each with its own database tables, users, files, automations — without deploying anything: you call an API, get a board (an app), and everything is already there.
Boards = apps
Everything starts with a board. Create one:
curl -X POST https://your-engine/mcp -d '{"method":"tools/call","params":{"name":"apps.create","arguments":{"title":"My App"}}}'
You get back a board id like b_7z5lr8zaurkd0000. That id is your app’s root:
- its data lives in its own tenant (fully isolated from other boards)
- its tables are created on demand (
POST /api/srv/<board>/tables/<name>) - its users authenticate with board-scoped sessions
- its files upload to
<board>/files/, its static frontend to/srv/<board>/
One engine process can host hundreds of boards. Deleting a board removes all of it.
What every board gets out of the box
| Capability | Surface | Notes |
|---|---|---|
| Document store | REST /tables/<t>/records |
JSON payloads, schema optional |
| Queries / search / aggregates | /query, /aggregate, q= |
filters, BM25 full-text, count/sum/avg/min/max |
| Schema layer | computed fields, validate, redact | declared per table; enforced server-side |
| Auth | signup/login/JWT/sessions + API keys with roles & scopes | owner/writer/reader/customer |
| Automations | recipes ($call, $set, $create_user, …) |
trigger on record events or cron |
| Webhooks | signed deliveries with retry/backoff | HMAC-SHA256 signatures |
| Cron jobs | schedule → HTTP action or recipe | server-side scheduler |
| Files | upload/download/list | object-store backed |
| Realtime | SSE /events/stream + WebSocket |
live record events |
| Static hosting | /srv/<board>/ serves your SPA |
same-origin with the API |
All of it reachable over plain HTTP — no SDK required.
Two control surfaces
- REST — what frontends use (
/api/srv/<board>/...) - MCP — what agents use. Every operation is also an MCP tool (
records.submit,recipes.add,graph.traverse, …), so coding agents can build and operate entire apps without ever touching a UI.
That second surface is unusual and deliberate: this engine was designed so that an AI agent is a first-class operator, not just a human with curl.
The storage chain
srv daemon (:7070)
└─ HelixDB (:7979) graph database, tenant-scoped nodes
└─ SlateDB LSM key-value layer
└─ MinIO/S3 durable objects (the actual bytes)
Every engine record is one HelixDB node carrying routing properties (table, seq,
board_id) plus the full JSON payload. Queries push down what Helix can answer
(label + property predicates) and filter the rest in Rust. A result cache sits in
front, with singleflight coalescing so concurrent identical queries share one scan.
Swap the whole chain by config — the engine speaks to a Database trait, so in-memory,
Helix, or your own adapter are interchangeable. Tests run entirely in-memory.
How it differs from Supabase/Firebase/PocketBase
| Typical BaaS | This engine | |
|---|---|---|
| Model | One giant shared DB, projects are folders | One process, boards are hard-isolated tenants |
| Deploy story | Cloud console, vendor lock-in | Single binary you own; runs on a VPS, in Docker, or embedded |
| Embedding | Impossible | It’s a Rust library crate — drop it into any project |
| Agent ops | Bolt-on APIs | Native MCP tool surface, built agent-first |
| Cost shape | Per-seat/per-row pricing | Your hardware, your rules |
The portability point matters most: serverless-engine-rs is published as a library.
If a product needs “a database plus auth plus files plus automations” inside a bigger
Rust application, you don’t deploy a SaaS — you add a dependency.
Where to go next
- Build your first app in 15 minutes
- How a write flows through the engine
- RSS for new posts: /rss.xml