A PHP framework for serious software
Fast, explicit, and small enough to understand. Crab gives long-lived PHP applications a clear foundation for APIs, services, and the work around them.
PHP 8.4 · MIT · open source
composer create-project crabphp/crab my-app
cd my-app
php cua dev
One way to do each thing
- Explicit
- Typed actions, named services, ordinary PHP. The important parts stay visible instead of hiding behind conventions.
- Long-lived
- The application loads once and serves requests as a real server. No PHP-FPM, no bootstrapping on every request.
- Complete
- Routing, validation, databases, queues, scheduling, authentication, HTTP, streaming, and WebSockets on one small foundation.
Included
- Routing typed parameters and groups
- Actions classes that say what they need
- Validation input checked before your action
- Database SQLite and MySQL, async when needed
- Queues durable work outside a request
- AI applications streaming, runs, and actors
- Testing requests without a server
- Deployment a server you can operate
A route is just a route
// routes/web.php
use Crab\Route;
Route::get('/hello/{name}', static function (string $name): array {
return ['hello' => $name];
});
Written for agents too
Explicit types, no hidden state, one way to do each thing. The same things that make code easy for a person to read make it easy for a coding agent to get right.
$ php cua describe routes
routes
POST /orders -> App\Actions\PlaceOrder via Crab\Auth\TokenAuth
body { lines: Array<{ productId: int; quantity?: int | null (minimum=1, maximum=20, default=1) }> (minItems=1, maxItems=20) }
user: App\User
GET /products/{id} -> App\Actions\ShowProduct
{id}: int
- describe
- The whole application in one read: routes and what each takes, middleware, commands, schedule, listeners, databases, settings. One thing per line, in few tokens.
--jsongives JSON Schema. - AGENTS.md
- Every new app ships with one: where things go, the rules a long-lived server needs, and how to check the work.
- problem:
describe applists settings that do not fit and services that cannot be made, beforestartrefuses them.- Markdown
- The guide is plain Markdown, in
vendor/crabphp/framework/docs/and at /llms.txt.
One command runs all of it
HTTP, queue workers, and the scheduler start together. No Supervisor config, no systemd unit per worker, no crontab line. List the queue and the scheduler in app.php, then start.
$ php cua start --daemon
Starting Shop server on http://127.0.0.1:8080
Server Workers Runs
http 2 http://127.0.0.1:8080
queue 3 queue:work: mail x1, default x2
schedule 1 schedule:work
- --daemon
- Runs in the background and returns once it is up. A worker that dies is started again.
- reload
- HTTP, the queue, and the scheduler get the new code together, without refusing a connection.
- status
- Every worker, what it has handled, and its memory, in one table.
Benchmarks
Requests per second, median, 64 persistent connections.
| Framework | Hello | Database | Validation |
|---|---|---|---|
| Crab | 200,401 | 18,367 | 101,389 |
| webman Workerman | 146,898 | 8,314 | 11,873 |
| Hyperf Swoole | 97,048 | 20,102 | 13,225 |
| Symfony FrankenPHP | 12,718 | 7,442 | 10,116 |
| Spiral RoadRunner | 5,519 | 3,654 | 4,912 |
| Laravel Octane | 4,106 | 2,463 | 2,870 |
| Tempest FrankenPHP | needs PHP 8.5 | ||
Measured on one Apple M1 Pro with small, matched workloads. Not a universal ranking or a capacity estimate. Methodology and raw results