tx5 0.8.1

The main holochain tx5 webrtc networking crate
Documentation
use criterion::{criterion_group, criterion_main, Criterion};
use std::io::{Error, Result};
use std::sync::Arc;
use tokio::sync::Mutex;
use tx5::*;

const DATA: &[u8] = &[0xdb; 4096];

struct Test {
    _server: sbd_server::SbdServer,
    cli_url1: PeerUrl,
    ep1: Endpoint,
    ep_rcv1: EndpointRecv,
    cli_url2: PeerUrl,
    ep2: Endpoint,
    ep_rcv2: EndpointRecv,
}

impl Test {
    pub async fn new() -> Self {
        let bind = vec![format!("127.0.0.1:0"), format!("[::1]:0")];

        let config = Arc::new(sbd_server::Config {
            bind,
            disable_rate_limiting: true,
            ..Default::default()
        });

        let server = sbd_server::SbdServer::new(config).await.unwrap();

        let sig_url = SigUrl::parse(&format!(
            "ws://{}",
            server.bind_addrs().get(0).unwrap()
        ))
        .unwrap();

        let config = Arc::new(Config::new().with_signal_allow_plain_text(true));

        let (ep1, mut ep_rcv1) = Endpoint::new(config.clone());
        ep1.listen(sig_url.clone()).await;
        let (ep2, mut ep_rcv2) = Endpoint::new(config);
        ep2.listen(sig_url).await;

        let (cli_url1, cli_url2) = tokio::join!(
            async {
                loop {
                    if let Some(EndpointEvent::ListeningAddressOpen {
                        local_url,
                    }) = ep_rcv1.recv().await
                    {
                        break local_url;
                    }
                }
            },
            async {
                loop {
                    if let Some(EndpointEvent::ListeningAddressOpen {
                        local_url,
                    }) = ep_rcv2.recv().await
                    {
                        break local_url;
                    }
                }
            },
        );

        ep1.send(cli_url2.clone(), b"hello".to_vec()).await.unwrap();
        match ep_rcv2.recv().await {
            Some(EndpointEvent::Connected { .. }) => (),
            oth => panic!("unexpected: {oth:?}"),
        }
        match ep_rcv2.recv().await {
            Some(EndpointEvent::Message { .. }) => (),
            oth => panic!("unexpected: {oth:?}"),
        }

        ep2.send(cli_url1.clone(), b"world".to_vec()).await.unwrap();
        match ep_rcv1.recv().await {
            Some(EndpointEvent::Connected { .. }) => (),
            oth => panic!("unexpected: {oth:?}"),
        }
        match ep_rcv1.recv().await {
            Some(EndpointEvent::Message { .. }) => (),
            oth => panic!("unexpected: {oth:?}"),
        }

        Self {
            _server: server,
            cli_url1,
            ep1,
            ep_rcv1,
            cli_url2,
            ep2,
            ep_rcv2,
        }
    }

    pub async fn test(&mut self) {
        let Test {
            cli_url1,
            ep1,
            ep_rcv1,
            cli_url2,
            ep2,
            ep_rcv2,
            ..
        } = self;

        let _ = tokio::try_join!(
            ep1.send(cli_url2.clone(), DATA.to_vec()),
            ep2.send(cli_url1.clone(), DATA.to_vec()),
            async { txerr(ep_rcv1.recv().await) },
            async { txerr(ep_rcv2.recv().await) },
        )
        .unwrap();
    }
}

fn txerr(v: Option<EndpointEvent>) -> Result<()> {
    match v {
        None => Err(Error::other("end")),
        _ => Ok(()),
    }
}

fn criterion_benchmark(c: &mut Criterion) {
    let rt = tokio::runtime::Builder::new_multi_thread()
        .enable_all()
        .build()
        .unwrap();

    let test = Arc::new(Mutex::new(rt.block_on(Test::new())));
    let test = &test;

    c.bench_function("throughput", |b| {
        b.to_async(&rt).iter(|| async move {
            test.lock().await.test().await;
        });
    });
}

criterion_group!(benches, criterion_benchmark);
criterion_main!(benches);