hyperf / jet
Jet是一个统一模型RPC客户端,内置JSON RPC协议,可在所有PHP环境中运行,包括PHP-FPM和Swoole/Hyperf环境。
Requires
- php: >=8.0
- hyperf/rpc: ^3.0.19
- hyperf/stringable: ^3.0
Requires (Dev)
- friendsofphp/php-cs-fixer: ^3.0
- guzzlehttp/guzzle: ^6.3|^7.0
- hyperf/collection: ^3.0
- hyperf/consul: ^3.0
- hyperf/load-balancer: ^3.0
- mockery/mockery: ^1.0
- phpstan/phpstan: ^1.0
- phpunit/phpunit: ^9.0
Suggests
- guzzlehttp/guzzle: Required to use GuzzleHttpTransporter for rpc client.(^6.3|^7.0)
- hyperf/collection: Required if use Collection and Arr for node selector.(^3.0)
- hyperf/consul: Required if use Consul services.(^3.0)
- hyperf/load-balancer: Use load balancer for rpc client.(^3.0)
- hyperf/support: Required if use retry function for stream socket transporter.(^3.0)
README
英文 | 中文
Jet,由Hyperf提供
Jet是一个统一模型RPC客户端,内置JSONRPC协议,可在所有PHP环境中运行,包括PHP-FPM和Swoole/Hyperf环境。
未来还将内置gRPC和Tars协议。
安装
composer require hyperf/jet
快速开始
注册协议
注册协议不是必需的,但使用ProtocolManager可以更方便地管理协议。
您可以通过Hyperf\Jet\ProtocolManager
注册任何协议,每个协议基本上包括传输器、打包器、数据格式化器和路径生成器,您可以注册一个JSONRPC协议,如下所示
<?php use Hyperf\Jet\DataFormatter\DataFormatter; use Hyperf\Jet\Packer\JsonEofPacker; use Hyperf\Jet\PathGenerator\PathGenerator; use Hyperf\Jet\ProtocolManager; use Hyperf\Jet\Transporter\StreamSocketTransporter; ProtocolManager::register($protocol = 'jsonrpc', [ ProtocolManager::TRANSPORTER => new StreamSocketTransporter(), ProtocolManager::PACKER => new JsonEofPacker(), ProtocolManager::PATH_GENERATOR => new PathGenerator(), ProtocolManager::DATA_FORMATTER => new DataFormatter(), ]);
如果您使用consul,可以注册一个JSONRPC协议,如下所示
<?php use Hyperf\Jet\DataFormatter\DataFormatter; use Hyperf\Jet\Packer\JsonEofPacker; use Hyperf\Jet\PathGenerator\PathGenerator; use Hyperf\Jet\ProtocolManager; use Hyperf\Jet\Transporter\ConsulTransporter; // If you use consul service, you should register ProtocolManager::NODE_SELECTOR. ProtocolManager::register($protocol = 'consul', [ ProtocolManager::TRANSPORTER => new StreamSocketTransporter(), ProtocolManager::PACKER => new JsonEofPacker(), ProtocolManager::PATH_GENERATOR => new PathGenerator(), ProtocolManager::DATA_FORMATTER => new DataFormatter(), ProtocolManager::NODE_SELECTOR => new NodeSelector($this->host, $this->port, $config), ]);
注册服务
注册服务不是必需的,但使用ServiceManager可以更方便地管理服务。
在您将协议注册到Hyperf\Jet\ProtocolManager
之后,您可以通过Hyperf\Jet\ServiceManager
将协议与服务绑定,如下所示
<?php use Hyperf\Jet\ServiceManager; // Bind CalculatorService with jsonrpc protocol, and set the static nodes info. ServiceManager::register($service = 'CalculatorService', $protocol = 'jsonrpc', [ ServiceManager::NODES => [ [$host = '127.0.0.1', $port = 9503], ], ]);
调用RPC方法
通过ClientFactory调用
在您注册了协议和服务之后,您可以通过Hyperf/Jet/ClientFactory
获取服务客户端,如下所示
<?php use Hyperf\Jet\ClientFactory; $clientFactory = new ClientFactory(); $client = $clientFactory->create($service = 'CalculatorService', $protocol = 'jsonrpc');
当您有了客户端对象后,您可以通过对象调用任何远程方法,如下所示
// Call the remote method `add` with arguments `1` and `2`. // The $result is the result of the remote method. $result = $client->add(1, 2);
如果您调用一个不存在的远程方法,客户端将抛出Hyperf\Jet\Exception\ServerException
异常。
通过自定义客户端调用
您还可以创建一个扩展Hyperf\Jet\AbstractClient
的自定义客户端类,通过客户端对象调用远程方法。
例如,您想定义一个使用jsonrpc
协议的CalculatorService
RPC客户端,您首先可以创建一个CalculatorService
类,如下所示
<?php use Hyperf\Jet\AbstractClient; use Hyperf\Jet\Packer\JsonEofPacker; use Hyperf\Jet\Transporter\StreamSocketTransporter; use Hyperf\Rpc\Contract\DataFormatterInterface; use Hyperf\Rpc\Contract\PackerInterface; use Hyperf\Rpc\Contract\PathGeneratorInterface; use Hyperf\Rpc\Contract\TransporterInterface; /** * @method int add(int $a, int $b); */ class CalculatorService extends AbstractClient { // Define `CalculatorService` as the default value of $service. public function __construct( string $service = 'CalculatorService', TransporterInterface $transporter = null, PackerInterface $packer = null, ?DataFormatterInterface $dataFormatter = null, ?PathGeneratorInterface $pathGenerator = null ) { // Specific the transporter here, you could also retrieve the transporter from ProtocolManager or passing by constructor. $transporter = new StreamSocketTransporter('127.0.0.1', 9503); // Specific the packer here, you could also retrieve the packer from ProtocolManager or passing by constructor. $packer = new JsonEofPacker(); parent::__construct($service, $transporter, $packer, $dataFormatter, $pathGenerator); } }
如果使用Consul服务,您可以使用以下方式。
<?php use Hyperf\Jet\AbstractClient; use Hyperf\Jet\Packer\JsonEofPacker; use Hyperf\Jet\Transporter\StreamSocketTransporter; use Hyperf\Rpc\Contract\DataFormatterInterface; use Hyperf\Rpc\Contract\PackerInterface; use Hyperf\Rpc\Contract\PathGeneratorInterface; use Hyperf\Rpc\Contract\TransporterInterface; use Hyperf\Jet\NodeSelector\NodeSelector; /** * @method int add(int $a, int $b); */ class CalculatorService extends AbstractClient { // Define `CalculatorService` as the default value of $service. public function __construct( string $service = 'CalculatorService', TransporterInterface $transporter = null, PackerInterface $packer = null, ?DataFormatterInterface $dataFormatter = null, ?PathGeneratorInterface $pathGenerator = null ) { // Specific the transporter here, you could also retrieve the transporter from ProtocolManager or passing by constructor. $transporter = new StreamSocketTransporter(); $nodeSelector = new NodeSelector('127.0.0.1', 8500, $config); [$transporter->host, $transporter->port] = $nodeSelector->selectRandomNode($service, 'jsonrpc'); // Specific the packer here, you could also retrieve the packer from ProtocolManager or passing by constructor. $packer = new JsonEofPacker(); parent::__construct($service, $transporter, $packer, $dataFormatter, $pathGenerator); } }
现在,您可以使用这个类直接调用远程方法,如下所示
// Call the remote method `add` with arguments `1` and `2`. // The $result is the result of the remote method. $client = new CalculatorService(); $result = $client->add(1, 2);