lib

Core libraries for Radroots
git clone https://radroots.dev/git/lib.git
Log | Files | Refs | README | LICENSE

commit ef5f79a17ec3c901f5fe5dec5777ad6efbb04bac
parent fe1e6b8eb43163f29eabc3309b547c52eac0b02c
Author: triesap <tyson@radroots.org>
Date:   Wed,  4 Mar 2026 12:59:05 +0000

events-codec: add generic parsed event wrappers

- add generic parsed data and parsed event model types
- add constructors for direct event pairing and raw event part assembly
- expose parsed module from events-codec public surface
- add unit tests for constructor field mapping and consistency

Diffstat:
Mcrates/events-codec/src/lib.rs | 1+
Acrates/events-codec/src/parsed.rs | 147+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 148 insertions(+), 0 deletions(-)

diff --git a/crates/events-codec/src/lib.rs b/crates/events-codec/src/lib.rs @@ -8,6 +8,7 @@ pub mod error; pub mod event_ref; pub mod job; pub mod profile; +pub mod parsed; pub mod tag_builders; pub mod wire; diff --git a/crates/events-codec/src/parsed.rs b/crates/events-codec/src/parsed.rs @@ -0,0 +1,147 @@ +#[cfg(not(feature = "std"))] +use alloc::{string::String, vec::Vec}; + +use radroots_events::RadrootsNostrEvent; + +#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))] +#[derive(Clone, Debug, PartialEq, Eq)] +pub struct RadrootsParsedData<T> { + pub id: String, + pub author: String, + pub published_at: u32, + pub kind: u32, + pub data: T, +} + +impl<T> RadrootsParsedData<T> { + #[inline] + pub fn new(id: String, author: String, published_at: u32, kind: u32, data: T) -> Self { + Self { + id, + author, + published_at, + kind, + data, + } + } +} + +#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))] +#[derive(Clone, Debug)] +pub struct RadrootsParsedEvent<T> { + pub event: RadrootsNostrEvent, + pub data: RadrootsParsedData<T>, +} + +impl<T> RadrootsParsedEvent<T> { + #[inline] + pub fn new(event: RadrootsNostrEvent, data: RadrootsParsedData<T>) -> Self { + Self { event, data } + } + + #[allow(clippy::too_many_arguments)] + pub fn from_parts( + id: String, + author: String, + published_at: u32, + kind: u32, + content: String, + tags: Vec<Vec<String>>, + sig: String, + data: T, + ) -> Self { + Self { + event: RadrootsNostrEvent { + id: id.clone(), + author: author.clone(), + created_at: published_at, + kind, + tags, + content, + sig, + }, + data: RadrootsParsedData::new(id, author, published_at, kind, data), + } + } +} + +#[cfg(test)] +mod tests { + use super::{RadrootsParsedData, RadrootsParsedEvent}; + use radroots_events::RadrootsNostrEvent; + + #[test] + fn parsed_data_constructor_maps_fields() { + let out = RadrootsParsedData::new( + "id".to_string(), + "author".to_string(), + 10, + 30402, + "payload".to_string(), + ); + assert_eq!(out.id, "id"); + assert_eq!(out.author, "author"); + assert_eq!(out.published_at, 10); + assert_eq!(out.kind, 30402); + assert_eq!(out.data, "payload"); + } + + #[test] + fn parsed_event_constructor_maps_event_and_data() { + let event = RadrootsNostrEvent { + id: "id".to_string(), + author: "author".to_string(), + created_at: 22, + kind: 1, + tags: vec![vec!["k".to_string(), "v".to_string()]], + content: "content".to_string(), + sig: "sig".to_string(), + }; + let data = RadrootsParsedData::new( + "id".to_string(), + "author".to_string(), + 22, + 1, + "payload".to_string(), + ); + + let out = RadrootsParsedEvent::new(event.clone(), data.clone()); + assert_eq!(out.event.id, event.id); + assert_eq!(out.event.author, event.author); + assert_eq!(out.event.created_at, event.created_at); + assert_eq!(out.event.kind, event.kind); + assert_eq!(out.event.tags, event.tags); + assert_eq!(out.event.content, event.content); + assert_eq!(out.event.sig, event.sig); + assert_eq!(out.data, data); + } + + #[test] + fn parsed_event_from_parts_builds_consistent_structs() { + let out = RadrootsParsedEvent::from_parts( + "id".to_string(), + "author".to_string(), + 77, + 1111, + "hello".to_string(), + vec![vec!["e".to_string(), "root".to_string()]], + "sig".to_string(), + "payload".to_string(), + ); + assert_eq!(out.event.id, "id"); + assert_eq!(out.event.author, "author"); + assert_eq!(out.event.created_at, 77); + assert_eq!(out.event.kind, 1111); + assert_eq!(out.event.content, "hello"); + assert_eq!( + out.event.tags, + vec![vec!["e".to_string(), "root".to_string()]] + ); + assert_eq!(out.event.sig, "sig"); + assert_eq!(out.data.id, "id"); + assert_eq!(out.data.author, "author"); + assert_eq!(out.data.published_at, 77); + assert_eq!(out.data.kind, 1111); + assert_eq!(out.data.data, "payload"); + } +}