use std::{pin::pin, time::Duration};
use ergot::{
Address, AnyAllAppendix, DEFAULT_TTL, FrameKind, Header, HeaderSeq, Key, NetStack, endpoint,
interface_manager::profiles::null::Null, traits::Endpoint,
};
use mutex::raw_impls::cs::CriticalSectionRawMutex;
use postcard_schema::Schema;
use serde::{Deserialize, Serialize};
use tokio::{
spawn,
time::{sleep, timeout},
};
#[derive(Serialize, Deserialize, Debug, PartialEq, Schema, Clone)]
pub struct Example {
a: u8,
b: u32,
}
#[derive(Serialize, Deserialize, Debug, PartialEq, Schema, Clone)]
pub struct Other {
a: u64,
b: i32,
}
endpoint!(ExampleEndpoint, Example, u32, "example");
endpoint!(OtherEndpoint, Other, u32, "other");
type TestNetStack = NetStack<CriticalSectionRawMutex, Null>;
#[tokio::test]
async fn hello() {
static STACK: TestNetStack = NetStack::new();
let src = Address {
network_id: 0,
node_id: 0,
port_id: 123,
};
let dst = Address {
network_id: 0,
node_id: 0,
port_id: 0,
};
{
let socket = STACK.endpoints().bounded_server::<ExampleEndpoint, 2>(None);
let mut socket = pin!(socket);
let mut hdl = socket.as_mut().attach();
let tsk = spawn(async move {
sleep(Duration::from_millis(100)).await;
STACK
.send_ty::<Other>(
&Header {
src,
dst,
any_all: Some(AnyAllAppendix {
key: Key(OtherEndpoint::REQ_KEY.to_bytes()),
nash: None,
}),
seq_no: None,
kind: FrameKind::ENDPOINT_REQ,
ttl: DEFAULT_TTL,
},
&Other { a: 345, b: -123 },
)
.unwrap_err();
STACK
.send_ty::<Example>(
&Header {
src,
dst,
any_all: Some(AnyAllAppendix {
key: Key(ExampleEndpoint::REQ_KEY.to_bytes()),
nash: None,
}),
seq_no: None,
kind: FrameKind::ENDPOINT_REQ,
ttl: DEFAULT_TTL,
},
&Example { a: 42, b: 789 },
)
.unwrap();
sleep(Duration::from_millis(100)).await;
let body = postcard::to_vec::<_, 128>(&Example { a: 56, b: 1234 }).unwrap();
STACK
.send_raw(
&HeaderSeq {
src,
dst,
any_all: Some(AnyAllAppendix {
key: Key(ExampleEndpoint::REQ_KEY.to_bytes()),
nash: None,
}),
seq_no: 123,
kind: FrameKind::ENDPOINT_REQ,
ttl: DEFAULT_TTL,
},
&body,
(),
)
.unwrap();
});
let msg = hdl.recv_manual().await.unwrap();
assert_eq!(
Address {
network_id: 0,
node_id: 0,
port_id: 123
},
msg.hdr.src
);
assert_eq!(
Address {
network_id: 0,
node_id: 0,
port_id: 0
},
msg.hdr.dst
);
assert_eq!(Example { a: 42, b: 789 }, msg.t);
let msg = hdl.recv_manual().await.unwrap();
assert_eq!(
Address {
network_id: 0,
node_id: 0,
port_id: 123
},
msg.hdr.src
);
assert_eq!(
Address {
network_id: 0,
node_id: 0,
port_id: 0
},
msg.hdr.dst
);
assert_eq!(Example { a: 56, b: 1234 }, msg.t);
tsk.await.unwrap();
}
STACK
.send_ty::<Other>(
&Header {
src,
dst,
any_all: Some(AnyAllAppendix {
key: Key(OtherEndpoint::REQ_KEY.to_bytes()),
nash: None,
}),
seq_no: None,
kind: FrameKind::ENDPOINT_REQ,
ttl: DEFAULT_TTL,
},
&Other { a: 345, b: -123 },
)
.unwrap_err();
STACK
.send_ty::<Example>(
&Header {
src,
dst,
any_all: Some(AnyAllAppendix {
key: Key(ExampleEndpoint::REQ_KEY.to_bytes()),
nash: None,
}),
seq_no: None,
kind: FrameKind::ENDPOINT_REQ,
ttl: DEFAULT_TTL,
},
&Example { a: 42, b: 789 },
)
.unwrap_err();
}
#[tokio::test]
async fn req_resp() {
static STACK: TestNetStack = NetStack::new();
let server = STACK.endpoints().bounded_server::<ExampleEndpoint, 2>(None);
let server = pin!(server);
let mut server_hdl = server.attach();
let reqqr = tokio::task::spawn(async {
for i in 0..3 {
sleep(Duration::from_millis(100)).await;
let resp = STACK
.endpoints()
.request::<ExampleEndpoint>(
Address {
network_id: 0,
node_id: 0,
port_id: 0,
},
&Example {
a: i as u8,
b: i * 10,
},
None,
)
.await
.unwrap();
println!("RESP: {:?}", resp);
}
});
for _i in 0..3 {
let srv = timeout(
Duration::from_secs(1),
server_hdl.serve(async |req| {
req.b + 5
}),
)
.await;
println!("SERV: {:?}", srv);
}
reqqr.await.unwrap();
}
#[tokio::test]
async fn req_resp_stack_vec() {
static STACK: TestNetStack = NetStack::new();
let server = STACK
.endpoints()
.bounded_server::<ExampleEndpoint, 64>(None);
let server = pin!(server);
let mut server_hdl = server.attach();
let reqqr = tokio::task::spawn(async {
for i in 0..3 {
sleep(Duration::from_millis(100)).await;
let resp = STACK
.endpoints()
.request::<ExampleEndpoint>(
Address {
network_id: 0,
node_id: 0,
port_id: 0,
},
&Example {
a: i as u8,
b: i * 10,
},
None,
)
.await
.unwrap();
println!("RESP: {:?}", resp);
}
});
for _i in 0..3 {
let srv = timeout(
Duration::from_secs(1),
server_hdl.serve(async |req| {
req.b + 5
}),
)
.await;
println!("SERV: {:?}", srv);
}
reqqr.await.unwrap();
}