mod.rs

 1use bevy_app::{App, Plugin, Update};
 2use bevy_ecs::resource::Resource;
 3use futures::StreamExt;
 4use tokio::runtime::Runtime;
 5use tokio::sync::mpsc;
 6use tokio_xmpp::{Component as TokioComponent, connect::TcpServerConnector, jid::BareJid};
 7
 8pub mod resource;
 9mod system;
10mod task;
11
12pub use resource::component_connection::{ComponentConfig, ComponentConnection, IncomingStanza};
13pub use system::receive_stanzas;
14
15#[derive(Resource)]
16pub struct AsyncRuntime(pub Runtime);
17
18impl From<Runtime> for AsyncRuntime {
19    fn from(value: Runtime) -> Self {
20        Self(value)
21    }
22}
23
24pub struct ComponentPlugin;
25
26impl Plugin for ComponentPlugin {
27    fn build(&self, app: &mut App) {
28        app.init_resource::<ComponentConfig>()
29            .add_message::<IncomingStanza>()
30            .add_systems(Update, receive_stanzas);
31    }
32}
33
34pub fn setup_component_connection(
35    runtime: &Runtime,
36    component: TokioComponent<TcpServerConnector>,
37    buffer_size: usize,
38) -> ComponentConnection {
39    let (incoming_tx, incoming_rx) = mpsc::channel(buffer_size);
40    let (outgoing_tx, outgoing_rx) = mpsc::channel(buffer_size);
41
42    let jid: BareJid = component.jid.clone().into_bare();
43    let (sink, stream) = component.split();
44
45    runtime.spawn(task::incoming_stanza_task(stream, incoming_tx));
46    runtime.spawn(task::outgoing_stanza_task(sink, outgoing_rx));
47
48    ComponentConnection {
49        jid,
50        incoming_rx,
51        outgoing_tx,
52    }
53}
54
55#[cfg(test)]
56mod test {
57    use super::*;
58    use bevy_app::App;
59
60    #[test]
61    fn api_sketching() {
62        let runtime = Runtime::new().unwrap();
63        println!("about to connect");
64        let component = runtime
65            .block_on(TokioComponent::new("sgxbwmsgsv2.localhost", "secret"))
66            .unwrap();
67        let conn = setup_component_connection(&runtime, component, 256);
68
69        println!("finished connecting");
70
71        App::new()
72            .insert_resource(conn)
73            .insert_resource(AsyncRuntime::from(runtime))
74            .add_plugins(ComponentPlugin)
75            .run();
76    }
77}