2024-12-23 00:20:59 -03:00
|
|
|
use futures_util::SinkExt;
|
|
|
|
use tokio_tungstenite::{connect_async, tungstenite::Message};
|
2024-12-22 20:56:52 -03:00
|
|
|
use gb_core::{Result, Error};
|
|
|
|
|
|
|
|
pub struct WebSocketClient {
|
2024-12-23 00:20:59 -03:00
|
|
|
stream: tokio_tungstenite::WebSocketStream<
|
|
|
|
tokio_tungstenite::MaybeTlsStream<tokio::net::TcpStream>
|
|
|
|
>,
|
2024-12-22 20:56:52 -03:00
|
|
|
}
|
|
|
|
|
|
|
|
impl WebSocketClient {
|
2024-12-23 00:20:59 -03:00
|
|
|
fn to_gb_error(error: tokio_tungstenite::tungstenite::Error) -> Error {
|
|
|
|
Error::new(
|
|
|
|
gb_core::ErrorKind::WebSocket(error.to_string()),
|
|
|
|
error.to_string()
|
|
|
|
)
|
|
|
|
}
|
2024-12-22 20:56:52 -03:00
|
|
|
|
2024-12-23 00:20:59 -03:00
|
|
|
pub async fn connect(url: &str) -> Result<Self> {
|
|
|
|
let (ws_stream, _) = connect_async(url).await.map_err(Self::to_gb_error)?;
|
2024-12-22 20:56:52 -03:00
|
|
|
Ok(Self {
|
2024-12-23 00:20:59 -03:00
|
|
|
stream: ws_stream,
|
2024-12-22 20:56:52 -03:00
|
|
|
})
|
|
|
|
}
|
|
|
|
|
2024-12-23 00:20:59 -03:00
|
|
|
pub async fn send_message(&mut self, payload: String) -> Result<()> {
|
|
|
|
self.stream
|
|
|
|
.send(Message::Text(payload))
|
2024-12-22 20:56:52 -03:00
|
|
|
.await
|
2024-12-23 00:20:59 -03:00
|
|
|
.map_err(Self::to_gb_error)?;
|
2024-12-22 20:56:52 -03:00
|
|
|
Ok(())
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
#[cfg(test)]
|
|
|
|
mod tests {
|
|
|
|
use super::*;
|
|
|
|
use rstest::*;
|
|
|
|
use serde::{Deserialize, Serialize};
|
2024-12-23 00:20:59 -03:00
|
|
|
use std::time::Duration;
|
2024-12-22 20:56:52 -03:00
|
|
|
use tokio::net::TcpListener;
|
|
|
|
use uuid::Uuid;
|
|
|
|
|
|
|
|
#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)]
|
|
|
|
struct TestMessage {
|
|
|
|
id: Uuid,
|
|
|
|
content: String,
|
|
|
|
}
|
|
|
|
|
|
|
|
async fn create_test_server() -> String {
|
|
|
|
let listener = TcpListener::bind("127.0.0.1:0").await.unwrap();
|
|
|
|
let addr = listener.local_addr().unwrap();
|
2024-12-23 00:20:59 -03:00
|
|
|
|
2024-12-22 20:56:52 -03:00
|
|
|
tokio::spawn(async move {
|
|
|
|
while let Ok((stream, _)) = listener.accept().await {
|
2024-12-23 00:20:59 -03:00
|
|
|
let ws_stream = tokio_tungstenite::accept_async(stream).await.unwrap();
|
2024-12-22 20:56:52 -03:00
|
|
|
let (mut write, mut read) = ws_stream.split();
|
2024-12-23 00:20:59 -03:00
|
|
|
|
2024-12-22 20:56:52 -03:00
|
|
|
while let Some(Ok(msg)) = read.next().await {
|
|
|
|
if let Message::Text(_) = msg {
|
|
|
|
write.send(msg).await.unwrap();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
format!("ws://{}", addr)
|
|
|
|
}
|
|
|
|
|
|
|
|
#[fixture]
|
|
|
|
fn test_message() -> TestMessage {
|
|
|
|
TestMessage {
|
|
|
|
id: Uuid::new_v4(),
|
|
|
|
content: "test message".to_string(),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
#[rstest]
|
|
|
|
#[tokio::test]
|
2024-12-23 00:20:59 -03:00
|
|
|
async fn test_websocket(test_message: TestMessage) {
|
2024-12-22 20:56:52 -03:00
|
|
|
let server_url = create_test_server().await;
|
2024-12-23 00:20:59 -03:00
|
|
|
let mut client = WebSocket::new(&server_url).await.unwrap();
|
2024-12-22 20:56:52 -03:00
|
|
|
tokio::time::sleep(Duration::from_millis(100)).await;
|
|
|
|
client.send(&test_message).await.unwrap();
|
|
|
|
}
|
|
|
|
}
|