/** * Titanic request service */ function titanic_request($pipe) { $worker = new Mdwrk("tcp://localhost:5555", "titanic.request"); $reply = null; while (true) { // Get next request from broker $request = $worker->recv($reply); // Ensure message directory exists if (!is_dir(TITANIC_DIR)) { mkdir(TITANIC_DIR); } // Generate UUID and save message to disk $uuid = s_generate_uuid(); $filename = s_request_filename($uuid); $fh = fopen($filename, "w"); $request->save($fh); fclose($fh); // Send UUID through to message queue $reply = new Zmsg($pipe); $reply->push($uuid); $reply->send(); // Now send UUID back to client // - sent in the next loop iteration $reply = new Zmsg(); $reply->push($uuid); $reply->push("200"); } }
public function send($data) { $msg = new Zmsg($this->socket); $msg->push($data); $msg->wrap(sprintf("%.0f", microtime(1) * 1000)); $msg->send(true); }
function worker_task() { $context = new ZMQContext(); $worker = new ZMQSocket($context, ZMQ::SOCKET_DEALER); $worker->setSockOpt(ZMQ::SOCKOPT_IDENTITY, "W"); $worker->connect("tcp://localhost:5556"); while (true) { $zmsg = new Zmsg($worker); $zmsg->recv(); $zmsg->send(); } }
function worker_thread($self) { $context = new ZMQContext(); $worker = $context->getSocket(ZMQ::SOCKET_REQ); $endpoint = sprintf("ipc://%s-localbe.ipc", $self); $worker->connect($endpoint); // Tell broker we're ready for work $worker->send("READY"); while (true) { $zmsg = new Zmsg($worker); $zmsg->recv(); sleep(mt_rand(0, 2)); $zmsg->send(); } }
function worker_thread() { $context = new ZMQContext(); $worker = $context->getSocket(ZMQ::SOCKET_REQ); $worker->connect("ipc://backend.ipc"); // Tell broker we're ready for work $worker->send("READY"); while (true) { $zmsg = new Zmsg($worker); $zmsg->recv(); // Additional logic to clean up workers. if ($zmsg->address() == "END") { exit; } printf("Worker: %s\n", $zmsg->body()); $zmsg->body_set("OK"); $zmsg->send(); } }
/** * Run a self test of the Zmsg class. * * @return boolean * @todo See if assert returns */ public static function test() { $result = true; $context = new ZMQContext(); $output = new ZMQSocket($context, ZMQ::SOCKET_XREQ); $output->bind("inproc://zmsg_selftest"); $input = new ZMQSocket($context, ZMQ::SOCKET_XREP); $input->connect("inproc://zmsg_selftest"); // Test send and receive of single-part message $zmsgo = new Zmsg($output); $zmsgo->body_set("Hello"); $result &= assert($zmsgo->body() == "Hello"); $zmsgo->send(); $zmsgi = new Zmsg($input); $zmsgi->recv(); $result &= assert($zmsgi->parts() == 2); $result &= assert($zmsgi->body() == "Hello"); echo $zmsgi; // Test send and receive of multi-part message $zmsgo = new Zmsg($output); $zmsgo->body_set("Hello"); $zmsgo->wrap("address1", ""); $zmsgo->wrap("address2"); $result &= assert($zmsgo->parts() == 4); echo $zmsgo; $zmsgo->send(); $zmsgi = new Zmsg($input); $zmsgi->recv(); $result &= assert($zmsgi->parts() == 5); $zmsgi->unwrap(); $result &= assert($zmsgi->unwrap() == "address2"); $zmsgi->body_fmt("%s%s", 'W', "orld"); $result &= assert($zmsgi->body() == "World"); // Pull off address 1, check that empty part was dropped $zmsgi->unwrap(); $result &= assert($zmsgi->parts() == 1); // Check that message body was correctly modified $part = $zmsgi->pop(); $result &= assert($part == "World"); $result &= assert($zmsgi->parts() == 0); // Test load and save $zmsg = new Zmsg(); $zmsg->body_set("Hello"); $zmsg->wrap("address1", ""); $zmsg->wrap("address2"); $result &= assert($zmsg->parts() == 4); $fh = fopen(sys_get_temp_dir() . "/zmsgtest.zmsg", 'w'); $zmsg->save($fh); fclose($fh); $fh = fopen(sys_get_temp_dir() . "/zmsgtest.zmsg", 'r'); $zmsg2 = new Zmsg(); $zmsg2->load($fh); assert($zmsg2->last() == $zmsg->last()); fclose($fh); $result &= assert($zmsg2->parts() == 4); echo $result ? "OK" : "FAIL", PHP_EOL; return $result; }
// - 3-part envelope + content -> request // - 1-part "HEARTBEAT" -> heartbeat $zmsg = new Zmsg($worker); $zmsg->recv(); if ($zmsg->parts() == 3) { // Simulate various problems, after a few cycles $cycles++; if ($cycles > 3 && rand(0, 5) == 0) { printf("I: (%s) simulating a crash%s", $identity, PHP_EOL); break; } elseif ($cycles > 3 && rand(0, 5) == 0) { printf("I: (%s) simulating CPU overload%s", $identity, PHP_EOL); sleep(5); } printf("I: (%s) normal reply - %s%s", $identity, $zmsg->body(), PHP_EOL); $zmsg->send(); $liveness = HEARTBEAT_LIVENESS; sleep(1); // Do some heavy work } elseif ($zmsg->parts() == 1 && $zmsg->body() == 'HEARTBEAT') { $liveness = HEARTBEAT_LIVENESS; } else { printf("E: (%s) invalid message%s%s", $identity, PHP_EOL, $zmsg->__toString()); } $interval = INTERVAL_INIT; } elseif (--$liveness == 0) { printf("W: (%s) heartbeat failure, can't reach queue%s", $identity, PHP_EOL); printf("W: (%s) reconnecting in %d msec...%s", $identity, $interval, PHP_EOL); usleep($interval * 1000); if ($interval < INTERVAL_MAX) { $interval *= 2;
function server_worker() { $context = new ZMQContext(); $worker = new ZMQSocket($context, ZMQ::SOCKET_DEALER); $worker->connect("ipc://backend"); $zmsg = new Zmsg($worker); while (true) { // The DEALER socket gives us the address envelope and message $zmsg->recv(); assert($zmsg->parts() == 2); // Send 0..4 replies back $replies = rand(0, 4); for ($reply = 0; $reply < $replies; $reply++) { // Sleep for some fraction of a second usleep(rand(0, 1000) + 1); $zmsg->send(Zmsg::NOCLEAR); } } }
/** * Send request to broker and get reply by hook or crook * Takes ownership of request message and destroys it when sent. * Returns the reply message or NULL if there was no reply. * * @param string $service * @param Zmsg $request * @param string $client * @return Zmsg */ public function send($service, Zmsg $request) { // Prefix request with protocol frames // Frame 1: "MDPCxy" (six bytes, MDP/Client // Frame 2: Service name (printable string) $request->push($service); $request->push(MDPC_CLIENT); if ($this->verbose) { printf("I: send request to '%s' service:", $service); echo $request->__toString(); } $retries_left = $this->retries; $read = $write = array(); while ($retries_left) { $request->set_socket($this->client)->send(); // Poll socket for a reply, with timeout $poll = new ZMQPoll(); $poll->add($this->client, ZMQ::POLL_IN); $events = $poll->poll($read, $write, $this->timeout); // If we got a reply, process it if ($events) { $request->recv(); if ($this->verbose) { echo "I: received reply:", $request->__toString(), PHP_EOL; } // Don't try to handle errors, just assert noisily assert($request->parts() >= 3); $header = $request->pop(); assert($header == MDPC_CLIENT); $reply_service = $request->pop(); assert($reply_service == $service); return $request; // Success } elseif ($retries_left--) { if ($this->verbose) { echo "W: no reply, reconnecting...", PHP_EOL; } // Reconnect, and resend message $this->connect_to_broker(); $request->send(); } else { echo "W: permanent error, abandoning request", PHP_EOL; break; // Give up } } }