Skip to content

unable to track connection status correctly #581

Description

@qknight

Describe the Bug

The code below works in general for the sending / receiving of data. I wanted to add an indication if a connection has been made with the leptos ws_is_connected signal and this part fails because I first need to send data like text/bin to know it works. The WS connection could indicate an "open" or "established" state even without data being sent but I can't figure out how to do that.

In the code below i use match WebSocket::open( and match the result:

let ws_is_connected: RwSignal<bool> = RwSignal::new(false);
...
#[cfg(feature = "hydrate")]
    spawn_local({
        let plane_data = plane_data.clone();
        let ws_tx = ws_tx.clone();
        async move {
            loop {
                let websocket_address = get_websocket_address();

                console::log_1(&format!("Connecting to {}", websocket_address).into());

                match WebSocket::open(websocket_address.as_str()) {
                    Ok(ws) => {
                        let (mut write, mut read) = ws.split();

                        // Create a channel -> writer task pumps messages to the socket.
                        let (tx, mut rx) = mpsc::unbounded::<Message>();
                        ws_tx.set(Some(tx.clone()));
                        drop(tx); // keep only the copy stored in ws_tx

                        // Background writer: forwards messages from UI to the socket.
                        spawn_local(async move {
                            while let Some(msg) = rx.next().await {
                                if let Err(e) = write.send(msg).await {
                                    console::error_1(&format!("Write error: {:?}", e).into());
                                    break;
                                }
                            }
                            console::log_1(&"📝 Writer task ended".into());
                        });

                        while let Some(msg) = read.next().await {
                            match msg {
                                Ok(Message::Text(text)) => {
                                    ws_is_connected.set(true);
                                    if let Ok(new_state) = serde_json::from_str::<PlaneData>(&text) {
                                        plane_data.set(new_state.clone());
                                        // console::log_1(
                                        //     &format!("✅ Updated from server {:#?}", new_state).into(),
                                        // );
                                    }
                                }
                                Ok(Message::Bytes(bin)) => {
                                    if let Ok(text) = std::str::from_utf8(&bin) {
                                        ws_is_connected.set(true);
                                        if let Ok(new_state) =
                                            serde_json::from_str::<PlaneData>(text)
                                        {
                                            plane_data.set(new_state);
                                        }
                                    }
                                }
                                Err(e) => {
                                    ws_is_connected.set(false);
                                    console::error_1(&format!("Read error: {:?}", e).into());
                                    break;
                                }
                            }
                        }

                        // Drop sender to stop writer task cleanly before reconnecting.
                        ws_is_connected.set(false);
                        ws_tx.set(None);
                        console::log_1(&"🔌 Disconnected, retrying…".into());
                    }
                    Err(e) => {
                        ws_is_connected.set(false);
                        console::error_1(&format!("Open failed: {:?}", e).into());
                        ws_tx.set(None);
                    }
                }

                sleep(Duration::from_secs(2)).await;
            }
        }
    });

Steps to Reproduce

Take any example with gloo ws and try to add proper tracking.

Expected Behavior

In the file https://docs.rs/gloo-net/0.7.0/src/gloo_net/eventsource/mod.rs.html there is a pub enum State { but I don't know how to access that.

Actual Behavior

I need to understand how to use this library properly and I did not find any examples which illustrate this.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions