diff options
Diffstat (limited to 'common')
| -rw-r--r-- | common/Cargo.toml | 1 | ||||
| -rw-r--r-- | common/object/src/lib.rs | 55 | ||||
| -rw-r--r-- | common/object/src/value.rs | 73 | ||||
| -rw-r--r-- | common/src/lib.rs | 44 |
4 files changed, 100 insertions, 73 deletions
diff --git a/common/Cargo.toml b/common/Cargo.toml index 51e2208..b0ecc02 100644 --- a/common/Cargo.toml +++ b/common/Cargo.toml @@ -9,4 +9,5 @@ chrono = { version = "0.4.42", features = ["serde"] } blake3 = "1.8.2" hex = "0.4.3" jellystream-types = { path = "../stream/types" } +jellyobject = { path = "object" } base64 = "0.22.1" diff --git a/common/object/src/lib.rs b/common/object/src/lib.rs index 33d38d1..90ddef5 100644 --- a/common/object/src/lib.rs +++ b/common/object/src/lib.rs @@ -4,6 +4,9 @@ Copyright (C) 2025 metamuffin <metamuffin.org> */ +mod value; +pub use value::*; + use std::marker::PhantomData; #[repr(transparent)] @@ -78,55 +81,3 @@ impl<'a> Object<'a> { } } } - -pub trait Value<'a>: Sized { - const ALIGNED: bool; - fn load_aligned(buf: &'a [u32]) -> Option<Self> { - let _ = buf; - None - } - fn load_unaligned(buf: &'a [u8]) -> Option<Self> { - let _ = buf; - None - } - fn store(&self, buf: &mut Vec<u8>); - fn size(&self) -> usize; -} -impl<'a> Value<'a> for &'a str { - const ALIGNED: bool = false; - fn load_unaligned(buf: &'a [u8]) -> Option<Self> { - str::from_utf8(buf).ok() - } - fn store(&self, buf: &mut Vec<u8>) { - buf.extend(self.as_bytes()); - } - fn size(&self) -> usize { - self.len() - } -} -impl Value<'_> for u32 { - const ALIGNED: bool = false; - fn load_aligned(buf: &[u32]) -> Option<Self> { - buf.get(0).copied() - } - fn store(&self, buf: &mut Vec<u8>) { - buf.extend(self.to_ne_bytes()); - } - fn size(&self) -> usize { - 4 - } -} -impl Value<'_> for u64 { - const ALIGNED: bool = false; - fn load_aligned(buf: &[u32]) -> Option<Self> { - let hi = *buf.get(0)? as u64; - let lo = *buf.get(1)? as u64; - Some(hi << 32 | lo) - } - fn store(&self, buf: &mut Vec<u8>) { - buf.extend(self.to_ne_bytes()); - } - fn size(&self) -> usize { - 8 - } -} diff --git a/common/object/src/value.rs b/common/object/src/value.rs new file mode 100644 index 0000000..18aae97 --- /dev/null +++ b/common/object/src/value.rs @@ -0,0 +1,73 @@ +/* + This file is part of jellything (https://codeberg.org/metamuffin/jellything) + which is licensed under the GNU Affero General Public License (version 3); see /COPYING. + Copyright (C) 2025 metamuffin <metamuffin.org> +*/ + +use crate::Object; + +pub trait Value<'a>: Sized { + const ALIGNED: bool; + fn load_aligned(buf: &'a [u32]) -> Option<Self> { + let _ = buf; + None + } + fn load_unaligned(buf: &'a [u8]) -> Option<Self> { + let _ = buf; + None + } + fn store(&self, buf: &mut Vec<u8>); + fn size(&self) -> usize; +} +impl<'a> Value<'a> for &'a str { + const ALIGNED: bool = false; + fn load_unaligned(buf: &'a [u8]) -> Option<Self> { + str::from_utf8(buf).ok() + } + fn store(&self, buf: &mut Vec<u8>) { + buf.extend(self.as_bytes()); + } + fn size(&self) -> usize { + self.len() + } +} +impl Value<'_> for u32 { + const ALIGNED: bool = false; + fn load_aligned(buf: &[u32]) -> Option<Self> { + buf.get(0).copied() + } + fn store(&self, buf: &mut Vec<u8>) { + buf.extend(self.to_ne_bytes()); + } + fn size(&self) -> usize { + 4 + } +} +impl Value<'_> for u64 { + const ALIGNED: bool = false; + fn load_aligned(buf: &[u32]) -> Option<Self> { + let hi = *buf.get(0)? as u64; + let lo = *buf.get(1)? as u64; + Some(hi << 32 | lo) + } + fn store(&self, buf: &mut Vec<u8>) { + buf.extend(self.to_ne_bytes()); + } + fn size(&self) -> usize { + 8 + } +} +impl<'a> Value<'a> for Object<'a> { + const ALIGNED: bool = true; + fn load_aligned(buf: &'a [u32]) -> Option<Self> { + Self::load(buf) + } + fn store(&self, buf: &mut Vec<u8>) { + buf.extend(self.tags.iter().copied().map(u32::to_ne_bytes).flatten()); + buf.extend(self.offsets.iter().copied().map(u32::to_ne_bytes).flatten()); + buf.extend(self.values.iter().copied().map(u32::to_ne_bytes).flatten()); + } + fn size(&self) -> usize { + (self.tags.len() + self.offsets.len() + self.values.len()) * size_of::<u32>() + } +} diff --git a/common/src/lib.rs b/common/src/lib.rs index 769cfe2..209aeef 100644 --- a/common/src/lib.rs +++ b/common/src/lib.rs @@ -53,33 +53,35 @@ pub enum NodeIDOrSlug { Slug(String), } +use jellyobject::{Object, Tag, TypedTag}; +use std::marker::PhantomData; macro_rules! keys { - ($($id:ident = $tag:literal $name:literal;)*) => { - $(const $id: Tag = Tag($tag);)* + ($($id:ident: $type:ty = $tag:literal $name:literal;)*) => { + $(pub const $id: TypedTag<$type> = TypedTag(Tag($tag), PhantomData);)* }; } keys! { - N_KIND = 1 "kind"; - N_TITLE = 2 "title"; - N_PARENT = 3 "parent"; - N_TAGLINE = 4 "tagline"; - N_DESCRIPTION = 5 "description"; - N_RELEASEDATE = 6 "releasedate"; - N_INDEX = 7 "index"; - N_SEASON_INDEX = 8 "season_index"; - N_MEDIA = 9 "media"; - N_TAG = 10 "tag"; - N_RATINGS = 11 "ratings"; - N_PICTURES = 12 "pictures"; - N_IDENTIFIERS = 13 "identifiers"; - N_VISIBILITY = 14 "visibility"; - N_STORAGE_SIZE = 15 "storage_size"; + N_KIND: Tag = 1 "kind"; + N_TITLE: &str = 2 "title"; + N_PARENT: u64 = 3 "parent"; + N_TAGLINE: &str = 4 "tagline"; + N_DESCRIPTION: &str = 5 "description"; + N_RELEASEDATE: u64 = 6 "releasedate"; + N_INDEX: u64 = 7 "index"; + N_SEASON_INDEX: u64 = 8 "season_index"; + N_MEDIA: Object = 9 "media"; + N_TAG: &str = 10 "tag"; + N_RATINGS: Object = 11 "ratings"; + N_PICTURES: Object = 12 "pictures"; + N_IDENTIFIERS: Object = 13 "identifiers"; + N_VISIBILITY: Tag = 14 "visibility"; + N_STORAGE_SIZE: u64 = 15 "storage_size"; - LANG_NATIVE = 0xa001 "native"; - LANG_ENG = 0xa002 "eng"; - LANG_DEU = 0xa003 "deu"; - LANG_JPN = 0xa003 "jpn"; + LANG_NATIVE: &str = 0xa001 "native"; + LANG_ENG: &str = 0xa002 "eng"; + LANG_DEU: &str = 0xa003 "deu"; + LANG_JPN: &str = 0xa003 "jpn"; } #[derive(Debug, Clone, Deserialize, Serialize, Default)] |