e
This commit is contained in:
@@ -0,0 +1,94 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events;
|
||||
|
||||
|
||||
use Exception;
|
||||
use HttpServer\Application;
|
||||
use Snowflake\Error\Logger;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Timer;
|
||||
|
||||
abstract class Callback extends Application
|
||||
{
|
||||
|
||||
/** @var \Snowflake\Application */
|
||||
protected $container;
|
||||
|
||||
|
||||
/**
|
||||
* Callback constructor.
|
||||
* @param $container
|
||||
*/
|
||||
public function __construct($container)
|
||||
{
|
||||
$this->container = $container;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @param $server
|
||||
* @param $worker_id
|
||||
* @param $message
|
||||
* @throws Exception
|
||||
*/
|
||||
protected function clear($server, $worker_id, $message)
|
||||
{
|
||||
Timer::clearAll();
|
||||
$event = Snowflake::get()->event;
|
||||
|
||||
$event->offName(Event::EVENT_AFTER_REQUEST);
|
||||
$event->offName(Event::EVENT_BEFORE_REQUEST);
|
||||
$this->eventNotify($message, $event);
|
||||
|
||||
Snowflake::clearProcessId($server->worker_pid);
|
||||
Logger::write($this->_MESSAGE[$message] . $worker_id);
|
||||
Logger::clear();
|
||||
}
|
||||
|
||||
|
||||
|
||||
const EVENT_ERROR = 'WORKER:ERROR';
|
||||
const EVENT_STOP = 'WORKER:STOP';
|
||||
const EVENT_EXIT = 'WORKER:EXIT';
|
||||
|
||||
|
||||
private $_MESSAGE = [
|
||||
self::EVENT_ERROR => 'The server error. at No.',
|
||||
self::EVENT_STOP => 'The server stop. at No.',
|
||||
self::EVENT_EXIT => 'The server exit. at No.',
|
||||
];
|
||||
|
||||
/**
|
||||
* @param $message
|
||||
* @param $event
|
||||
*/
|
||||
private function eventNotify($message, $event)
|
||||
{
|
||||
switch ($message) {
|
||||
case self::EVENT_ERROR:
|
||||
if (!$event->exists(Event::SERVER_WORKER_ERROR)) {
|
||||
return;
|
||||
}
|
||||
$event->trigger(Event::SERVER_WORKER_ERROR);
|
||||
break;
|
||||
case self::EVENT_EXIT:
|
||||
if (!$event->exists(Event::SERVER_WORKER_EXIT)) {
|
||||
return;
|
||||
}
|
||||
$event->trigger(Event::SERVER_WORKER_EXIT);
|
||||
break;
|
||||
case self::EVENT_STOP:
|
||||
if (!$event->exists(Event::SERVER_WORKER_STOP)) {
|
||||
return;
|
||||
}
|
||||
$event->trigger(Event::SERVER_WORKER_STOP);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,118 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events;
|
||||
|
||||
|
||||
use HttpServer\Http\Context;
|
||||
use HttpServer\Http\Request as HRequest;
|
||||
use HttpServer\Http\Response as HResponse;
|
||||
use HttpServer\ServerManager;
|
||||
use ReflectionException;
|
||||
use Snowflake\Application;
|
||||
use Snowflake\Core\JSON;
|
||||
use Snowflake\Exception\NotFindClassException;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Error;
|
||||
use Swoole\Http\Request;
|
||||
use Swoole\Http\Response;
|
||||
use Exception;
|
||||
use Swoole\Http\Server;
|
||||
|
||||
class Http extends Server
|
||||
{
|
||||
|
||||
/** @var Application */
|
||||
protected $application;
|
||||
|
||||
|
||||
/**
|
||||
* Receive constructor.
|
||||
* @param $application
|
||||
* @param $host
|
||||
* @param null $port
|
||||
* @param null $mode
|
||||
* @param null $sock_type
|
||||
*/
|
||||
public function __construct($application, $host, $port = null, $mode = null, $sock_type = null)
|
||||
{
|
||||
parent::__construct($host, $port, $mode, $sock_type);
|
||||
$this->application = $application;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param array $settings
|
||||
* @param array $events
|
||||
* @param array $config
|
||||
* @return mixed|void
|
||||
* @throws NotFindClassException
|
||||
* @throws ReflectionException
|
||||
*/
|
||||
public function set(array $settings, $events = [], $config = [])
|
||||
{
|
||||
parent::set($settings);
|
||||
ServerManager::set($this, $settings, $this->application, $events, $config);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param Request $request
|
||||
* @param Response $response
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler(Request $request, Response $response)
|
||||
{
|
||||
try {
|
||||
[$sRequest, $sResponse] = static::setContext($request, $response);
|
||||
$sResponse->send(Snowflake::get()->router->dispatch(), 200);
|
||||
} catch (Error | \Throwable $exception) {
|
||||
if (!isset($sResponse)) {
|
||||
$response->status(200);
|
||||
$response->end($exception->getMessage());
|
||||
} else {
|
||||
$sResponse->send($this->format($exception), 200);
|
||||
}
|
||||
} finally {
|
||||
$dividing_line = str_pad('', 100, '-');
|
||||
$this->application->debug($dividing_line, 'app');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $exception
|
||||
* @return false|int|mixed|string
|
||||
* @throws Exception
|
||||
*/
|
||||
public function format($exception)
|
||||
{
|
||||
$errorInfo = [
|
||||
'message' => $exception->getMessage(),
|
||||
'file' => $exception->getFile(),
|
||||
'line' => $exception->getLine()
|
||||
];
|
||||
$this->application->error(var_export($errorInfo, true));
|
||||
|
||||
$code = $exception->getCode() ?? 500;
|
||||
$trance = array_slice($exception->getTrace(), 0, 10);
|
||||
Snowflake::get()->logger->write(print_r($trance, true), 'exception');
|
||||
|
||||
return JSON::to($code, $errorInfo['message']);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $request
|
||||
* @param $response
|
||||
* @return array
|
||||
* @throws Exception
|
||||
*/
|
||||
public static function setContext($request, $response): array
|
||||
{
|
||||
$request = Context::setContext('request', HRequest::create($request));
|
||||
$response = Context::setContext('response', HResponse::create($response));
|
||||
return [$request, $response];
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events;
|
||||
|
||||
|
||||
use Exception;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
/**
|
||||
* Class OnPacket
|
||||
* @package HttpServer\Events\Trigger
|
||||
*/
|
||||
class Packet extends Service
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param $data
|
||||
* @param $clientInfo
|
||||
* @return mixed
|
||||
* @throws
|
||||
*/
|
||||
public function onHandler($server, $data, $clientInfo)
|
||||
{
|
||||
try {
|
||||
$client = [$clientInfo['address'], $clientInfo['port']];
|
||||
if (empty($data = $this->unpack($data))) {
|
||||
throw new Exception('Format error.');
|
||||
}
|
||||
$client[] = $this->pack($data);
|
||||
return $server->sendto(...$client);
|
||||
} catch (\Throwable $exception) {
|
||||
$client[] = $this->pack(['message' => $exception->getMessage()]);
|
||||
return $server->sendto(...$client);
|
||||
} finally {
|
||||
$event = Snowflake::get()->event;
|
||||
$event->trigger(Event::SERVER_WORKER_STOP);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events;
|
||||
|
||||
|
||||
use Exception;
|
||||
use Snowflake\Core\JSON;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
/**
|
||||
* Class Receive
|
||||
* @package HttpServer\Events
|
||||
*/
|
||||
class Receive extends Service
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param int $fd
|
||||
* @param int $reactorId
|
||||
* @param string $data
|
||||
* @return mixed
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onReceive(\Swoole\Server $server, int $fd, int $reactorId, string $data)
|
||||
{
|
||||
try {
|
||||
$client = [$fd];
|
||||
if (empty($data = $this->unpack($data))) {
|
||||
throw new Exception('Format error.');
|
||||
}
|
||||
$client[] = $this->pack($data);
|
||||
return $server->send(...$client);
|
||||
} catch (\Throwable $exception) {
|
||||
$client[] = $this->pack(['message' => $exception->getMessage()]);
|
||||
return $server->send(...$client);
|
||||
} finally {
|
||||
$event = Snowflake::get()->event;
|
||||
$event->trigger(Event::SERVER_WORKER_STOP);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,128 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events;
|
||||
|
||||
|
||||
use Exception;
|
||||
use HttpServer\Application;
|
||||
use HttpServer\ServerManager;
|
||||
use ReflectionException;
|
||||
use Snowflake\Core\JSON;
|
||||
use Snowflake\Exception\ComponentException;
|
||||
use Snowflake\Exception\NotFindClassException;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Process\Pool;
|
||||
use Swoole\Server;
|
||||
use Closure;
|
||||
|
||||
/**
|
||||
* Class Service
|
||||
* @package HttpServer\Events
|
||||
*/
|
||||
abstract class Service extends Server
|
||||
{
|
||||
|
||||
/** @var \Snowflake\Application */
|
||||
protected $application;
|
||||
|
||||
|
||||
/** @var Closure|array */
|
||||
public $unpack;
|
||||
|
||||
|
||||
/** @var Closure|array */
|
||||
public $pack;
|
||||
|
||||
|
||||
/**
|
||||
* Receive constructor.
|
||||
* @param $application
|
||||
* @param $host
|
||||
* @param null $port
|
||||
* @param null $mode
|
||||
* @param null $sock_type
|
||||
*/
|
||||
public function __construct($application, $host, $port = null, $mode = null, $sock_type = null)
|
||||
{
|
||||
parent::__construct($host, $port, $mode, $sock_type);
|
||||
$this->application = $application;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param array $settings
|
||||
* @param array $events
|
||||
* @param array $config
|
||||
* @return mixed|void
|
||||
* @throws NotFindClassException
|
||||
* @throws ReflectionException
|
||||
*/
|
||||
public function set(array $settings, $events = [], $config = [])
|
||||
{
|
||||
parent::set($settings);
|
||||
ServerManager::set($this, $settings, $this->application, $events, $config);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $callbacks
|
||||
*/
|
||||
protected function bindCallback($callbacks)
|
||||
{
|
||||
if (empty($callbacks) || !is_array($callbacks)) {
|
||||
return;
|
||||
}
|
||||
foreach ($callbacks as $callback) {
|
||||
$this->on($callback[0], [$this, $callback[1][1]]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $eventName
|
||||
* @return array
|
||||
* @throws NotFindClassException
|
||||
* @throws ReflectionException
|
||||
* @throws Exception
|
||||
*/
|
||||
protected function createHandler($eventName)
|
||||
{
|
||||
$classPrefix = 'HttpServer\Events\Trigger\On' . ucfirst($eventName);
|
||||
if (!class_exists($classPrefix)) {
|
||||
throw new Exception('class not found.');
|
||||
}
|
||||
$class = Snowflake::createObject($classPrefix, [Snowflake::get()]);
|
||||
return [$class, 'onHandler'];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $data
|
||||
* @return mixed
|
||||
* @throws Exception
|
||||
*/
|
||||
public function pack($data)
|
||||
{
|
||||
$callback = $this->pack;
|
||||
if (is_callable($callback, true)) {
|
||||
return $callback($data);
|
||||
}
|
||||
return JSON::encode($data);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $data
|
||||
* @return mixed
|
||||
*/
|
||||
public function unpack($data)
|
||||
{
|
||||
$callback = $this->unpack;
|
||||
if (is_callable($callback, true)) {
|
||||
return $callback($data);
|
||||
}
|
||||
return JSON::decode($data);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnAfterReload extends Callback
|
||||
{
|
||||
|
||||
|
||||
public function onHandler()
|
||||
{
|
||||
// TODO: Implement onHandler() method.
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnBeforeReload extends Callback
|
||||
{
|
||||
|
||||
public function onHandler()
|
||||
{
|
||||
// TODO: Implement onHandler() method.
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnClose extends Callback
|
||||
{
|
||||
|
||||
public function onHandler()
|
||||
{
|
||||
// TODO: Implement onHandler() method.
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use Exception;
|
||||
use HttpServer\Events\Callback;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
/**
|
||||
* Class OnConnect
|
||||
* @package HttpServer\Events\Trigger
|
||||
*/
|
||||
class OnConnect extends Callback
|
||||
{
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param int $fd
|
||||
* @param int $reactorId
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onHandler(\Swoole\Server $server, int $fd, int $reactorId)
|
||||
{
|
||||
$event = Snowflake::get()->event;
|
||||
if (!$event->exists(Event::RECEIVE_CONNECTION)) {
|
||||
return;
|
||||
}
|
||||
$event->trigger(Event::RECEIVE_CONNECTION, [$server, $fd, $reactorId]);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use Exception;
|
||||
use HttpServer\Events\Callback;
|
||||
use Swoole\Server;
|
||||
|
||||
class OnFinish extends Callback
|
||||
{
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param $task_id
|
||||
* @param $data
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onHandler(Server $server, $task_id, $data)
|
||||
{
|
||||
$data = json_decode($data, true);
|
||||
$data['work_id'] = $task_id;
|
||||
$this->write(var_export($data, true), 'Task');
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
class OnManagerStart extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler(Server $server)
|
||||
{
|
||||
$this->debug('manager start.');
|
||||
Snowflake::setProcessId($server->manager_pid);
|
||||
|
||||
$events = Snowflake::get()->event;
|
||||
if ($events->exists(Event::SERVER_MANAGER_START)) {
|
||||
$events->trigger(Event::SERVER_MANAGER_START, null, $server);
|
||||
}
|
||||
if (Snowflake::isLinux()) {
|
||||
name('Server Manager.');
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
/**
|
||||
* Class OnManagerStop
|
||||
* @package HttpServer\Events\Trigger
|
||||
*/
|
||||
class OnManagerStop extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @param $server
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler(Server $server)
|
||||
{
|
||||
$this->warning('manager stop.');
|
||||
|
||||
$events = Snowflake::get()->event;
|
||||
if ($events->exists(Event::SERVER_MANAGER_STOP)) {
|
||||
$events->trigger(Event::SERVER_MANAGER_STOP, [$server]);
|
||||
}
|
||||
|
||||
// $runPath = storage(null, 'workerIds');
|
||||
// foreach (glob($runPath . '/*') as $item) {
|
||||
// if (!file_exists($item)) {
|
||||
// continue;
|
||||
// }
|
||||
// @unlink($item);
|
||||
// }
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnPipeMessage extends Callback
|
||||
{
|
||||
|
||||
public function onHandler()
|
||||
{
|
||||
// TODO: Implement onHandler() method.
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use Exception;
|
||||
use HttpServer\Events\Callback;
|
||||
use Snowflake\Core\JSON;
|
||||
use Snowflake\Error\Logger;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
use Closure;
|
||||
|
||||
class OnShutdown extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
*/
|
||||
public function onHandler(Server $server)
|
||||
{
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
class OnStart extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler($server)
|
||||
{
|
||||
$time = storage('socket.sock');
|
||||
Snowflake::writeFile($time, $server->master_pid);
|
||||
|
||||
$event = Snowflake::get()->event;
|
||||
if ($event->exists(Event::SERVER_EVENT_START)) {
|
||||
$event->trigger(Event::SERVER_EVENT_START, null, $server);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,140 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
use HttpServer\IInterface\Task as ITask;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
use Swoole\Timer;
|
||||
use Exception;
|
||||
|
||||
class OnTask extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onHandler()
|
||||
{
|
||||
$parameter = func_get_args();
|
||||
if (count($parameter) < 4) {
|
||||
$this->onContinueTask(...func_get_args());
|
||||
} else {
|
||||
$this->onTask(...func_get_args());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param int $task_id
|
||||
* @param int $from_id
|
||||
* @param string $data
|
||||
*
|
||||
* @return mixed|void
|
||||
* @throws Exception
|
||||
* 异步任务
|
||||
*/
|
||||
public function onTask(Server $server, $task_id, $from_id, $data)
|
||||
{
|
||||
$time = microtime(TRUE);
|
||||
if (empty($data)) {
|
||||
return $server->finish('null data');
|
||||
}
|
||||
$finish = $this->runTaskHandler($data);
|
||||
if (!$finish) {
|
||||
$finish = [];
|
||||
}
|
||||
$finish['runTime'] = [
|
||||
'startTime' => $time,
|
||||
'runTime' => microtime(TRUE) - $time,
|
||||
'endTime' => microtime(TRUE),
|
||||
];
|
||||
$server->finish(json_encode($finish));
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param Server\Task $task
|
||||
* @return mixed|void
|
||||
* @throws Exception
|
||||
* 异步任务
|
||||
*/
|
||||
public function onContinueTask(Server $server, Server\Task $task)
|
||||
{
|
||||
$time = microtime(TRUE);
|
||||
if (empty($task->data)) {
|
||||
return $task->finish('null data');
|
||||
}
|
||||
$finish = $this->runTaskHandler($task->data);
|
||||
if (!$finish) {
|
||||
$finish = [];
|
||||
}
|
||||
$finish['runTime'] = [
|
||||
'startTime' => $time,
|
||||
'runTime' => microtime(TRUE) - $time,
|
||||
'endTime' => microtime(TRUE),
|
||||
];
|
||||
$task->finish(json_encode($finish));
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $data
|
||||
* @return array|null
|
||||
* @throws Exception
|
||||
*/
|
||||
private function runTaskHandler($data)
|
||||
{
|
||||
$serialize = $this->before($data);
|
||||
try {
|
||||
$params = $serialize->getParams();
|
||||
if (is_object($params)) {
|
||||
$params = get_object_vars($params);
|
||||
}
|
||||
$finish['class'] = get_class($serialize);
|
||||
$finish['params'] = $params;
|
||||
$finish['status'] = 'success';
|
||||
$finish['info'] = $serialize->handler();
|
||||
} catch (\Throwable $exception) {
|
||||
$finish['status'] = 'error';
|
||||
$finish['info'] = $this->format($exception);
|
||||
$this->error($exception, 'Task');
|
||||
} finally {
|
||||
$event = Snowflake::get()->event;
|
||||
$event->trigger(Event::RELEASE_ALL);
|
||||
|
||||
$this->endCoroutine();
|
||||
Timer::clearAll();
|
||||
}
|
||||
return $finish;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $data
|
||||
* @return ITask|null
|
||||
*/
|
||||
protected function before($data)
|
||||
{
|
||||
if (empty($serialize = unserialize($data))) {
|
||||
return null;
|
||||
}
|
||||
if (!($serialize instanceof ITask)) {
|
||||
return null;
|
||||
}
|
||||
return $serialize;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $exception
|
||||
* @return string
|
||||
*/
|
||||
private function format($exception)
|
||||
{
|
||||
return $exception->getMessage() . " on line " . $exception->getLine() . " at file " . $exception->getFile();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnWorkerError extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @param $server
|
||||
* @param $worker_id
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler($server, $worker_id)
|
||||
{
|
||||
$this->clear($server, $worker_id, self::EVENT_ERROR);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnWorkerExit extends Callback
|
||||
{
|
||||
|
||||
/**
|
||||
* @param $server
|
||||
* @param $worker_id
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler($server, $worker_id)
|
||||
{
|
||||
$this->clear($server, $worker_id, self::EVENT_EXIT);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use Exception;
|
||||
use HttpServer\Events\Callback;
|
||||
use Snowflake\Error\Logger;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Server;
|
||||
|
||||
/**
|
||||
* Class OnWorkerStart
|
||||
* @package HttpServer\Events\Trigger
|
||||
*/
|
||||
class OnWorkerStart extends Callback
|
||||
{
|
||||
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param int $worker_id
|
||||
*
|
||||
* @return mixed|void
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onHandler(Server $server, $worker_id)
|
||||
{
|
||||
Logger::$worker_id = $worker_id;
|
||||
|
||||
Snowflake::setProcessId($server->worker_pid);
|
||||
|
||||
$get_name = $this->get_process_name($server, $worker_id);
|
||||
if (!empty($get_name) && !Snowflake::isMac()) {
|
||||
swoole_set_process_name($get_name);
|
||||
}
|
||||
$this->setWorkerAction($server, $worker_id);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $worker_id
|
||||
* @param $socket
|
||||
* @throws Exception
|
||||
*/
|
||||
private function setWorkerAction($socket, $worker_id)
|
||||
{
|
||||
try {
|
||||
$event = Snowflake::get()->event;
|
||||
if ($event->exists(Event::SERVER_WORKER_START)) {
|
||||
$event->trigger(Event::SERVER_WORKER_START);
|
||||
}
|
||||
} catch (\Throwable $exception) {
|
||||
Logger::write($exception->getMessage(), 'worker');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $socket
|
||||
* @param $worker_id
|
||||
* @return string
|
||||
*/
|
||||
private function get_process_name($socket, $worker_id)
|
||||
{
|
||||
$prefix = 'system:';
|
||||
if ($worker_id >= $socket->setting['worker_num']) {
|
||||
return $prefix . ': Task: No.' . $worker_id;
|
||||
} else {
|
||||
return $prefix . ': worker: No.' . $worker_id;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace HttpServer\Events\Trigger;
|
||||
|
||||
|
||||
use HttpServer\Events\Callback;
|
||||
|
||||
class OnWorkerStop extends Callback
|
||||
{
|
||||
|
||||
|
||||
/**
|
||||
* @param $server
|
||||
* @param $worker_id
|
||||
* @throws \Exception
|
||||
*/
|
||||
public function onHandler($server, $worker_id)
|
||||
{
|
||||
$this->clear($server, $worker_id, self::EVENT_STOP);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,182 @@
|
||||
<?php
|
||||
/**
|
||||
* Created by PhpStorm.
|
||||
* User: whwyy
|
||||
* Date: 2018/11/8 0008
|
||||
* Time: 18:15
|
||||
*/
|
||||
|
||||
namespace HttpServer\Events;
|
||||
|
||||
use BeReborn;
|
||||
use Exception;
|
||||
use HttpServer\ServerManager;
|
||||
use Snowflake\Error\Logger;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Exception\NotFindClassException;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Http\Request as SRequest;
|
||||
use Swoole\Http\Response as SResponse;
|
||||
use Swoole\WebSocket\Frame;
|
||||
use Swoole\WebSocket\Server;
|
||||
|
||||
/**
|
||||
* Class ServerWebSocket
|
||||
* @package BeReborn\Server
|
||||
*/
|
||||
class WebSocket extends Server
|
||||
{
|
||||
public $namespace = 'App\\Sockets\\';
|
||||
|
||||
public $callback = [];
|
||||
|
||||
|
||||
public $application;
|
||||
|
||||
|
||||
/**
|
||||
* WebSocket constructor.
|
||||
* @param $application
|
||||
* @param $host
|
||||
* @param null $port
|
||||
* @param null $mode
|
||||
* @param null $sock_type
|
||||
*/
|
||||
public function __construct($application, $host, $port = null, $mode = null, $sock_type = null)
|
||||
{
|
||||
$this->application = $application;
|
||||
parent::__construct($host, $port, $mode, $sock_type);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param array $settings
|
||||
* @param array $events
|
||||
* @param $config
|
||||
* @return mixed|void
|
||||
* @throws \ReflectionException
|
||||
* @throws NotFindClassException
|
||||
*/
|
||||
public function set(array $settings, $events = [], $config = [])
|
||||
{
|
||||
parent::set($settings);
|
||||
ServerManager::set($this, $settings, $this->application, $events, $config);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param Frame $frame
|
||||
* @throws
|
||||
*/
|
||||
public function onMessage(Server $server, Frame $frame)
|
||||
{
|
||||
try {
|
||||
$event = Snowflake::get()->event;
|
||||
if ($event->exists(Event::SERVER_MESSAGE)) {
|
||||
$event->trigger(Event::SERVER_MESSAGE, [$server, $frame]);
|
||||
return;
|
||||
}
|
||||
if ($frame->opcode == 0x08) {
|
||||
return;
|
||||
}
|
||||
$json = json_decode($frame->data, true);
|
||||
|
||||
$manager = Snowflake::get()->annotation;
|
||||
$manager->runWith($this->getName($json), [$frame->fd, $server]);
|
||||
} catch (Exception $exception) {
|
||||
// $this->error($exception->getMessage(), __METHOD__, __FILE__);
|
||||
// $this->addError($exception->getMessage());
|
||||
} finally {
|
||||
$event = Snowflake::get()->event;
|
||||
$event->trigger(Event::EVENT_AFTER_REQUEST);
|
||||
Logger::insert();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $json
|
||||
* @return string
|
||||
*/
|
||||
private function getName($json)
|
||||
{
|
||||
return 'WEBSOCKET:MESSAGE:' . $json['route'];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param SRequest $request
|
||||
* @param SResponse $response
|
||||
* @return bool
|
||||
* @throws Exception
|
||||
*/
|
||||
protected function connect($request, $response)
|
||||
{
|
||||
$manager = Snowflake::get()->event;
|
||||
if ($manager->exists(Event::SERVER_HANDSHAKE)) {
|
||||
return $manager->trigger(Event::SERVER_HANDSHAKE, [$request, $response]);
|
||||
}
|
||||
$response->status(502);
|
||||
$response->end();
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param SRequest $request
|
||||
* @param SResponse $response
|
||||
* @return bool|string
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onHandshake(SRequest $request, SResponse $response)
|
||||
{
|
||||
/** @var Server $server */
|
||||
$secWebSocketKey = $request->header['sec-websocket-key'];
|
||||
$patten = '#^[+/0-9A-Za-z]{21}[AQgw]==$#';
|
||||
if (0 === preg_match($patten, $secWebSocketKey) || 16 !== strlen(base64_decode($secWebSocketKey))) {
|
||||
return false;
|
||||
}
|
||||
$key = base64_encode(sha1(
|
||||
$request->header['sec-websocket-key'] . '258EAFA5-E914-47DA-95CA-C5AB0DC85B11',
|
||||
TRUE
|
||||
));
|
||||
$headers = [
|
||||
'Upgrade' => 'websocket',
|
||||
'Connection' => 'Upgrade',
|
||||
'Sec-websocket-Accept' => $key,
|
||||
'Sec-websocket-Version' => '13',
|
||||
];
|
||||
if (isset($request->header['sec-websocket-protocol'])) {
|
||||
$headers['Sec-websocket-Protocol'] = $request->header['sec-websocket-protocol'];
|
||||
}
|
||||
foreach ($headers as $key => $val) {
|
||||
$response->header($key, $val);
|
||||
}
|
||||
if (isset($request->get['debug']) && $request->get['debug'] == 'test') {
|
||||
$response->status(101);
|
||||
$response->end();
|
||||
return true;
|
||||
} else {
|
||||
return $this->connect($request, $response);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Server $server
|
||||
* @param int $fd
|
||||
* @throws Exception
|
||||
*/
|
||||
public function onClose(Server $server, int $fd)
|
||||
{
|
||||
$event = Snowflake::get()->event;
|
||||
try {
|
||||
if ($event->exists(Event::SERVER_CLOSE)) {
|
||||
$event->trigger(Event::SERVER_CLOSE, [$fd]);
|
||||
}
|
||||
} catch (\Throwable $exception) {
|
||||
// $this->addError($exception->getMessage());
|
||||
} finally {
|
||||
$event->trigger(Event::RELEASE_ALL);
|
||||
Logger::insert();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user