Jelajahi Sumber

dchat: renamed dchat to dchatd and add placeholder dchat-cli

lunar-mining 2 tahun lalu
induk
melakukan
f8dc600fd9

+ 90 - 0
example/dchat/dchat-cli/main.py

@@ -0,0 +1,90 @@
+# This file is part of DarkFi (https://dark.fi)
+#
+# Copyright (C) 2020-2023 Dyne.org foundation
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU Affero General Public License as
+# published by the Free Software Foundation, either version 3 of the
+# License, or (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU Affero General Public License for more details.
+#
+# You should have received a copy of the GNU Affero General Public License
+# along with this program.  If not, see <https://www.gnu.org/licenses/>.
+import asyncio, json, random, sys, time
+
+# TODO: this cli is currently unimplemented
+
+class JsonRpc:
+
+    async def start(self, server, port):
+        reader, writer = await asyncio.open_connection(server, port)
+        self.reader = reader
+        self.writer = writer
+
+    async def stop(self):
+        self.writer.close()
+        await self.writer.wait_closed()
+
+    async def _make_request(self, method, params):
+        ident = random.randint(0, 2**16)
+        print(ident)
+        request = {
+            "jsonrpc": "2.0",
+            "method": method,
+            "params": params,
+            "id": ident,
+        }
+
+        message = json.dumps(request) + "\n"
+        self.writer.write(message.encode())
+        await self.writer.drain()
+
+        data = await self.reader.readline()
+        message = data.decode().strip()
+        response = json.loads(message)
+        print(response)
+        return response
+
+    async def _subscribe(self, method, params):
+        ident = random.randint(0, 2**16)
+        request = {
+            "jsonrpc": "2.0",
+            "method": method,
+            "params": params,
+            "id": ident,
+        }
+
+        message = json.dumps(request) + "\n"
+        self.writer.write(message.encode())
+        await self.writer.drain()
+        print("Subscribed")
+
+    async def ping(self):
+        return await self._make_request("ping", [])
+
+    async def dnet_switch(self, state):
+        return await self._make_request("dnet.switch", [state])
+
+    async def dnet_subscribe_events(self):
+        return await self._subscribe("dnet.subscribe_events", [])
+
+
+async def main(argv):
+    # TODO: Rpc port should be command line flag
+    # e.g. dchat 1066
+    rpc = JsonRpc()
+    while True:
+        try:
+            await rpc.start("localhost", 26660)
+            break
+        except OSError:
+            pass
+    await rpc.stop()
+
+
+asyncio.run(main(sys.argv))
+

+ 14 - 11
example/dchat/Cargo.toml → example/dchat/dchatd/Cargo.toml

@@ -1,33 +1,36 @@
 [package]
-name = "dchat"
+name = "dchatd"
 version = "0.4.2"
 homepage = "https://dark.fi"
-description = "Demo chat app used to document DarkFi networking code"
+description = "Simple chat app p2p daemon used to document DarkFi networking code"
 authors = ["Dyne.org foundation <foundation@dyne.org>"]
 repository = "https://github.com/darkrenaissance/darkfi"
 license = "AGPL-3.0-only"
 edition = "2021"
 
-# ANCHOR: darkfi
-[dependencies]
-darkfi = {path = "../../", features = ["net", "toml", "system", "async-daemonize", "rpc"]}
-darkfi-serial = {path = "../../src/serial"}
-# ANCHOR_END: darkfi
-
 # ANCHOR: dependencies
 async-trait = "0.1.74"
 log = "0.4.20"
 url = "2.5.0"
+[dependencies]
+# darkfi
+darkfi = {path = "../../../", features = ["net", "toml", "system", "async-daemonize", "rpc"]}
+darkfi-serial = {path = "../../../src/serial"}
 
-# Daemon
+# daemon
 easy-parallel = "3.3.1"
 signal-hook-async-std = "0.2.2"
 signal-hook = "0.3.17"
 simplelog = "0.12.1"
 smol = "1.3.0"
 
-# Arg parsing
-serde = {version = "1.0.193", features = ["derive"]}
+# arg parsing
+serde = {version = "1.0.192", features = ["derive"]}
 structopt = "0.3.26"
 structopt-toml = "0.5.1"
+
+# misc
+async-trait = "0.1.74"
+log = "0.4.20"
+url = "2.4.1"
 # ANCHOR_END: dependencies

+ 1 - 1
example/dchat/README.md → example/dchat/dchatd/README.md

@@ -1,6 +1,6 @@
 # Dchat
 
-A demo chat program to document DarkFi net
+A simple chat program to document DarkFi net
 code. Tutorial can be found in the [DarkFi
 book](https://darkrenaissance.github.io/darkfi/learn/writing-a-p2p-app.html).
 

+ 2 - 0
example/dchat/dchat_config.toml → example/dchat/dchatd/dchatd_config.toml

@@ -10,3 +10,5 @@
 ## Seed nodes to connect to. Required for inbound and outbound nodes.
 seeds=["tcp://127.0.0.1:55555"]
 
+## Outbound connect slots. Required for outbound nodes.
+outbound_connections = 5

+ 0 - 0
example/dchat/src/dchat_error.rs → example/dchat/dchatd/src/dchat_error.rs


+ 0 - 0
example/dchat/src/dchatmsg.rs → example/dchat/dchatd/src/dchatmsg.rs


+ 63 - 67
example/dchat/src/main.rs → example/dchat/dchatd/src/main.rs

@@ -29,7 +29,6 @@ use darkfi::{
         server::{listen_and_serve, RequestHandler},
     },
     system::{StoppableTask, StoppableTaskPtr},
-    util::path::get_config_path,
     Error, Result,
 };
 
@@ -45,8 +44,8 @@ pub mod dchatmsg;
 pub mod protocol_dchat;
 pub mod rpc;
 
-const CONFIG_FILE: &str = "dchat_config.toml";
-const CONFIG_FILE_CONTENTS: &str = include_str!("../dchat_config.toml");
+const CONFIG_FILE: &str = "dchatd_config.toml";
+const CONFIG_FILE_CONTENTS: &str = include_str!("../dchatd_config.toml");
 
 // ANCHOR: args
 #[derive(Clone, Debug, Deserialize, StructOpt, StructOptToml)]
@@ -98,68 +97,65 @@ impl Dchat {
 // ANCHOR: main
 async_daemonize!(realmain);
 async fn realmain(args: Args, ex: Arc<smol::Executor<'static>>) -> Result<()> {
-    let cfg_path = get_config_path(args.config, CONFIG_FILE)?;
-    let _toml_contents = std::fs::read_to_string(cfg_path)?;
-
     let p2p = net::P2p::new(args.net.into(), ex.clone()).await;
 
-    // ANCHOR: dnet
-    info!("Starting dnet subs task");
-    let dnet_sub = JsonSubscriber::new("dnet.subscribe_events");
-    let dnet_sub_ = dnet_sub.clone();
-    let p2p_ = p2p.clone();
-    let dnet_task = StoppableTask::new();
-    dnet_task.clone().start(
-        async move {
-            let dnet_sub = p2p_.dnet_subscribe().await;
-            loop {
-                let event = dnet_sub.receive().await;
-                debug!("Got dnet event: {:?}", event);
-                dnet_sub_.notify(vec![event.into()].into()).await;
-            }
-        },
-        |res| async {
-            match res {
-                Ok(()) | Err(Error::DetachedTaskStopped) => { /* Do nothing */ }
-                Err(e) => panic!("{}", e),
-            }
-        },
-        Error::DetachedTaskStopped,
-        ex.clone(),
-    );
-    // ANCHOR_end: dnet
-
-    // ANCHOR: rpc
-    info!("Starting JSON-RPC server on port {}", args.rpc_listen);
-    let msgs: DchatMsgsBuffer = Arc::new(Mutex::new(vec![DchatMsg { msg: String::new() }]));
-    let rpc_connections = Mutex::new(HashSet::new());
-    let dchat = Arc::new(Dchat::new(p2p.clone(), msgs.clone(), rpc_connections, dnet_sub));
-    let _ex = ex.clone();
-
-    let rpc_task = StoppableTask::new();
-    rpc_task.clone().start(
-        listen_and_serve(args.rpc_listen, dchat.clone(), None, ex.clone()),
-        |res| async move {
-            match res {
-                Ok(()) | Err(Error::RpcServerStopped) => dchat.stop_connections().await,
-                Err(e) => error!("Failed stopping JSON-RPC server: {}", e),
-            }
-        },
-        Error::RpcServerStopped,
-        ex.clone(),
-    );
-    // ANCHOR_end: rpc
-
-    // ANCHOR: register_protocol
-    info!("Registering Dchat protocol");
-    let registry = p2p.protocol_registry();
-    registry
-        .register(!net::session::SESSION_SEED, move |channel, _p2p| {
-            let msgs_ = msgs.clone();
-            async move { ProtocolDchat::init(channel, msgs_).await }
-        })
-        .await;
-    // ANCHOR_END: register_protocol
+   // // ANCHOR: dnet
+   // info!("Starting dnet subs task");
+   // let dnet_sub = JsonSubscriber::new("dnet.subscribe_events");
+   // let dnet_sub_ = dnet_sub.clone();
+   // let p2p_ = p2p.clone();
+   // let dnet_task = StoppableTask::new();
+   // dnet_task.clone().start(
+   //     async move {
+   //         let dnet_sub = p2p_.dnet_subscribe().await;
+   //         loop {
+   //             let event = dnet_sub.receive().await;
+   //             debug!("Got dnet event: {:?}", event);
+   //             dnet_sub_.notify(vec![event.into()].into()).await;
+   //         }
+   //     },
+   //     |res| async {
+   //         match res {
+   //             Ok(()) | Err(Error::DetachedTaskStopped) => { /* Do nothing */ }
+   //             Err(e) => panic!("{}", e),
+   //         }
+   //     },
+   //     Error::DetachedTaskStopped,
+   //     ex.clone(),
+   // );
+   // // ANCHOR_end: dnet
+
+   // // ANCHOR: rpc
+   // info!("Starting JSON-RPC server on port {}", args.rpc_listen);
+   // let msgs: DchatMsgsBuffer = Arc::new(Mutex::new(vec![DchatMsg { msg: String::new() }]));
+   // let rpc_connections = Mutex::new(HashSet::new());
+   // let dchat = Arc::new(Dchat::new(p2p.clone(), msgs.clone(), rpc_connections, dnet_sub));
+   // let _ex = ex.clone();
+
+   // let rpc_task = StoppableTask::new();
+   // rpc_task.clone().start(
+   //     listen_and_serve(args.rpc_listen, dchat.clone(), None, ex.clone()),
+   //     |res| async move {
+   //         match res {
+   //             Ok(()) | Err(Error::RpcServerStopped) => dchat.stop_connections().await,
+   //             Err(e) => error!("Failed stopping JSON-RPC server: {}", e),
+   //         }
+   //     },
+   //     Error::RpcServerStopped,
+   //     ex.clone(),
+   // );
+   // // ANCHOR_end: rpc
+
+   // // ANCHOR: register_protocol
+   // info!("Registering Dchat protocol");
+   // let registry = p2p.protocol_registry();
+   // registry
+   //     .register(!net::session::SESSION_SEED, move |channel, _p2p| {
+   //         let msgs_ = msgs.clone();
+   //         async move { ProtocolDchat::init(channel, msgs_).await }
+   //     })
+   //     .await;
+   // // ANCHOR_END: register_protocol
 
     // ANCHOR: p2p_start
     info!("Starting P2P network");
@@ -174,11 +170,11 @@ async fn realmain(args: Args, ex: Arc<smol::Executor<'static>>) -> Result<()> {
     info!("Stopping P2P network");
     p2p.stop().await;
 
-    info!("Stopping JSON-RPC server");
-    rpc_task.stop().await;
-    dnet_task.stop().await;
+    //info!("Stopping JSON-RPC server");
+    //rpc_task.stop().await;
+    //dnet_task.stop().await;
 
-    info!("Shut down successfully");
+    //info!("Shut down successfully");
     // ANCHOR_END: shutdown
     Ok(())
 }

+ 0 - 0
example/dchat/src/protocol_dchat.rs → example/dchat/dchatd/src/protocol_dchat.rs


+ 0 - 0
example/dchat/src/rpc.rs → example/dchat/dchatd/src/rpc.rs