10个版本
新 0.1.13 | 2024年8月23日 |
---|---|
0.1.12 | 2022年10月30日 |
0.1.7 | 2022年9月17日 |
0.1.3 |
|
#1552 在 网络编程
1,148 每月下载量
在 23 个包中使用了(17个直接使用)
21KB
334 行
nanorpc:JSON-RPC 2.0子集的魔法库(WIP)
动机
通常,编写客户端-服务器网络API(例如,REST API)涉及以下三个步骤
- 用英语指定协议
- 实现协议的服务器端
- 分别实现协议的客户端
这很麻烦,而且容易出错。协议实际上在三个不同的地方和以三种不同的方式指定了三次,并且保持它们同步是一项巨大的工作。
相反,我们希望一次指定协议,然后自动拥有
- 一个服务器实现,泛型
- 每个端点的业务逻辑
- 低级网络细节(例如,“在此HTTP端点监听”)
- 一个客户端实现,泛型于低级网络细节(例如,“调用此HTTP端点”)
- 充分利用Rust的类型系统,以帮助避免序列化和反序列化不匹配、打字错误等问题。
关于 nanorpc
nanorpc
确实做到了。它是一个带有宏 #[nanorpc_derive]
的JSON-RPC子集实现,该宏给定表示API接口的trait,抽象出实现API的所有 重复 部分。
特别是
nanorpc
定义了动态类型的JSON-RPC服务器和客户端trait- 一个
RpcService
trait,用于描述JSON-RPC服务器端响应者(给定JSON请求,生成JSON响应) - 一个
RpcTransport
trait,用于描述JSON-RPC客户端请求者(给定JSON请求,与某人交谈以生成JSON响应)
- 一个
- 给定描述RPC方法、它们的参数类型和它们的返回类型的
FooProtocol
trait,[nanorpc_derive]
继承- 一个名为
FooService
的结构体,它可以将任何实现FooProtocol
的“业务逻辑”结构体包装成一个实现了RpcService
的结构体。 - 一个名为
FooClient
的结构体,它可以将任何实现RpcTransport
的 JSON 传输包装成一个具有对应 RPC 方法的结构体。
- 一个名为
例如
#[nanorpc_derive]
#[async_trait]
pub trait MathProtocol {
/// Adds two numbers. Arguments and return type must be JSON-serializable through `serde_json`
async fn add(&self, x: f64, y: f64) -> f64;
/// Multiplies two numbers
async fn mult(&self, x: f64, y: f64) -> f64;
}
// Autogenerates a server struct:
pub struct MathService<T: MathProtocol>(pub T);
#[async_trait]
impl <T: MathService> RpcService for MathService<T> {
//...
}
// Autogenerates a client struct like:
pub struct MathClient<T: RpcTransport>(pub T);
impl <T: RpcTransport> MathClient {
/// Adds two numbers
pub async fn add(&self, x: f64, y: f64) -> Result<f64, T::Error>;
//...
}
在 JSON 层面上,上述协议将响应 JSON-RPC 2.0 请求
{"jsonrpc": "2.0", "method": "mult", "params": [42, 23], "id": 1}
如下
{"jsonrpc": "2.0", "result": 966, "id": 1}
依赖
~2-3MB
~63K SLoC