use std::net::SocketAddr; use std::io::Write; use log::info; use structopt::StructOpt; use sodiumoxide::crypto::auth; use sodiumoxide::crypto::sign::ed25519; use netapp::peering::fullmesh::*; use netapp::NetApp; #[derive(StructOpt, Debug)] #[structopt(name = "netapp")] pub struct Opt { #[structopt(long = "network-key", short = "n")] network_key: Option, #[structopt(long = "private-key", short = "p")] private_key: Option, #[structopt(long = "bootstrap-peer", short = "b")] bootstrap_peers: Vec, #[structopt(long = "listen-addr", short = "l", default_value = "127.0.0.1:1980")] listen_addr: String, } #[tokio::main] async fn main() { env_logger::Builder::new() .parse_env("RUST_LOG") .format(|buf, record| { writeln!(buf, "{} {} {} {}", chrono::Local::now().format("%s%.6f"), record.module_path().unwrap_or("_"), record.level(), record.args() ) }) .init(); let opt = Opt::from_args(); let netid = match &opt.network_key { Some(k) => auth::Key::from_slice(&hex::decode(k).unwrap()).unwrap(), None => auth::gen_key(), }; info!("Network key: {}", hex::encode(&netid)); let privkey = match &opt.private_key { Some(k) => ed25519::SecretKey::from_slice(&hex::decode(k).unwrap()).unwrap(), None => { let (_pk, sk) = ed25519::gen_keypair(); sk } }; info!("Node private key: {}", hex::encode(&privkey)); info!("Node public key: {}", hex::encode(&privkey.public_key())); let listen_addr = opt.listen_addr.parse().unwrap(); let netapp = NetApp::new(listen_addr, netid, privkey); let mut bootstrap_peers = vec![]; for peer in opt.bootstrap_peers.iter() { if let Some(delim) = peer.find('@') { let (key, ip) = peer.split_at(delim); let pubkey = ed25519::PublicKey::from_slice(&hex::decode(&key).unwrap()).unwrap(); let ip = ip[1..].parse::().unwrap(); bootstrap_peers.push((pubkey, ip)); } } let peering = FullMeshPeeringStrategy::new(netapp.clone(), bootstrap_peers); tokio::join!(netapp.listen(), peering.run(),); }