Skip to content

Commit

Permalink
refactor(any): IOC container can manipulate data for a specified swoo…
Browse files Browse the repository at this point in the history
…le coroutine id.
  • Loading branch information
doyouhaobaby committed Jul 27, 2020
1 parent b58f613 commit 6c56b83
Show file tree
Hide file tree
Showing 9 changed files with 87 additions and 56 deletions.
3 changes: 2 additions & 1 deletion src/Leevel/Database/Manager.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
namespace Leevel\Database;

use InvalidArgumentException;
use Leevel\Di\IContainer;
use Leevel\Event\IDispatch;
use Leevel\Manager\Manager as Managers;
use Leevel\Protocol\Pool\IConnection;
Expand Down Expand Up @@ -180,7 +181,7 @@ class Manager extends Managers
*/
public function setTransactionConnection(IConnection $connection): void
{
$this->container->instance(self::TRANSACTION_SERVICE, $connection, true);
$this->container->instance(self::TRANSACTION_SERVICE, $connection, IContainer::DEFAULT_COROUTINE_ID);
}

/**
Expand Down
57 changes: 29 additions & 28 deletions src/Leevel/Di/Container.php
Original file line number Diff line number Diff line change
Expand Up @@ -224,7 +224,7 @@ public function bind($name, $service = null, bool $share = false, bool $coroutin
*
* @return \Leevel\Di\IContainer
*/
public function instance($name, $service = null, bool $coroutine = false): IContainer
public function instance($name, $service = null, int $cid = self::NOT_COROUTINE_ID): IContainer
{
if (is_array($name)) {
list($name, $alias) = $this->parseAlias($name);
Expand All @@ -235,12 +235,13 @@ public function instance($name, $service = null, bool $coroutine = false): ICont
$service = $name;
}

if ($coroutine) {
if ($cid > self::NOT_COROUTINE_ID) {
$this->serviceCoroutine($name);
}

if ($this->coroutineContext($service)) {
$this->coroutineInstances[$this->coroutineCid()][$name] = $service;
if ($this->inCroutineContext($service)) {
$cid = $this->getCoroutineId($cid > self::NOT_COROUTINE_ID ? $cid : self::DEFAULT_COROUTINE_ID);
$this->coroutineInstances[$cid][$name] = $service;
} else {
$this->instances[$name] = $service;
}
Expand Down Expand Up @@ -293,7 +294,7 @@ public function alias($alias, $value = null): IContainer
*
* @return mixed
*/
public function make(string $name, array $args = [])
public function make(string $name, array $args = [], int $cid = self::DEFAULT_COROUTINE_ID)
{
// 别名
$name = $this->getAlias($name);
Expand All @@ -302,8 +303,8 @@ public function make(string $name, array $args = [])
}

// 存在直接返回
if ($this->existsCoroutine($name)) {
return $this->coroutineInstances[$this->coroutineCid()][$name];
if ($this->existsCoroutine($name, $cid)) {
return $this->coroutineInstances[$this->getCoroutineId($cid)][$name];
}

if (isset($this->instances[$name])) {
Expand All @@ -328,8 +329,8 @@ public function make(string $name, array $args = [])

// 单一实例
if (in_array($name, $this->singletons, true)) {
if ($this->coroutineContext($instance)) {
return $this->coroutineInstances[$this->coroutineCid()][$name] = $instance;
if ($this->inCroutineContext($instance)) {
return $this->coroutineInstances[$this->getCoroutineId($cid)][$name] = $instance;
}

return $this->instances[$name] = $instance;
Expand Down Expand Up @@ -384,7 +385,7 @@ public function call($callback, array $args = [])
/**
* 删除服务和实例.
*/
public function remove(string $name): void
public function remove(string $name, int $cid = self::DEFAULT_COROUTINE_ID): void
{
$name = $this->normalize($name);
foreach (['services', 'instances', 'singletons'] as $item) {
Expand All @@ -393,8 +394,8 @@ public function remove(string $name): void
}
}

if ($this->existsCoroutine($name)) {
unset($this->coroutineInstances[$this->coroutineCid()][$name]);
if ($this->existsCoroutine($name, $cid)) {
unset($this->coroutineInstances[$this->getCoroutineId($cid)][$name]);
}

foreach ($this->alias as $alias => $service) {
Expand Down Expand Up @@ -541,29 +542,31 @@ public function getCoroutine(): ?ICoroutine
/**
* 协程服务或者实例是否存在.
*/
public function existsCoroutine(string $name): bool
public function existsCoroutine(string $name, int $cid = self::DEFAULT_COROUTINE_ID): bool
{
return false !== $this->coroutineCid() &&
isset($this->coroutineInstances[$this->coroutineCid()], $this->coroutineInstances[$this->coroutineCid()][$name]);
$cid = $this->getCoroutineId($cid);

return isset($this->coroutineInstances[$cid], $this->coroutineInstances[$cid][$name]);
}

/**
* 删除协程上下文服务和实例.
*/
public function removeCoroutine(?string $name = null): void
public function removeCoroutine(?string $name = null, int $cid = self::DEFAULT_COROUTINE_ID): void
{
if (!$this->coroutine) {
return;
}

$cid = $this->getCoroutineId($cid);
if (null === $name) {
if (isset($this->coroutineInstances[$this->coroutineCid()])) {
unset($this->coroutineInstances[$this->coroutineCid()]);
if (isset($this->coroutineInstances[$cid])) {
unset($this->coroutineInstances[$cid]);
}
} else {
$name = $this->normalize($name);
if ($this->existsCoroutine($name)) {
unset($this->coroutineInstances[$this->coroutineCid()][$name]);
if ($this->existsCoroutine($name, $cid)) {
unset($this->coroutineInstances[$cid][$name]);
}
}
}
Expand Down Expand Up @@ -664,7 +667,7 @@ protected function getAlias(string $name): string
*
* @param mixed $instance
*/
protected function coroutineContext($instance): bool
protected function inCroutineContext($instance): bool
{
if (!$this->coroutine) {
return false;
Expand All @@ -674,21 +677,19 @@ protected function coroutineContext($instance): bool
$instance = get_class($instance);
}

return $this->coroutine->context($instance);
return $this->coroutine->inContext($instance);
}

/**
* 当前协程 ID.
*
* @return false|int
*/
protected function coroutineCid()
protected function getCoroutineId(int $cid = self::DEFAULT_COROUTINE_ID): int
{
if (!$this->coroutine) {
return false;
if (self::NOT_COROUTINE_ID === $cid || !$this->coroutine) {
return self::NOT_COROUTINE_ID;
}

return $this->coroutine->cid();
return $cid ?: $this->coroutine->cid();
}

/**
Expand Down
24 changes: 19 additions & 5 deletions src/Leevel/Di/IContainer.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,20 @@
*/
interface IContainer
{
/**
* 默认协程 ID 标识.
*
* @var int
*/
const DEFAULT_COROUTINE_ID = 0;

/**
* 非协程 ID 标识.
*
* @var int
*/
const NOT_COROUTINE_ID = -1;

/**
* 注册到容器.
*
Expand All @@ -43,7 +57,7 @@ public function bind($name, $service = null, bool $share = false, bool $coroutin
*
* @return \Leevel\Di\IContainer
*/
public function instance($name, $service, bool $coroutine = false): self;
public function instance($name, $service = null, int $cid = self::NOT_COROUTINE_ID): self;

/**
* 注册单一实例.
Expand All @@ -70,7 +84,7 @@ public function alias($alias, $value = null): self;
*
* @return mixed
*/
public function make(string $name, array $args = []);
public function make(string $name, array $args = [], int $cid = self::DEFAULT_COROUTINE_ID);

/**
* 回调自动依赖注入.
Expand All @@ -86,7 +100,7 @@ public function call($callback, array $args = []);
/**
* 删除服务和实例.
*/
public function remove(string $name): void;
public function remove(string $name, int $cid = self::DEFAULT_COROUTINE_ID): void;

/**
* 服务或者实例是否存在.
Expand Down Expand Up @@ -148,12 +162,12 @@ public function getCoroutine(): ?ICoroutine;
/**
* 协程服务或者实例是否存在.
*/
public function existsCoroutine(string $name): bool;
public function existsCoroutine(string $name, int $cid = self::DEFAULT_COROUTINE_ID): bool;

/**
* 删除协程上下文服务和实例.
*/
public function removeCoroutine(?string $name = null): void;
public function removeCoroutine(?string $name = null, int $cid = self::DEFAULT_COROUTINE_ID): void;

/**
* 设置服务到协程上下文.
Expand Down
9 changes: 8 additions & 1 deletion src/Leevel/Di/ICoroutine.php
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ interface ICoroutine
/**
* 是否处于协程上下文.
*/
public function context(string $key): bool;
public function inContext(string $key): bool;

/**
* 添加协程上下文键值.
Expand All @@ -37,6 +37,13 @@ public function context(string $key): bool;
*/
public function addContext(...$keys): void;

/**
* 删除协程上下文键值.
*
* @param array ...$keys
*/
public function removeContext(...$keys): void;

/**
* 当前协程 ID.
*
Expand Down
20 changes: 10 additions & 10 deletions src/Leevel/Kernel/Proxy/App.php
Original file line number Diff line number Diff line change
Expand Up @@ -418,9 +418,9 @@ public static function bind($name, $service = null, bool $share = false, bool $c
* @param mixed $name
* @param mixed $service
*/
public static function instance($name, $service, bool $coroutine = false): IBaseContainer
public static function instance($name, $service, int $cid = IBaseContainer::NOT_COROUTINE_ID): IBaseContainer
{
return self::proxyContainer()->instance($name, $service, $coroutine);
return self::proxyContainer()->instance($name, $service, $cid);
}

/**
Expand Down Expand Up @@ -450,9 +450,9 @@ public static function alias($alias, $value = null): IBaseContainer
*
* @return mixed
*/
public static function make(string $name, array $args = [])
public static function make(string $name, array $args = [], int $cid = IBaseContainer::DEFAULT_COROUTINE_ID)
{
return self::proxyContainer()->make($name, $args);
return self::proxyContainer()->make($name, $args, $cid);
}

/**
Expand All @@ -472,9 +472,9 @@ public static function call($callback, array $args = [])
/**
* 删除服务和实例.
*/
public static function remove(string $name): void
public static function remove(string $name, int $cid = IBaseContainer::DEFAULT_COROUTINE_ID): void
{
self::proxyContainer()->remove($name);
self::proxyContainer()->remove($name, $cid);
}

/**
Expand Down Expand Up @@ -556,17 +556,17 @@ public static function getCoroutine(): ?ICoroutine
/**
* 协程服务或者实例是否存在.
*/
public static function existsCoroutine(string $name): bool
public static function existsCoroutine(string $name, int $cid = IBaseContainer::DEFAULT_COROUTINE_ID): bool
{
return self::proxyContainer()->existsCoroutine($name);
return self::proxyContainer()->existsCoroutine($name, $cid);
}

/**
* 删除协程上下文服务和实例.
*/
public static function removeCoroutine(?string $name = null): void
public static function removeCoroutine(?string $name = null, int $cid = IBaseContainer::DEFAULT_COROUTINE_ID): void
{
self::proxyContainer()->removeCoroutine($name);
self::proxyContainer()->removeCoroutine($name, $cid);
}

/**
Expand Down
12 changes: 11 additions & 1 deletion src/Leevel/Protocol/Coroutine.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ class Coroutine implements ICoroutine
/**
* 是否处于协程上下文.
*/
public function context(string $key): bool
public function inContext(string $key): bool
{
if (in_array($key, $this->context, true)) {
return true;
Expand Down Expand Up @@ -75,6 +75,16 @@ public function addContext(...$keys): void
$this->context = array_merge($this->context, $keys);
}

/**
* 删除协程上下文键值.
*
* @param array ...$keys
*/
public function removeContext(...$keys): void
{
$this->context = array_values(array_diff($this->context, $keys));
}

/**
* 当前协程 ID.
*
Expand Down
2 changes: 1 addition & 1 deletion src/Leevel/Protocol/HttpServer.php
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,7 @@ public function onRequest(SwooleHttpRequest $swooleRequest, SwooleHttpResponse $
return;
}

$this->clearRootCoroutine();
$request = $this->normalizeRequest($swooleRequest);
$response = $this->dispatchRouter($request);
$swooleResponse = $this->normalizeResponse($response, $swooleResponse);
Expand Down Expand Up @@ -145,7 +146,6 @@ protected function dispatchRouter(Request $request): Response
$kernel = $this->container->make(IKernel::class);
$response = $kernel->handle($request);
$kernel->terminate($request, $response);
$this->removeCoroutine();

return $response;
}
Expand Down
14 changes: 6 additions & 8 deletions src/Leevel/Protocol/Server.php
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,7 @@ abstract class Server
public function __construct(IContainer $container, ICoroutine $coroutine, array $option = [])
{
$this->validSwoole();
$container->remove('request');
$container->setCoroutine($coroutine);
$this->container = $container;
$this->option = array_merge($this->option, $option);
Expand Down Expand Up @@ -381,11 +382,13 @@ protected function parseTask(string $task): array
}

/**
* 清理协程上下文数据.
* 清理根协程上下文数据.
*/
protected function removeCoroutine(): void
protected function clearRootCoroutine(): void
{
$this->container->removeCoroutine();
/** @var \Leevel\Di\ICoroutine $coroutine */
$coroutine = $this->container->make(ICoroutine::class);
\defer(fn () => $this->container->removeCoroutine(null, $coroutine->cid()));
}

/**
Expand Down Expand Up @@ -420,15 +423,10 @@ protected function createSwooleServer(): void
protected function initSwooleServer(): void
{
$this->server->set($this->option);

foreach ($this->option['processes'] as $process) {
$this->process($process);
}

$this->container->instance('server', $this->server);

// 删除容器中注册为 -1 的数据
$this->removeCoroutine();
}

/**
Expand Down
Loading

0 comments on commit 6c56b83

Please sign in to comment.