mod.rs (2458B)
1 use ewebsock::{Options, WsMessage, WsReceiver, WsSender}; 2 3 use crate::{ClientMessage, Result}; 4 use nostrdb::Filter; 5 use std::fmt; 6 use std::hash::{Hash, Hasher}; 7 use tracing::{debug, error, info}; 8 9 pub mod message; 10 pub mod pool; 11 12 #[derive(Debug)] 13 pub enum RelayStatus { 14 Connected, 15 Connecting, 16 Disconnected, 17 } 18 19 pub struct Relay { 20 pub url: String, 21 pub status: RelayStatus, 22 pub sender: WsSender, 23 pub receiver: WsReceiver, 24 } 25 26 impl fmt::Debug for Relay { 27 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { 28 f.debug_struct("Relay") 29 .field("url", &self.url) 30 .field("status", &self.status) 31 .finish() 32 } 33 } 34 35 impl Hash for Relay { 36 fn hash<H: Hasher>(&self, state: &mut H) { 37 // Hashes the Relay by hashing the URL 38 self.url.hash(state); 39 } 40 } 41 42 impl PartialEq for Relay { 43 fn eq(&self, other: &Self) -> bool { 44 self.url == other.url 45 } 46 } 47 48 impl Eq for Relay {} 49 50 impl Relay { 51 pub fn new(url: String, wakeup: impl Fn() + Send + Sync + 'static) -> Result<Self> { 52 let status = RelayStatus::Connecting; 53 let (sender, receiver) = ewebsock::connect_with_wakeup(&url, Options::default(), wakeup)?; 54 55 Ok(Self { 56 url, 57 sender, 58 receiver, 59 status, 60 }) 61 } 62 63 pub fn send(&mut self, msg: &ClientMessage) { 64 let json = match msg.to_json() { 65 Ok(json) => { 66 debug!("sending {} to {}", json, self.url); 67 json 68 } 69 Err(e) => { 70 error!("error serializing json for filter: {e}"); 71 return; 72 } 73 }; 74 75 let txt = WsMessage::Text(json); 76 self.sender.send(txt); 77 } 78 79 pub fn connect(&mut self, wakeup: impl Fn() + Send + Sync + 'static) -> Result<()> { 80 let (sender, receiver) = 81 ewebsock::connect_with_wakeup(&self.url, Options::default(), wakeup)?; 82 self.status = RelayStatus::Connecting; 83 self.sender = sender; 84 self.receiver = receiver; 85 Ok(()) 86 } 87 88 pub fn ping(&mut self) { 89 let msg = WsMessage::Ping(vec![]); 90 self.sender.send(msg); 91 } 92 93 pub fn subscribe(&mut self, subid: String, filters: Vec<Filter>) { 94 info!( 95 "sending '{}' subscription to relay pool: {:?}", 96 subid, filters 97 ); 98 self.send(&ClientMessage::req(subid, filters)); 99 } 100 }