Connection.php 2.5 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  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\Pool;
  12. use Hyperf\Contract\ConnectionInterface;
  13. use Hyperf\Contract\PoolInterface;
  14. use Hyperf\Contract\StdoutLoggerInterface;
  15. use Hyperf\Pool\Event\ReleaseConnection;
  16. use Psr\Container\ContainerInterface;
  17. use Psr\EventDispatcher\EventDispatcherInterface;
  18. use Throwable;
  19. abstract class Connection implements ConnectionInterface
  20. {
  21. protected float $lastUseTime = 0.0;
  22. protected float $lastReleaseTime = 0.0;
  23. private ?EventDispatcherInterface $dispatcher = null;
  24. private ?StdoutLoggerInterface $logger = null;
  25. public function __construct(protected ContainerInterface $container, protected PoolInterface $pool)
  26. {
  27. if ($this->container->has(EventDispatcherInterface::class)) {
  28. $this->dispatcher = $this->container->get(EventDispatcherInterface::class);
  29. }
  30. if ($this->container->has(StdoutLoggerInterface::class)) {
  31. $this->logger = $this->container->get(StdoutLoggerInterface::class);
  32. }
  33. }
  34. public function release(): void
  35. {
  36. try {
  37. $this->lastReleaseTime = microtime(true);
  38. $events = $this->pool->getOption()->getEvents();
  39. if (in_array(ReleaseConnection::class, $events, true)) {
  40. $this->dispatcher?->dispatch(new ReleaseConnection($this));
  41. }
  42. } catch (Throwable $exception) {
  43. $this->logger?->error((string) $exception);
  44. } finally {
  45. $this->pool->release($this);
  46. }
  47. }
  48. public function getConnection()
  49. {
  50. try {
  51. return $this->getActiveConnection();
  52. } catch (Throwable $exception) {
  53. $this->logger?->warning('Get connection failed, try again. ' . $exception);
  54. return $this->getActiveConnection();
  55. }
  56. }
  57. public function check(): bool
  58. {
  59. $maxIdleTime = $this->pool->getOption()->getMaxIdleTime();
  60. $now = microtime(true);
  61. if ($now > $maxIdleTime + $this->lastUseTime) {
  62. return false;
  63. }
  64. $this->lastUseTime = $now;
  65. return true;
  66. }
  67. public function getLastUseTime(): float
  68. {
  69. return $this->lastUseTime;
  70. }
  71. public function getLastReleaseTime(): float
  72. {
  73. return $this->lastReleaseTime;
  74. }
  75. abstract public function getActiveConnection();
  76. }