subscriptions.rs (2730B)
1 //! Local nostrdb subscription management for nostrverse rooms. 2 //! 3 //! Subscribes to room events (kind 37555) and presence events (kind 10555) 4 //! in the local nostrdb and polls for updates each frame. 5 6 use nostrdb::{Filter, Ndb, Note, Subscription, Transaction}; 7 8 use crate::kinds; 9 10 /// A local nostrdb subscription that polls for notes of a given kind. 11 struct KindSubscription { 12 sub: Subscription, 13 } 14 15 impl KindSubscription { 16 fn new(ndb: &Ndb, kind: u16) -> Self { 17 let filter = Filter::new().kinds([kind as u64]).build(); 18 let sub = ndb.subscribe(&[filter]).expect("kind subscription"); 19 Self { sub } 20 } 21 22 fn poll<'a>(&self, ndb: &'a Ndb, txn: &'a Transaction) -> Vec<Note<'a>> { 23 ndb.poll_for_notes(self.sub, 50) 24 .into_iter() 25 .filter_map(|nk| ndb.get_note_by_key(txn, nk).ok()) 26 .collect() 27 } 28 } 29 30 /// Manages a local nostrdb subscription for room events. 31 pub struct RoomSubscription { 32 inner: KindSubscription, 33 } 34 35 impl RoomSubscription { 36 /// Subscribe to all room events (kind 37555) in the local nostrdb. 37 pub fn new(ndb: &Ndb) -> Self { 38 Self { 39 inner: KindSubscription::new(ndb, kinds::ROOM), 40 } 41 } 42 43 /// Subscribe to room events from a specific author. 44 #[allow(dead_code)] 45 pub fn for_author(ndb: &Ndb, author: &[u8; 32]) -> Self { 46 let filter = Filter::new() 47 .kinds([kinds::ROOM as u64]) 48 .authors([author]) 49 .build(); 50 let sub = ndb.subscribe(&[filter]).expect("room subscription"); 51 Self { 52 inner: KindSubscription { sub }, 53 } 54 } 55 56 /// Poll for new room events. Returns parsed notes. 57 pub fn poll<'a>(&self, ndb: &'a Ndb, txn: &'a Transaction) -> Vec<Note<'a>> { 58 self.inner.poll(ndb, txn) 59 } 60 61 /// Query for existing room events (e.g. on startup). 62 pub fn query_existing<'a>(ndb: &'a Ndb, txn: &'a Transaction) -> Vec<Note<'a>> { 63 let filter = Filter::new().kinds([kinds::ROOM as u64]).limit(50).build(); 64 ndb.query(txn, &[filter], 50) 65 .unwrap_or_default() 66 .into_iter() 67 .map(|qr| qr.note) 68 .collect() 69 } 70 } 71 72 /// Manages a local nostrdb subscription for presence events (kind 10555). 73 pub struct PresenceSubscription { 74 inner: KindSubscription, 75 } 76 77 impl PresenceSubscription { 78 /// Subscribe to presence events in the local nostrdb. 79 pub fn new(ndb: &Ndb) -> Self { 80 Self { 81 inner: KindSubscription::new(ndb, kinds::PRESENCE), 82 } 83 } 84 85 /// Poll for new presence events. 86 pub fn poll<'a>(&self, ndb: &'a Ndb, txn: &'a Transaction) -> Vec<Note<'a>> { 87 self.inner.poll(ndb, txn) 88 } 89 }