rpc_client_server/
rpc_client_server.rs1use serde::{Deserialize, Serialize};
4use std::env;
5use std::sync::Arc;
6use xrpc::{
7 MessageChannelAdapter, RpcClient, RpcServer, SharedMemoryConfig, SharedMemoryFrameTransport,
8};
9
10#[derive(Debug, Clone, Serialize, Deserialize)]
11struct AddRequest {
12 a: i32,
13 b: i32,
14}
15
16#[derive(Debug, Clone, Serialize, Deserialize)]
17struct AddResponse {
18 result: i32,
19}
20
21#[derive(Debug, Clone, Serialize, Deserialize)]
22struct EchoRequest {
23 message: String,
24}
25
26#[derive(Debug, Clone, Serialize, Deserialize)]
27struct EchoResponse {
28 message: String,
29 length: usize,
30}
31
32const SERVICE_NAME: &str = "rpc_example_service";
33
34#[tokio::main]
35async fn main() -> Result<(), Box<dyn std::error::Error>> {
36 let args: Vec<String> = env::args().collect();
37 let mode = args.get(1).map(|s| s.as_str()).unwrap_or("server");
38
39 match mode {
40 "server" => run_server().await?,
41 "client" => run_client().await?,
42 _ => {
43 eprintln!("Usage: cargo run --example rpc_client_server -- [server|client]");
44 std::process::exit(1);
45 }
46 }
47
48 Ok(())
49}
50
51async fn run_server() -> Result<(), Box<dyn std::error::Error>> {
52 println!("[Server] Starting RPC server");
53
54 let config = SharedMemoryConfig::default();
55 let transport = SharedMemoryFrameTransport::create_server(SERVICE_NAME, config)?;
56 let channel = Arc::new(MessageChannelAdapter::new(transport));
57
58 let server = RpcServer::new();
59
60 server.register_typed("add", |req: AddRequest| async move {
61 println!("[Server] add({}, {})", req.a, req.b);
62 Ok(AddResponse {
63 result: req.a + req.b,
64 })
65 });
66
67 server.register_typed("echo", |req: EchoRequest| async move {
68 println!("[Server] echo(\"{}\")", req.message);
69 let len = req.message.len();
70 Ok(EchoResponse {
71 message: req.message,
72 length: len,
73 })
74 });
75
76 println!("[Server] Registered {} handlers", server.handler_count());
77 println!("[Server] Waiting for requests\n");
78
79 server.serve(channel).await?;
80
81 Ok(())
82}
83
84async fn run_client() -> Result<(), Box<dyn std::error::Error>> {
85 println!("[Client] Connecting to RPC server");
86
87 let transport = SharedMemoryFrameTransport::connect_client(SERVICE_NAME)?;
88 let channel = MessageChannelAdapter::new(transport);
89
90 let client = RpcClient::new(channel);
91 let _handle = client.start();
92
93 println!("[Client] Connected!\n");
94
95 println!("[Client] Calling add(10, 32)");
96 let resp: AddResponse = client.call("add", &AddRequest { a: 10, b: 32 }).await?;
97 println!("[Client] Result: {}\n", resp.result);
98
99 println!("[Client] Calling add(100, 200)");
100 let resp: AddResponse = client.call("add", &AddRequest { a: 100, b: 200 }).await?;
101 println!("[Client] Result: {}\n", resp.result);
102
103 println!("[Client] Calling echo(\"Hello, RPC!\")");
104 let resp: EchoResponse = client
105 .call(
106 "echo",
107 &EchoRequest {
108 message: "Hello, RPC!".to_string(),
109 },
110 )
111 .await?;
112 println!(
113 "[Client] Result: message=\"{}\", length={}\n",
114 resp.message, resp.length
115 );
116
117 println!("[Client] Calling unknown method");
118 let result: Result<(), _> = client.call("unknown", &()).await;
119 match result {
120 Ok(_) => println!("[Client] Unexpected success"),
121 Err(e) => println!("[Client] Got expected error: {}\n", e),
122 }
123
124 client.close().await?;
125 println!("[Client] Done!");
126
127 Ok(())
128}