Worker
Creating a worker
Worker types
Simple HTTP worker
composer require spiral/roadrunner-http nyholm/psr7<?php
require __DIR__ . '/vendor/autoload.php';
use Nyholm\Psr7\Response;
use Nyholm\Psr7\Factory\Psr17Factory;
use Spiral\RoadRunner\Worker;
use Spiral\RoadRunner\Http\PSR7Worker;
// Create new RoadRunner worker from global environment
$worker = Worker::create();
// Create common PSR-17 HTTP factory
$factory = new Psr17Factory();
$psr7 = new PSR7Worker($worker, $factory, $factory, $factory);
while (true) {
try {
$request = $psr7->waitRequest();
if ($request === null) {
break;
}
} catch (\Throwable $e) {
// Although the PSR-17 specification clearly states that there can be
// no exceptions when creating a request, however, some implementations
// may violate this rule. Therefore, it is recommended to process the
// incoming request for errors.
//
// Send "Bad Request" response.
$psr7->respond(new Response(400));
continue;
}
try {
// Here is where the call to your application code will be located.
// For example:
// $response = $app->send($request);
//
// Reply by the 200 OK response
$psr7->respond(new Response(200, [], 'Hello RoadRunner!'));
} catch (\Throwable $e) {
// In case of any exceptions in the application code, you should handle
// them and inform the client about the presence of a server error.
//
// Reply by the 500 Internal Server Error response
$psr7->respond(new Response(500, [], 'Something Went Wrong!'));
// Additionally, we can inform the RoadRunner that the processing
// of the request failed. Use error instead of response to indicate
// worker error, do not use both.
// $psr7->getWorker()->error((string)$e);
}
}server:
command: "php psr-worker.php"
http:
address: 0.0.0.0:8080Single entry point
composer require spiral/roadrunner-http spiral/roadrunner-jobs nyholm/psr7namespace App;
enum RoadRunnerMode: string
{
case Http = 'http';
case Jobs = 'jobs';
case Temporal = 'temporal';
case Grpc = 'grpc';
case Tcp = 'tcp';
case Centrifuge = 'centrifuge';
case Unknown = 'unknown';
}namespace App\Dispatcher;
use Spiral\RoadRunner\EnvironmentInterface;
interface DispatcherInterface
{
public function canServe(EnvironmentInterface $env): bool;
public function serve(): void;
}namespace App\Dispatcher;
use App\RoadRunnerMode;
use Nyholm\Psr7\Factory\Psr17Factory;
use Nyholm\Psr7\Response;
use Spiral\RoadRunner\EnvironmentInterface;
use Spiral\RoadRunner\Http\PSR7Worker;
use Spiral\RoadRunner\Worker;
final class HttpDispatcher implements DispatcherInterface
{
public function canServe(EnvironmentInterface $env): bool
{
return $env->getMode() === RoadRunnerMode::Http->value;
}
public function serve(): void
{
$factory = new Psr17Factory();
$worker = new PSR7Worker(Worker::create(), $factory, $factory, $factory);
while (true) {
try {
$request = $worker->waitRequest();
if ($request === null) {
break;
}
} catch (\Throwable $e) {
$worker->respond(new Response(400));
continue;
}
try {
// Handle request and return response.
$worker->respond(new Response(200, [], 'Hello RoadRunner!'));
} catch (\Throwable $e) {
$worker->respond(new Response(500, [], 'Something Went Wrong!'));
}
}
}
}namespace App\Dispatcher;
use App\RoadRunnerMode;
use Spiral\RoadRunner\EnvironmentInterface;
use Spiral\RoadRunner\Jobs\Consumer;
final class QueueDispatcher implements DispatcherInterface
{
public function canServe(EnvironmentInterface $env): bool
{
return $env->getMode() === RoadRunnerMode::Jobs->value;
}
public function serve(): void
{
$consumer = new Consumer();
while ($task = $consumer->waitTask()) {
try {
// Handle and process task. Here we just print payload.
var_dump($task);
// Complete task.
$task->complete();
} catch (\Throwable $e) {
$task->fail($e);
}
}
}
}require __DIR__ . '/vendor/autoload.php';
use App\Dispatcher\DispatcherInterface;
use App\Dispatcher\HttpDispatcher;
use App\Dispatcher\QueueDispatcher;
use Spiral\RoadRunner\Environment;
/**
* Collect all dispatchers.
*
* @var DispatcherInterface[] $dispatchers
*/
$dispatchers = [
new HttpDispatcher(),
new QueueDispatcher(),
];
// Create environment
$env = Environment::fromGlobals();
// Execute dispatcher that can serve the request
foreach ($dispatchers as $dispatcher) {
if ($dispatcher->canServe($env)) {
$dispatcher->serve();
}
}version: '3'
rpc:
listen: tcp://127.0.0.1:6001
server:
command: "php app.php"
http:
address: "0.0.0.0:8080"
jobs:
consume: [ "default" ]
pool:
num_workers: 2
supervisor:
max_worker_memory: 100
pipelines:
default:
driver: memory
config:
priority: 10./rr serveError Handling
try {
$resp = new Psr7\Response();
$resp->getBody()->write("hello world");
$psr7->respond($resp);
} catch (\Throwable $e) {
$psr7->getWorker()->error((string)$e);
}file_put_contents('php://stderr', 'Error message');Communication Methods
server:
command: "php psr-worker.php"
relay: "tcp://127.0.0.1:7000"
http:
address: 0.0.0.0:8080server:
command: "php psr-worker.php"
relay: "unix://rr.sock"
http:
address: 0.0.0.0:8080Process supervision
http:
address: "0.0.0.0:8080"
pool:
supervisor:
# watch_tick defines how often to check the state of the workers (seconds)
watch_tick: 5s
# ttl defines maximum time worker is allowed to live (seconds)
ttl: 0s
# idle_ttl defines maximum duration worker can spend in idle mode after
# first use. Disabled when 0 (seconds)
idle_ttl: 10s
# exec_ttl defines maximum lifetime per job (seconds)
exec_ttl: 10s
# max_worker_memory limits memory usage per worker (MB)
max_worker_memory: 100
num_workers: 6Troubleshooting
./rr servephp psr-worker.phpWhat's Next?
Last updated