futures_jsonrpc/
handler.rs1use crate::futures::prelude::*;
2use crate::{ErrorVariant, JrpcMethodTrait, JrpcRequest, JrpcResponse};
3use std::collections::HashMap;
4use std::sync::{Arc, RwLock};
5
6pub struct JrpcHandler<'a> {
7 hm_methods: Arc<RwLock<HashMap<String, Box<dyn JrpcMethodTrait<'a> + 'a>>>>,
8}
9
10impl<'a> JrpcHandler<'a> {
11 pub fn new() -> Result<Self, ErrorVariant> {
12 let hm_methods = Arc::new(RwLock::new(HashMap::new()));
13 let handler = JrpcHandler { hm_methods };
14 Ok(handler)
15 }
16
17 pub fn register_method<T: ToString, F: JrpcMethodTrait<'a> + 'a>(
18 &self,
19 signature: T,
20 jrpc_method: F,
21 ) -> Result<&Self, ErrorVariant> {
22 let signature = signature.to_string();
23 let jrpc_method = Box::new(jrpc_method);
24 let log_message = format!("Signature {} registered as method", &signature);
25
26 {
27 self.hm_methods
28 .try_write()
29 .map_err(|_| ErrorVariant::RwLockPoisoned)
30 .and_then(|mut hm| {
31 hm.insert(signature, jrpc_method);
32 Ok(())
33 })?;
34 }
35
36 trace!("{}", log_message);
37 Ok(self)
38 }
39
40 pub fn handle_message<T: ToString>(
41 &self,
42 message: T,
43 ) -> Result<Box<'a + Future<Item = Option<JrpcResponse>, Error = ErrorVariant>>, ErrorVariant>
44 {
45 let message = message.to_string();
46 let log_message = format!("Message {}", &message);
47 let request = JrpcRequest::parse(message)?;
48 let log_message = format!("{} generated response {:?}", &log_message, &request);
49
50 let future = {
51 self.hm_methods
52 .try_read()
53 .map_err(|_| ErrorVariant::RwLockPoisoned)
54 .and_then(|hm| {
55 hm.get(request.get_method())
56 .map(|method| Ok(method))
57 .unwrap_or(Err(ErrorVariant::MethodSignatureNotFound(
58 request.get_method().clone(),
59 )))
60 .and_then(|method| method.generate_future(request))
61 })?
62 };
63
64 trace!("{}", log_message);
65 Ok(future)
66 }
67}