yoanm / jsonrpc-server-sdk
将 JSON-RPC 请求字符串转换为 JSON-RPC 响应字符串的服务器 SDK
Requires
- php: ^8.0
- ext-json: *
Requires (Dev)
- behat/behat: ^3.9.0
- coduo/php-matcher: ^6.0
- dvdoug/behat-code-coverage: ^5.0
- phpspec/prophecy: ^1.15
- phpspec/prophecy-phpunit: ^2.0
- phpunit/phpunit: ^9.6
- squizlabs/php_codesniffer: ^3.5
- yoanm/jsonrpc-server-doc-sdk: ^0.3 || ^1.0
- yoanm/php-unit-extended: ^2.0
Suggests
- yoanm/jsonrpc-params-symfony-validator-sdk: Compatible params validator
- yoanm/jsonrpc-server-doc-sdk: Create documentation for your server
- yoanm/symfony-jsonrpc-http-server: JSON-RPC HTTP Symfony server Bundle
README
简单的服务器 SDK,用于将 JSON-RPC 请求字符串转换为 JSON-RPC 响应字符串。
有关自动依赖注入,请参阅 yoanm/symfony-jsonrpc-http-server。
有关参数验证,请参阅 yoanm/jsonrpc-params-symfony-validator-sdk。
有关文档生成,请参阅 yoanm/jsonrpc-server-doc-sdk。
如何使用
SDK 仅需要两样东西
- 方法解析器:必须实现 JsonRpcMethodResolverInterface,解析逻辑由您自己决定。
- 方法:实现 JsonRpcMethodInterface 的 JsonRpc 方法
SDK 可选提供
- 事件调度
- 参数验证
简单示例
JSON-RPC 方法
use Yoanm\JsonRpcServer\Domain\JsonRpcMethodInterface; class DummyMethod implements JsonRpcMethodInterface { /** * {@inheritdoc} */ public function apply(array $paramList = null) { // Handle the request ... // Then return a result return [ 'status' => 'done', ]; // Or return null; // Or return 12345; } }
数组方法解析器(简单示例)
您可以使用 behat 测试中使用的 或此 Psr11 方法解析器 作为示例。
use Yoanm\JsonRpcServer\Domain\JsonRpcMethodInterface; use Yoanm\JsonRpcServer\Domain\JsonRpcMethodResolverInterface; class ArrayMethodResolver implements JsonRpcMethodResolverInterface { /** @var JsonRpcMethodInterface[] */ private $methodList = []; /** * {@inheritdoc} */ public function resolve(string $methodName) : ?JsonRpcMethodInterface { return array_key_exists($methodName, $this->methodList) ? $this->methodList[$methodName] : null ; } /** * @param JsonRpcMethodInterface $method * @param string $methodName */ public function addMethod(JsonRpcMethodInterface $method, string $methodName) { $this->methodList[$methodName] = $method; } }
然后将您的 方法添加到解析器中并创建端点
use Yoanm\JsonRpcServer\App\Creator\ResponseCreator; use Yoanm\JsonRpcServer\App\Handler\ExceptionHandler; use Yoanm\JsonRpcServer\App\Handler\JsonRpcRequestHandler; use Yoanm\JsonRpcServer\App\Serialization\JsonRpcCallDenormalizer; use Yoanm\JsonRpcServer\App\Serialization\JsonRpcCallResponseNormalizer; use Yoanm\JsonRpcServer\App\Serialization\JsonRpcCallSerializer; use Yoanm\JsonRpcServer\App\Serialization\JsonRpcRequestDenormalizer; use Yoanm\JsonRpcServer\App\Serialization\JsonRpcResponseErrorNormalizer; use Yoanm\JsonRpcServer\App\Serialization\JsonRpcResponseNormalizer; use Yoanm\JsonRpcServer\Infra\Endpoint\JsonRpcEndpoint; $resolver = new ArrayMethodResolver(); $resolver->addMethod('dummy-method', new DummyMethod()); $jsonRpcSerializer = new JsonRpcCallSerializer( new JsonRpcCallDenormalizer( new JsonRpcRequestDenormalizer() ), new JsonRpcCallResponseNormalizer( new JsonRpcResponseNormalizer() // Or `new JsonRpcResponseNormalizer(new JsonRpcResponseErrorNormalizer())` for debug purpose // To also dump arguments, be sure 'zend.exception_ignore_args' ini option is not at true/1 ) ); $responseCreator = new ResponseCreator(); $requestHandler = new JsonRpcRequestHandler($resolver, $responseCreator); $exceptionHandler = new ExceptionHandler($responseCreator); $endpoint = new JsonRpcEndpoint($jsonRpcSerializer, $requestHandler, $exceptionHandler);
端点准备就绪后,您可以发送请求字符串
$requestString = <<<JSONRPC { "jsonrpc": "2.0", "id": 1 "method": "dummy-method" } JSONRPC; $responseString = $endpoint->index($requestString);
$responseString
将根据方法的返回值成为以下字符串
-
{"jsonrpc":"2.0","id":1,"result":{"status":"done"}}
-
{"jsonrpc":"2.0","id":1,"result":null}
-
{"jsonrpc":"2.0","id":1,"result":12345}
事件调度示例
简单事件调度器
您可以使用 behat 测试中使用的 作为示例。
use Yoanm\JsonRpcServer\Domain\Event\JsonRpcServerEvent; use Yoanm\JsonRpcServer\Domain\JsonRpcServerDispatcherInterface; /** * Class SimpleDispatcher */ class SimpleDispatcher implements JsonRpcServerDispatcherInterface { /** @var callable[] */ private $listenerList = []; /** * {@inheritdoc} */ public function dispatchJsonRpcEvent(string $eventName, JsonRpcServerEvent $event = null) : void { if (!array_key_exists($eventName, $this->listenerList)) { return; } foreach ($this->listenerList[$eventName] as $listener) { $listener($event, $eventName); } } /** * {@inheritdoc} */ public function addJsonRpcListener(string $eventName, $listener) : void { $this->listenerList[$eventName][] = $listener; } }
然后将您的监听器绑定到您的调度器上
use Yoanm\JsonRpcServer\Domain\Event\Acknowledge\OnRequestReceivedEvent; use Yoanm\JsonRpcServer\Domain\Event\Acknowledge\OnResponseSendingEvent; use Yoanm\JsonRpcServer\Domain\Event\Action\OnMethodSuccessEvent; $dispatcher = new SimpleDispatcher(); $listener = function ($event, $eventName) { echo sprintf( 'Received %s with event class "%s"', $eventName, get_class($event) ); }; $dispatcher->addJsonRpcListener(OnRequestReceivedEvent::EVENT_NAME, $listener); $dispatcher->addJsonRpcListener(OnResponseSendingEvent::EVENT_NAME, $listener); $dispatcher->addJsonRpcListener(OnMethodSuccessEvent::EVENT_NAME, $listener);
并按以下方式绑定调度器
$endpoint->setJsonRpcServerDispatcher($dispatcher); $requestHandler->setJsonRpcServerDispatcher($dispatcher); $exceptionHandler->setJsonRpcServerDispatcher($dispatcher);
事件已分发
基本请求生命周期
-
json_rpc_server_skd.on_request_received
/Acknowledge\OnRequestReceivedEvent
当一个请求已传递到端点并成功反序列化时,将触发此事件。
注意:当请求字符串不是有效的 JSON-RPC 请求时,不会触发此事件。
它包括
-
解析错误异常(格式不正确的 JSON 字符串)
-
对于简单请求,在无效请求(不是对象 / 缺少必需属性 / ...)的情况下。
⚠️ 对于包含无效子请求的批请求,此事件仍将被触发
-
-
或者是
-
json_rpc_server_skd.on_method_success
/Action\OnMethodSuccessEvent
只有在 JSON-RPC 方法已成功执行的情况下才会触发。
-
json_rpc_server_skd.on_method_failure
/Action\OnMethodFailureEvent
只有在 JSON-RPC 方法在执行过程中抛出异常的情况下才会触发。
-
-
json_rpc_server_skd.on_response_sending
/Acknowledge\OnResponseSendingEvent
当端点成功序列化响应时触发,并将被返回。
其他事件
批量请求
-
json_rpc_server_skd.on_batch_sub_request_processing
/Acknowledge\OnBatchSubRequestProcessingEvent
在处理子请求之前触发。
-
json_rpc_server_skd.on_batch_sub_request_processed
/Acknowledge\OnBatchSubRequestProcessedEvent
在处理子请求之后触发(无论子请求方法执行成功或失败)。
异常
json_rpc_server_skd.on_exception
/ Action\OnExceptionEvent
在SDK执行期间发生异常时触发。
行为与确认事件
确认
它们只有确认的目的。
它们被分组在Yoanm\JsonRpcServer\Domain\Event\Acknowledge
命名空间下。
行为
它们允许您覆盖内容。
它们被分组在Yoanm\JsonRpcServer\Domain\Event\Action
命名空间下。
这里,列表
Action\OnMethodSuccessEvent
允许您更新/更改方法的结果。Action\OnMethodFailureEvent
允许您更新/更改方法抛出的异常。Action\OnExceptionEvent
允许您更新/更改抛出的异常。
参数验证示例
您可以使用此 JSON-RPC params symfony validator 作为示例
为了验证给定方法的参数,请执行以下操作
use Yoanm\JsonRpcServer\Domain\JsonRpcMethodInterface; use Yoanm\JsonRpcServer\Domain\JsonRpcMethodParamsValidatorInterface; use Yoanm\JsonRpcServer\Domain\Model\JsonRpcRequest; $validator = new class implements JsonRpcMethodParamsValidatorInterface { public function validate(JsonRpcRequest $jsonRpcRequest, JsonRpcMethodInterface $method) : array { if (!(/** Skip unexpected method */)) { return []; } // Create your violations based on what you want $paramList = $jsonRpcRequest->getParamList(); $violation = "???"; return [$violation]; } }; $requestHandler->setMethodParamsValidator($validator);
贡献
查看 贡献说明