Coroutine.php 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. <?php
  2. declare(strict_types=1);
  3. /**
  4. * This file is part of Hyperf.
  5. *
  6. * @link https://www.hyperf.io
  7. * @document https://hyperf.wiki
  8. * @contact group@hyperf.io
  9. * @license https://github.com/hyperf/hyperf/blob/master/LICENSE
  10. */
  11. namespace Hyperf\Engine;
  12. use Hyperf\Engine\Contract\CoroutineInterface;
  13. use Hyperf\Engine\Exception\CoroutineDestroyedException;
  14. use Hyperf\Engine\Exception\RunningInNonCoroutineException;
  15. use Hyperf\Engine\Exception\RuntimeException;
  16. use Swoole\Coroutine as SwooleCo;
  17. class Coroutine implements CoroutineInterface
  18. {
  19. /**
  20. * @var callable
  21. */
  22. private $callable;
  23. /**
  24. * @var int
  25. */
  26. private $id;
  27. public function __construct(callable $callable)
  28. {
  29. $this->callable = $callable;
  30. }
  31. public static function create(callable $callable, ...$data)
  32. {
  33. $coroutine = new static($callable);
  34. $coroutine->execute(...$data);
  35. return $coroutine;
  36. }
  37. public function execute(...$data)
  38. {
  39. $this->id = SwooleCo::create($this->callable, ...$data);
  40. return $this;
  41. }
  42. public function getId()
  43. {
  44. if (is_null($this->id)) {
  45. throw new RuntimeException('Coroutine was not be executed.');
  46. }
  47. return $this->id;
  48. }
  49. public static function id()
  50. {
  51. return SwooleCo::getCid();
  52. }
  53. public static function pid(?int $id = null)
  54. {
  55. if ($id) {
  56. $cid = SwooleCo::getPcid($id);
  57. if ($cid === false) {
  58. throw new CoroutineDestroyedException(sprintf('Coroutine #%d has been destroyed.', $id));
  59. }
  60. } else {
  61. $cid = SwooleCo::getPcid();
  62. }
  63. if ($cid === false) {
  64. throw new RunningInNonCoroutineException('Non-Coroutine environment don\'t has parent coroutine id.');
  65. }
  66. return max(0, $cid);
  67. }
  68. public static function set(array $config)
  69. {
  70. SwooleCo::set($config);
  71. }
  72. /**
  73. * @return null|\ArrayObject
  74. */
  75. public static function getContextFor(?int $id = null)
  76. {
  77. if ($id === null) {
  78. return SwooleCo::getContext();
  79. }
  80. return SwooleCo::getContext($id);
  81. }
  82. public static function defer(callable $callable)
  83. {
  84. SwooleCo::defer($callable);
  85. }
  86. }