소스 검색

rpc/jsonrpc: finish the implementation for supporting tor and nym protocols on client side

ghassmo 4 년 전
부모
커밋
59261f0d43
5개의 변경된 파일59개의 추가작업 그리고 29개의 파일을 삭제
  1. 2 2
      bin/darkfid/darkfid_config.toml
  2. 26 17
      bin/darkfid/src/main.rs
  3. 4 0
      bin/drk/drk_config.toml
  4. 14 7
      bin/drk/src/main.rs
  5. 13 3
      src/rpc/jsonrpc.rs

+ 2 - 2
bin/darkfid/darkfid_config.toml

@@ -17,9 +17,9 @@ wallet_password = "TEST_PASSWORD"
 # openssl pkcs12 -export -out identity.pfx -inkey key.pem -in cert.pem -certfile chain_certs.pem
 tls_identity_path = "~/.config/darkfi/darkfid_identity.pfx"
 
-# Socks5 server url. eg. `127.0.0.1:9050`
+# Socks5 server url. eg. `socks5://127.0.0.1:9050` used for tor and nym protocols 
 [socks_url]
-url = "127.0.0.1:9050"
+url = "socks5://127.0.0.1:9050"
 
 # The address where darkfid should bind its RPC socket
 [rpc_listener_url]

+ 26 - 17
bin/darkfid/src/main.rs

@@ -62,7 +62,7 @@ pub struct DarkfidConfig {
     pub wallet_password: String,
     /// Path to DER-formatted PKCS#12 archive. (used only with tls listener url)
     pub tls_identity_path: String,
-    /// Socks5 server url. eg. `127.0.0.1:9050`
+    /// Socks5 server url. eg. `socks5://127.0.0.1:9050` used for tor and nym protocols
     pub socks_url: UrlConfig,
     /// The address where darkfid should bind its RPC socket
     pub rpc_listener_url: UrlConfig,
@@ -111,6 +111,7 @@ struct Darkfid {
     btc_tokenlist: TokenList,
     drk_tokenlist: DrkTokenList,
     cashiers: Vec<Cashier>,
+    socks_url: Url,
 }
 
 #[async_trait]
@@ -157,6 +158,7 @@ impl Darkfid {
         client: Arc<Mutex<Client>>,
         state: Arc<Mutex<State>>,
         cashiers: Vec<Cashier>,
+        socks_url: Url,
     ) -> Result<Self> {
         let sol_tokenlist =
             TokenList::new(include_bytes!("../../../contrib/token/solana_token_list.json"))?;
@@ -174,6 +176,7 @@ impl Darkfid {
             btc_tokenlist,
             drk_tokenlist,
             cashiers,
+            socks_url,
         })
     }
 
@@ -504,7 +507,7 @@ impl Darkfid {
         let req = jsonreq(json!("features"), json!([]));
         let rep: JsonResult =
             // NOTE: this just selects the first cashier in the list
-            match send_request(&self.cashiers[0].rpc_url, json!(req), None).await {
+            match send_request(&self.cashiers[0].rpc_url, json!(req), Some(self.socks_url.clone())).await {
                 Ok(v) => v,
                 Err(e) => return JsonResult::Err(jsonerr(ServerError(-32004), Some(e.to_string()), id)),
             };
@@ -569,14 +572,16 @@ impl Darkfid {
         // (and token), it shall return a valid address where tokens can be deposited.
         // If not, an error is returned, and forwarded to the method caller.
         let req = jsonreq(json!("deposit"), json!([network, token_id, pubkey]));
-        let rep: JsonResult = match send_request(&self.cashiers[0].rpc_url, json!(req), None).await
-        {
-            Ok(v) => v,
-            Err(e) => {
-                debug!(target: "DARKFID", "REQUEST IS ERR");
-                return JsonResult::Err(jsonerr(ServerError(-32004), Some(e.to_string()), id))
-            }
-        };
+        let rep: JsonResult =
+            match send_request(&self.cashiers[0].rpc_url, json!(req), Some(self.socks_url.clone()))
+                .await
+            {
+                Ok(v) => v,
+                Err(e) => {
+                    debug!(target: "DARKFID", "REQUEST IS ERR");
+                    return JsonResult::Err(jsonerr(ServerError(-32004), Some(e.to_string()), id))
+                }
+            };
 
         match rep {
             JsonResult::Resp(r) => JsonResult::Resp(r),
@@ -647,12 +652,15 @@ impl Darkfid {
         };
 
         let req = jsonreq(json!("withdraw"), json!([network, token_id, address, amount_in_apo]));
-        let mut rep: JsonResult = match send_request(&self.cashiers[0].rpc_url, json!(req), None)
-            .await
-        {
-            Ok(v) => v,
-            Err(e) => return JsonResult::Err(jsonerr(ServerError(-32004), Some(e.to_string()), id)),
-        };
+        let mut rep: JsonResult =
+            match send_request(&self.cashiers[0].rpc_url, json!(req), Some(self.socks_url.clone()))
+                .await
+            {
+                Ok(v) => v,
+                Err(e) => {
+                    return JsonResult::Err(jsonerr(ServerError(-32004), Some(e.to_string()), id))
+                }
+            };
 
         let token_id: &DrkTokenId;
 
@@ -848,7 +856,8 @@ async fn start(
         public_keys: cashier_keys,
     }));
 
-    let mut darkfid = Darkfid::new(client, state, cashiers).await?;
+    let mut darkfid =
+        Darkfid::new(client, state, cashiers, Url::try_from(config.socks_url.clone())?).await?;
 
     // TODO fix this
     let server_config = RpcServerConfig {

+ 4 - 0
bin/drk/drk_config.toml

@@ -7,3 +7,7 @@
 [darkfid_rpc_url] 
 url = "tcp://127.0.0.1:8000"
 #url = "tls://127.0.0.1:8000"
+
+# Socks5 server url. eg. `socks5://127.0.0.1:9050` used for tor and nym protocols 
+[socks_url]
+url = "socks5://127.0.0.1:9050"

+ 14 - 7
bin/drk/src/main.rs

@@ -24,6 +24,8 @@ use darkfi::{
 pub struct DrkConfig {
     /// The URL where darkfid RPC is listening on
     pub darkfid_rpc_url: UrlConfig,
+    /// Socks5 server url. eg. `socks5://127.0.0.1:9050` used for tor and nym protocols
+    pub socks_url: UrlConfig,
 }
 
 #[derive(Subcommand)]
@@ -131,11 +133,12 @@ const CONFIG_FILE_CONTENTS: &[u8] = include_bytes!("../drk_config.toml");
 
 struct Drk {
     url: Url,
+    socks_url: Url,
 }
 
 impl Drk {
-    pub fn new(url: Url) -> Self {
-        Self { url }
+    pub fn new(url: Url, socks_url: Url) -> Self {
+        Self { url, socks_url }
     }
 
     // Retrieve cashier features and error if they
@@ -162,10 +165,11 @@ impl Drk {
     }
 
     async fn request(&self, r: jsonrpc::JsonRequest) -> Result<Value> {
-        let reply: JsonResult = match jsonrpc::send_request(&self.url, json!(r), None).await {
-            Ok(v) => v,
-            Err(e) => return Err(e),
-        };
+        let reply: JsonResult =
+            match jsonrpc::send_request(&self.url, json!(r), Some(self.socks_url.clone())).await {
+                Ok(v) => v,
+                Err(e) => return Err(e),
+            };
 
         match reply {
             JsonResult::Resp(r) => {
@@ -302,7 +306,10 @@ impl Drk {
 }
 
 async fn start(config: &DrkConfig, options: CliDrk) -> Result<()> {
-    let client = Drk::new(Url::try_from(config.darkfid_rpc_url.clone())?);
+    let client = Drk::new(
+        Url::try_from(config.darkfid_rpc_url.clone())?,
+        Url::try_from(config.socks_url.clone())?,
+    );
 
     match options.command {
         Some(CliDrkSubCommands::Hello {}) => {

+ 13 - 3
src/rpc/jsonrpc.rs

@@ -145,7 +145,7 @@ pub fn notification(m: Value, p: Value) -> JsonNotification {
 
 pub async fn send_request(uri: &Url, data: Value, socks_url: Option<Url>) -> Result<JsonResult> {
     if uri.host().is_none() && uri.port().is_none() {
-        return Err(Error::UrlParseError(format!("Missing port in {}", uri)))
+        return Err(Error::UrlParseError(format!("Missing part of url: {}", uri)))
     }
 
     let host = uri.host().unwrap().to_string();
@@ -187,11 +187,21 @@ pub async fn send_request(uri: &Url, data: Value, socks_url: Option<Url>) -> Res
             }
 
             let socks_url = socks_url.unwrap();
+
+            if socks_url.host().is_none() && socks_url.port().is_none() {
+                return Err(Error::UrlParseError(format!("Missing part of socks5 url: {}", uri)))
+            }
+
             let config = Config::default();
 
+            let socks_url_str = (socks_url.host().unwrap().to_string(), socks_url.port().unwrap())
+                .to_socket_addrs()?
+                .next()
+                .ok_or(Error::NoSocks5UrlFound)?;
+
             if !socks_url.username().is_empty() && socks_url.password().is_some() {
                 stream = Socks5Stream::connect_with_password(
-                    socks_url.as_str(),
+                    socks_url_str,
                     host,
                     port,
                     socks_url.username().to_string(),
@@ -200,7 +210,7 @@ pub async fn send_request(uri: &Url, data: Value, socks_url: Option<Url>) -> Res
                 )
                 .await?;
             } else {
-                stream = Socks5Stream::connect(socks_url.as_str(), host, port, config).await?;
+                stream = Socks5Stream::connect(socks_url_str, host, port, config).await?;
             }
 
             get_reply(&mut stream, data_str).await