改名
This commit is contained in:
@@ -29,7 +29,6 @@ use Server\ServerManager;
|
||||
use Snowflake\Aop;
|
||||
use Snowflake\Async;
|
||||
use Snowflake\Cache\Redis;
|
||||
use Snowflake\Channel;
|
||||
use Snowflake\Di\Service;
|
||||
use Snowflake\Error\ErrorHandler;
|
||||
use Snowflake\Error\Logger;
|
||||
@@ -423,16 +422,6 @@ abstract class BaseApplication extends Service
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @return Channel
|
||||
* @throws Exception
|
||||
*/
|
||||
public function getChannel(): Channel
|
||||
{
|
||||
return $this->get('channel');
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @return Pool
|
||||
* @throws Exception
|
||||
@@ -470,7 +459,6 @@ abstract class BaseApplication extends Service
|
||||
'goto' => ['class' => BaseGoto::class],
|
||||
'response' => ['class' => Response::class],
|
||||
'request' => ['class' => Request::class],
|
||||
'channel' => ['class' => Channel::class],
|
||||
'rpc' => ['class' => \Rpc\Producer::class],
|
||||
'rpc-service' => ['class' => \Rpc\Service::class],
|
||||
'http2' => ['class' => Http2::class],
|
||||
|
||||
@@ -19,7 +19,6 @@ use Kafka\Producer;
|
||||
use Rpc\Producer as RPCProducer;
|
||||
use Snowflake\Async;
|
||||
use Snowflake\Cache\Redis;
|
||||
use Snowflake\Channel;
|
||||
use Snowflake\Error\Logger;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Jwt\Jwt;
|
||||
@@ -50,7 +49,6 @@ use Snowflake\Pool\Pool;
|
||||
* @property \Snowflake\Crontab\Producer $crontab
|
||||
* @property HttpFilter $filter
|
||||
* @property RPCProducer $rpc
|
||||
* @property Channel $channel
|
||||
* @property Shutdown $shutdown
|
||||
* @property Pool $clientsPool
|
||||
*/
|
||||
|
||||
@@ -95,7 +95,7 @@ class Application extends BaseApplication
|
||||
if (!class_exists($service)) {
|
||||
throw new NotFindClassException($service);
|
||||
}
|
||||
$class = Snowflake::createObject($service);
|
||||
$class = Snowflake::getDi()->get($service);
|
||||
if (method_exists($class, 'onImport')) {
|
||||
$class->onImport($this);
|
||||
}
|
||||
|
||||
+16
-18
@@ -9,11 +9,14 @@ declare(strict_types=1);
|
||||
|
||||
namespace Snowflake\Cache;
|
||||
|
||||
use Annotation\Inject;
|
||||
use Exception;
|
||||
use Server\Events\OnWorkerExit;
|
||||
use Server\Events\OnWorkerStop;
|
||||
use Snowflake\Abstracts\Component;
|
||||
use Snowflake\Abstracts\Config;
|
||||
use Snowflake\Core\Json;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Events\EventProvider;
|
||||
use Snowflake\Exception\ConfigException;
|
||||
use Snowflake\Snowflake;
|
||||
|
||||
@@ -21,35 +24,32 @@ use Snowflake\Snowflake;
|
||||
* Class Redis
|
||||
* @package Snowflake\Snowflake\Cache
|
||||
* @see \Redis
|
||||
*
|
||||
* @mixin \Redis
|
||||
*/
|
||||
class Redis extends Component
|
||||
{
|
||||
|
||||
|
||||
/**
|
||||
* @throws Exception
|
||||
* @var EventProvider
|
||||
*/
|
||||
public function init()
|
||||
{
|
||||
Event::on(Event::SYSTEM_RESOURCE_CLEAN, [$this, 'destroy']);
|
||||
Event::on(Event::SYSTEM_RESOURCE_RELEASES, [$this, 'release']);
|
||||
Event::on(Event::SERVER_WORKER_START, [$this, 'createPool']);
|
||||
Event::on(Event::SERVER_TASK_START, [$this, 'createPool']);
|
||||
}
|
||||
#[Inject(EventProvider::class)]
|
||||
public EventProvider $eventProvider;
|
||||
|
||||
|
||||
/**
|
||||
* @throws ConfigException
|
||||
* @throws Exception
|
||||
*/
|
||||
public function createPool()
|
||||
public function init()
|
||||
{
|
||||
$connections = Snowflake::app()->getRedisFromPool();
|
||||
|
||||
$config = $this->get_config();
|
||||
|
||||
$length = Config::get('connections.pool.max',10);
|
||||
$length = Config::get('connections.pool.max', 10);
|
||||
|
||||
$this->eventProvider->on(OnWorkerStop::class, [$this, 'destroy'], 0);
|
||||
$this->eventProvider->on(OnWorkerExit::class, [$this, 'destroy'], 0);
|
||||
|
||||
$connections->initConnections('Redis:' . $config['host'], true, $length);
|
||||
}
|
||||
@@ -68,12 +68,11 @@ class Redis extends Component
|
||||
$data = $this->{$name}(...$arguments);
|
||||
} else {
|
||||
$data = $this->proxy()->{$name}(...$arguments);
|
||||
$this->release();
|
||||
}
|
||||
|
||||
if (microtime(true) - $time >= 0.02) {
|
||||
$this->warning('Redis:' . Json::encode([$name, $arguments]) . (microtime(true) - $time));
|
||||
}
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
@@ -94,7 +93,7 @@ if (_nx ~= 0) then
|
||||
end
|
||||
return 0
|
||||
SCRIPT;
|
||||
return $this->proxy()->eval($script, ['{lock}:' . $key, $timeout], 1);
|
||||
return $this->eval($script, ['{lock}:' . $key, $timeout], 1);
|
||||
}
|
||||
|
||||
|
||||
@@ -105,8 +104,7 @@ SCRIPT;
|
||||
*/
|
||||
public function unlock($key): int
|
||||
{
|
||||
$redis = $this->proxy();
|
||||
return $redis->del('{lock}:' . $key);
|
||||
return $this->del('{lock}:' . $key);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -1,108 +0,0 @@
|
||||
<?php
|
||||
|
||||
|
||||
namespace Snowflake;
|
||||
|
||||
|
||||
use Closure;
|
||||
use Exception;
|
||||
use Snowflake\Abstracts\Component;
|
||||
use SplQueue;
|
||||
|
||||
|
||||
/**
|
||||
* Class Channel
|
||||
* @package Snowflake
|
||||
*/
|
||||
class Channel extends Component
|
||||
{
|
||||
|
||||
|
||||
private static ?array $_channels = [];
|
||||
|
||||
|
||||
private static ?array $_waitRecover = [];
|
||||
|
||||
|
||||
public function init()
|
||||
{
|
||||
Event::on(Event::SYSTEM_RESOURCE_RELEASES, [$this, 'recover']);
|
||||
Event::on(Event::SERVER_WORKER_EXIT, [$this, 'cleanAll']);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 回收对象
|
||||
*/
|
||||
public function recover()
|
||||
{
|
||||
foreach (Channel::$_waitRecover as $key => $value) {
|
||||
if (empty($value)) {
|
||||
continue;
|
||||
}
|
||||
$channel = $this->channelInit($key);
|
||||
if ($channel->count() >= 100) {
|
||||
continue;
|
||||
}
|
||||
foreach ($value as $item) {
|
||||
$channel->enqueue($item);
|
||||
}
|
||||
}
|
||||
Channel::$_waitRecover = [];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param mixed $value
|
||||
* @param string $name
|
||||
* @throws Exception
|
||||
*/
|
||||
public function push(mixed $value, string $name = ''): void
|
||||
{
|
||||
if (!isset(Channel::$_waitRecover[$name])) {
|
||||
Channel::$_waitRecover[$name] = [];
|
||||
}
|
||||
Channel::$_waitRecover[$name][] = $value;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param string $name
|
||||
* @return bool|SplQueue
|
||||
*/
|
||||
private function channelInit(string $name = ''): bool|SplQueue
|
||||
{
|
||||
if (!isset(static::$_channels[$name]) || !(static::$_channels[$name] instanceof SplQueue)) {
|
||||
static::$_channels[$name] = new SplQueue();
|
||||
}
|
||||
return static::$_channels[$name];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
* 清空缓存
|
||||
*/
|
||||
public function cleanAll()
|
||||
{
|
||||
static::$_channels = null;
|
||||
static::$_channels = [];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param string $name
|
||||
* @param Closure $closure
|
||||
* @return mixed
|
||||
*/
|
||||
public function pop(string $name, Closure $closure): mixed
|
||||
{
|
||||
$channel = $this->channelInit($name);
|
||||
if ($channel->isEmpty()) {
|
||||
return call_user_func($closure);
|
||||
}
|
||||
return $channel->dequeue();
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
+12
-4
@@ -9,11 +9,14 @@ declare(strict_types=1);
|
||||
|
||||
namespace Snowflake\Error;
|
||||
|
||||
use Annotation\Inject;
|
||||
use Exception;
|
||||
use Server\Events\OnAfterRequest;
|
||||
use Snowflake\Abstracts\Component;
|
||||
use Snowflake\Abstracts\Config;
|
||||
use Snowflake\Core\Json;
|
||||
use Snowflake\Event;
|
||||
use Snowflake\Events\EventProvider;
|
||||
use Snowflake\Exception\ConfigException;
|
||||
use Snowflake\Snowflake;
|
||||
use Swoole\Coroutine;
|
||||
@@ -29,15 +32,20 @@ class Logger extends Component
|
||||
private array $logs = [];
|
||||
|
||||
|
||||
/** @var EventProvider */
|
||||
#[Inject(EventProvider::class)]
|
||||
public EventProvider $eventProvider;
|
||||
|
||||
|
||||
private array $sources = [];
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
public function init()
|
||||
{
|
||||
Event::on(Event::SYSTEM_RESOURCE_CLEAN, [$this, 'insert']);
|
||||
Event::on(Event::SYSTEM_RESOURCE_CLEAN, [$this, 'closeSource']);
|
||||
Event::on(Event::SYSTEM_RESOURCE_RELEASES, [$this, 'closeSource']);
|
||||
Event::on(Event::SYSTEM_RESOURCE_RELEASES, [$this, 'insert']);
|
||||
$this->eventProvider->on(OnAfterRequest::class, [$this, 'insert']);
|
||||
}
|
||||
|
||||
|
||||
|
||||
+17
-50
@@ -7,6 +7,7 @@ namespace Snowflake;
|
||||
|
||||
use Exception;
|
||||
use Snowflake\Abstracts\BaseObject;
|
||||
use Swoole\Coroutine;
|
||||
|
||||
/**
|
||||
* Class Event
|
||||
@@ -85,18 +86,16 @@ class Event extends BaseObject
|
||||
* @param bool $isAppend
|
||||
* @throws Exception
|
||||
*/
|
||||
public static function on($name, $callback, array $parameter = [], bool $isAppend = false)
|
||||
public static function on($name, $callback, bool $isAppend = false)
|
||||
{
|
||||
if (!isset(static::$_events[$name])) {
|
||||
static::$_events[$name] = [];
|
||||
}
|
||||
if ($callback instanceof \Closure) {
|
||||
$callback = \Closure::bind($callback, Snowflake::app());
|
||||
} else if (is_array($callback) && is_string($callback[0])) {
|
||||
if (is_array($callback) && is_string($callback[0])) {
|
||||
if (!class_exists($callback[0])) {
|
||||
throw new Exception('Undefined callback class.');
|
||||
}
|
||||
$callback[0] = Snowflake::createObject($callback[0]);
|
||||
$callback[0] = di($callback[0]);
|
||||
}
|
||||
if (static::exists($name, $callback)) {
|
||||
return;
|
||||
@@ -130,15 +129,10 @@ class Event extends BaseObject
|
||||
|
||||
/**
|
||||
* @param $name
|
||||
* @return bool
|
||||
*/
|
||||
public static function offName($name): bool
|
||||
public static function offName($name): void
|
||||
{
|
||||
if (!static::exists($name)) {
|
||||
return true;
|
||||
}
|
||||
unset(static::$_events[$name]);
|
||||
return static::exists($name);
|
||||
}
|
||||
|
||||
|
||||
@@ -147,14 +141,11 @@ class Event extends BaseObject
|
||||
* @param null $callback
|
||||
* @return bool
|
||||
*/
|
||||
public static function exists($name, $callback = null): bool
|
||||
public static function exists($name, $callback): bool
|
||||
{
|
||||
if (!isset(static::$_events[$name])) {
|
||||
if ($callback instanceof \Closure || !isset(static::$_events[$name])) {
|
||||
return false;
|
||||
}
|
||||
if ($callback === null) {
|
||||
return true;
|
||||
}
|
||||
foreach (static::$_events[$name] as $event) {
|
||||
[$handler, $parameter] = $event;
|
||||
if ($handler === $callback) {
|
||||
@@ -175,7 +166,6 @@ class Event extends BaseObject
|
||||
if (!static::exists($name, $handler)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (empty($handler)) {
|
||||
return static::$_events[$name];
|
||||
}
|
||||
@@ -216,11 +206,14 @@ class Event extends BaseObject
|
||||
*/
|
||||
public static function trigger($name, $parameter = null, bool $is_remove = false): bool
|
||||
{
|
||||
foreach ((static::$_events[$name] ?? []) as $event) {
|
||||
foreach ((static::$_events[$name] ?? []) as $key => $event) {
|
||||
static::execute($event, $parameter);
|
||||
if ($event instanceof \Closure) {
|
||||
unset(static::$_events[$name][$key]);
|
||||
}
|
||||
}
|
||||
if ($is_remove) {
|
||||
static::offName($name);
|
||||
unset(static::$_events[$name]);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -229,45 +222,19 @@ class Event extends BaseObject
|
||||
/**
|
||||
* @param $event
|
||||
* @param $parameter
|
||||
* @return bool
|
||||
* @return void
|
||||
* @throws Exception
|
||||
*/
|
||||
private static function execute($event, $parameter): bool
|
||||
private static function execute($event, $parameter): void
|
||||
{
|
||||
try {
|
||||
$meta = static::mergeParams($event[1], $parameter);
|
||||
if (call_user_func($event[0], ...$meta) === false) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
call_user_func($event[0], ...$parameter);
|
||||
} catch (\Throwable $throwable) {
|
||||
return logger()->addError($throwable, 'throwable');
|
||||
logger()->addError($throwable, 'throwable');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $defaultParameter
|
||||
* @param array $parameter
|
||||
* @return array
|
||||
*/
|
||||
private static function mergeParams($defaultParameter, array $parameter = []): array
|
||||
{
|
||||
if (empty($defaultParameter)) {
|
||||
$defaultParameter = $parameter;
|
||||
} else {
|
||||
if (!is_array($parameter)) {
|
||||
$parameter = [];
|
||||
}
|
||||
foreach ($parameter as $key => $value) {
|
||||
$defaultParameter[] = $value;
|
||||
}
|
||||
}
|
||||
if (!is_array($defaultParameter)) {
|
||||
$defaultParameter = [$defaultParameter];
|
||||
}
|
||||
return $defaultParameter;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -2,31 +2,36 @@
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
class EventDispatch
|
||||
use Annotation\Inject;
|
||||
use Snowflake\Abstracts\BaseObject;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
class EventDispatch extends BaseObject
|
||||
{
|
||||
|
||||
private EventListener $eventListener;
|
||||
#[Inject(EventProvider::class)]
|
||||
public EventProvider $eventProvider;
|
||||
|
||||
|
||||
/**
|
||||
* @param $event
|
||||
* @param array $params
|
||||
* @param object $triggerEvent
|
||||
* @return object
|
||||
*/
|
||||
public function emit($event, array $params = [])
|
||||
public function dispatch(object $triggerEvent): object
|
||||
{
|
||||
$events = $this->eventListener->getEventListeners($event);
|
||||
if (empty($events)) {
|
||||
return;
|
||||
}
|
||||
while ($events->valid()) {
|
||||
/** @var EventDispatchInterface $interface */
|
||||
$interface = $events->current();
|
||||
$interface->onHandler();
|
||||
if ($interface->stopPagination()) {
|
||||
$lists = $this->eventProvider->getListenersForEvent($triggerEvent);
|
||||
foreach ($lists as $listener) {
|
||||
/** @var Struct $list */
|
||||
$listener($triggerEvent);
|
||||
if ($triggerEvent instanceof StoppableEventInterface && $triggerEvent->isPropagationStopped()) {
|
||||
break;
|
||||
}
|
||||
$events->next();
|
||||
}
|
||||
return $triggerEvent;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -1,18 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
interface EventDispatchInterface
|
||||
{
|
||||
|
||||
public function getZOrder(): int;
|
||||
|
||||
public function onHandler(): void;
|
||||
|
||||
public function stopPagination(): bool;
|
||||
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
interface EventInterface
|
||||
{
|
||||
|
||||
|
||||
public function process(): void;
|
||||
|
||||
|
||||
}
|
||||
@@ -1,37 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
use SplPriorityQueue;
|
||||
|
||||
class EventListener
|
||||
{
|
||||
|
||||
/** @var SplPriorityQueue[] */
|
||||
private array $_events = [];
|
||||
|
||||
|
||||
/**
|
||||
* @param $event
|
||||
* @param EventDispatchInterface $handler
|
||||
*/
|
||||
public function on($event, EventDispatchInterface $handler)
|
||||
{
|
||||
if (!isset($this->_events[$event])) {
|
||||
$this->_events[$event] = new SplPriorityQueue();
|
||||
}
|
||||
$this->_events[$event]->insert($handler, $handler->getZOrder());
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param $event
|
||||
* @return SplPriorityQueue|null
|
||||
*/
|
||||
public function getEventListeners($event): ?SplPriorityQueue
|
||||
{
|
||||
return $this->_events[$event] ?? null;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
<?php
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
class EventProvider implements EventProviders
|
||||
{
|
||||
|
||||
/** @var Struct[] */
|
||||
private array $_listeners = [];
|
||||
|
||||
|
||||
/**
|
||||
* @param object $event
|
||||
* @return iterable
|
||||
*/
|
||||
public function getListenersForEvent(object $event): iterable
|
||||
{
|
||||
$queue = new \SplPriorityQueue();
|
||||
// TODO: Implement getListenersForEvent() method.
|
||||
foreach ($this->_listeners as $listener) {
|
||||
if (!($event instanceof $listener->event)) {
|
||||
continue;
|
||||
}
|
||||
$queue->insert($listener, $listener->priority);
|
||||
}
|
||||
return $queue;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @param string $event
|
||||
* @param callable $handler
|
||||
* @param int $zOrder
|
||||
*/
|
||||
public function on(string $event, callable $handler, int $zOrder = 1)
|
||||
{
|
||||
$this->_listeners[$event][] = new Struct($event, $handler, $zOrder);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -2,7 +2,21 @@
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
class EventProviders
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
interface EventProviders
|
||||
{
|
||||
|
||||
|
||||
/**
|
||||
* @param object $event
|
||||
* An event for which to return the relevant listeners.
|
||||
* @return iterable<callable>
|
||||
* An iterable (array, iterator, or generator) of callables. Each
|
||||
* callable MUST be type-compatible with $event.
|
||||
*/
|
||||
public function getListenersForEvent(object $event): iterable;
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,24 @@
|
||||
<?php
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
interface StoppableEventInterface
|
||||
{
|
||||
|
||||
|
||||
/**
|
||||
* Is propagation stopped?
|
||||
*
|
||||
* This will typically only be used by the Dispatcher to determine if the
|
||||
* previous listener halted propagation.
|
||||
*
|
||||
* @return bool
|
||||
* True if the Event is complete and no further listeners should be called.
|
||||
* False to continue calling listeners.
|
||||
*/
|
||||
public function isPropagationStopped() : bool;
|
||||
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Snowflake\Events;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
class Struct
|
||||
{
|
||||
|
||||
public string $event;
|
||||
|
||||
public \Closure $listener;
|
||||
|
||||
public int $priority;
|
||||
|
||||
public function __construct(string $event, callable $listener, int $priority)
|
||||
{
|
||||
$this->event = $event;
|
||||
$this->listener = $listener;
|
||||
$this->priority = $priority;
|
||||
}
|
||||
}
|
||||
@@ -182,7 +182,7 @@ class Connection extends Component
|
||||
return;
|
||||
}
|
||||
if ($client->inTransaction()) {
|
||||
$client->commit();
|
||||
return;
|
||||
}
|
||||
$this->getPool()->push($coroutineName, $client);
|
||||
Context::remove($coroutineName);
|
||||
|
||||
Reference in New Issue
Block a user