diff options
| -rw-r--r-- | common/object/src/buffer.rs | 5 | ||||
| -rw-r--r-- | common/object/src/debug.rs | 59 | ||||
| -rw-r--r-- | common/object/src/inspect.rs | 59 | ||||
| -rw-r--r-- | common/object/src/json.rs | 34 | ||||
| -rw-r--r-- | common/object/src/lib.rs | 64 | ||||
| -rw-r--r-- | common/object/src/registry.rs | 42 | ||||
| -rw-r--r-- | common/object/src/tests.rs | 34 | ||||
| -rw-r--r-- | common/object/src/value.rs | 78 | ||||
| -rw-r--r-- | common/src/api.rs | 76 | ||||
| -rw-r--r-- | common/src/internal.rs | 4 | ||||
| -rw-r--r-- | common/src/lib.rs | 21 | ||||
| -rw-r--r-- | common/src/node.rs | 212 | ||||
| -rw-r--r-- | common/src/user.rs | 12 | ||||
| -rw-r--r-- | database/src/kv/mod.rs | 10 | ||||
| -rw-r--r-- | database/src/lib.rs | 6 | ||||
| -rw-r--r-- | database/src/query_ser.rs | 56 | ||||
| -rw-r--r-- | database/src/test_shared.rs | 17 | ||||
| -rw-r--r-- | import/src/plugins/infojson.rs | 2 | ||||
| -rw-r--r-- | import/src/plugins/misc.rs | 10 | ||||
| -rw-r--r-- | server/src/main.rs | 4 | ||||
| -rw-r--r-- | server/src/ui_responder.rs | 3 | ||||
| -rw-r--r-- | ui/src/components/node_page.rs | 2 | ||||
| -rw-r--r-- | ui/src/components/props.rs | 2 |
23 files changed, 381 insertions, 431 deletions
diff --git a/common/object/src/buffer.rs b/common/object/src/buffer.rs index 05557e4..829cade 100644 --- a/common/object/src/buffer.rs +++ b/common/object/src/buffer.rs @@ -30,8 +30,9 @@ impl ObjectBuffer { let mut temp = Vec::new(); for (tag, val) in fields { tags.push(tag.0); - let off = (values.len() as u32) << 2; - if val.is_aligned() { + let ty = val.get_type(); + let off = (values.len() as u32) << 5 | (ty as u32) << 2; + if ty.is_aligned() { offsets.push(off); val.store_aligned(&mut values); } else { diff --git a/common/object/src/debug.rs b/common/object/src/debug.rs new file mode 100644 index 0000000..15812b1 --- /dev/null +++ b/common/object/src/debug.rs @@ -0,0 +1,59 @@ +/* + 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) 2026 metamuffin <metamuffin.org> +*/ + +use crate::{Object, ObjectBuffer, Tag, TypedTag, ValueType}; +use std::{any::type_name, fmt::Debug}; + +impl Debug for ObjectBuffer { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + self.as_object().fmt(f) + } +} + +impl Debug for Object<'_> { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + let mut s = f.debug_struct("Object"); + let mut nonexhaustive = false; + for (i, tag) in self.keys().enumerate() { + let kbytes = tag.0.to_be_bytes(); + let k = str::from_utf8(&kbytes).unwrap(); + let ty = self.offset_type(i); + let sz = self.size(i); + match (ty, sz) { + (ValueType::String, _) => s.field(k, &self.get_typed::<&str>(i).unwrap()), + (ValueType::Binary, _) => s.field(k, &self.get_typed::<&[u8]>(i).unwrap()), + (ValueType::Object, _) => s.field(k, &self.get_typed::<Object>(i).unwrap()), + (ValueType::UInt, 4) => s.field(k, &self.get_typed::<u32>(i).unwrap()), + (ValueType::UInt, 8) => s.field(k, &self.get_typed::<u64>(i).unwrap()), + (ValueType::Int, 8) => s.field(k, &self.get_typed::<i64>(i).unwrap()), + _ => { + nonexhaustive = true; + &mut s + } + }; + } + if nonexhaustive { + s.finish_non_exhaustive() + } else { + s.finish() + } + } +} + +impl<T> Debug for TypedTag<T> { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + f.debug_tuple(&format!("TypedTag<{}>", type_name::<T>())) + .field(&self.0) + .finish() + } +} +impl Debug for Tag { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + let bytes = self.0.to_be_bytes(); + let name = str::from_utf8(&bytes).unwrap(); + f.debug_tuple("Tag").field(&name).finish() + } +} diff --git a/common/object/src/inspect.rs b/common/object/src/inspect.rs deleted file mode 100644 index cfab5c3..0000000 --- a/common/object/src/inspect.rs +++ /dev/null @@ -1,59 +0,0 @@ -/* - 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) 2026 metamuffin <metamuffin.org> -*/ - -use crate::{Object, Registry, Tag, TypedTag, types::*}; -use std::{any::type_name, fmt::Debug}; - -pub struct Inspector<'a, T>(pub &'a Registry, pub T); - -impl Debug for Inspector<'_, Object<'_>> { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - let mut s = f.debug_struct("Object"); - let mut nonexhaustive = false; - for (i, k) in self.1.keys().enumerate() { - let Some(info) = self.0.info(k) else { - nonexhaustive = true; - continue; - }; - let Some(ty) = info.r#type else { - nonexhaustive = true; - continue; - }; - match ty { - x if x == STR => s.field(info.name, &self.1.get_typed::<&str>(i).unwrap()), - x if x == BINARY => s.field(info.name, &self.1.get_typed::<&[u8]>(i).unwrap()), - x if x == OBJECT => s.field(info.name, &self.1.get_typed::<Object>(i).unwrap()), - x if x == U32 => s.field(info.name, &self.1.get_typed::<u32>(i).unwrap()), - x if x == U64 => s.field(info.name, &self.1.get_typed::<u64>(i).unwrap()), - x if x == I64 => s.field(info.name, &self.1.get_typed::<i64>(i).unwrap()), - _ => { - nonexhaustive = true; - &mut s - } - }; - } - if nonexhaustive { - s.finish_non_exhaustive() - } else { - s.finish() - } - } -} - -impl<T> Debug for Inspector<'_, TypedTag<T>> { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - let name = self.0.info(self.1.0).map(|t| t.name).unwrap_or("unknown"); - f.debug_tuple(&format!("TypedTag<{}>", type_name::<T>())) - .field(&name) - .finish() - } -} -impl Debug for Inspector<'_, Tag> { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - let name = self.0.info(self.1).map(|t| t.name).unwrap_or("unknown"); - f.debug_tuple("Tag").field(&name).finish() - } -} diff --git a/common/object/src/json.rs b/common/object/src/json.rs index 0aa4cbd..cbb8bda 100644 --- a/common/object/src/json.rs +++ b/common/object/src/json.rs @@ -4,36 +4,30 @@ Copyright (C) 2026 metamuffin <metamuffin.org> */ -use crate::{Object, Registry, types::*}; +use crate::{Object, ValueType}; use serde_json::{Map, Value}; -pub fn object_to_json(reg: &Registry, ob: Object<'_>) -> Value { +pub fn object_to_json(ob: Object<'_>) -> Value { let mut o = Map::new(); let mut nonexhaustive = false; for (i, tag) in ob.keys().enumerate() { - let Some(info) = reg.info(tag) else { - nonexhaustive = true; - continue; - }; - let Some(ty) = info.r#type else { - nonexhaustive = true; - continue; - }; - let key = info.name.to_string(); - - let val = match ty { - x if x == STR => ob.get_typed::<&str>(i).unwrap().to_string().into(), - x if x == OBJECT => object_to_json(reg, ob.get_typed::<Object>(i).unwrap()), - x if x == U32 => ob.get_typed::<u32>(i).unwrap().into(), - x if x == U64 => ob.get_typed::<u64>(i).unwrap().into(), - x if x == I64 => ob.get_typed::<i64>(i).unwrap().into(), - x if x == F64 => ob.get_typed::<f64>(i).unwrap().into(), + let kbytes = tag.0.to_be_bytes(); + let k = str::from_utf8(&kbytes).unwrap().to_string(); + let ty = ob.offset_type(i); + let sz = ob.size(i); + let val = match (ty, sz) { + (ValueType::String, _) => ob.get_typed::<&str>(i).unwrap().to_string().into(), + (ValueType::Object, _) => object_to_json(ob.get_typed::<Object>(i).unwrap()), + (ValueType::UInt, 4) => ob.get_typed::<u32>(i).unwrap().into(), + (ValueType::UInt, 8) => ob.get_typed::<u64>(i).unwrap().into(), + (ValueType::Int, 8) => ob.get_typed::<i64>(i).unwrap().into(), + (ValueType::Float, 8) => ob.get_typed::<f64>(i).unwrap().into(), _ => { nonexhaustive = true; continue; } }; - multi_insert(&mut o, key, val); + multi_insert(&mut o, k, val); } if nonexhaustive { o.insert("_nonexhaustive".to_owned(), Value::Bool(true)); diff --git a/common/object/src/lib.rs b/common/object/src/lib.rs index 771dd94..bd00639 100644 --- a/common/object/src/lib.rs +++ b/common/object/src/lib.rs @@ -6,7 +6,7 @@ #![feature(iter_array_chunks)] mod buffer; -pub mod inspect; +pub mod debug; #[cfg(feature = "json")] pub mod json; mod path; @@ -20,14 +20,30 @@ pub use path::*; pub use registry::*; pub use value::*; -use std::{collections::BTreeSet, hash::Hash, marker::PhantomData}; +use std::{collections::BTreeSet, fmt::Display, hash::Hash, marker::PhantomData}; #[repr(transparent)] -#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] +#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] pub struct Tag(pub u32); -#[derive(Debug, PartialEq, Eq, PartialOrd, Ord)] +impl Tag { + pub const fn new(fourcc: &[u8; 4]) -> Self { + Self(u32::from_be_bytes(*fourcc)) + } +} +impl Display for Tag { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + f.write_str(str::from_utf8(&self.0.to_be_bytes()).unwrap()) + } +} + +#[derive(PartialEq, Eq, PartialOrd, Ord)] pub struct TypedTag<T>(pub Tag, pub PhantomData<T>); +impl<T> Display for TypedTag<T> { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + self.0.fmt(f) + } +} impl<T> Clone for TypedTag<T> { fn clone(&self) -> Self { @@ -36,7 +52,7 @@ impl<T> Clone for TypedTag<T> { } impl<T> Copy for TypedTag<T> {} -#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq)] +#[derive(Clone, Copy, Hash, PartialEq, Eq)] pub struct Object<'a> { tags: &'a [u32], offsets: &'a [u32], @@ -89,33 +105,50 @@ impl<'a> Object<'a> { fn offset(&self, i: usize) -> usize { self.offsets .get(i) - .map(|&v| v >> 2) + .map(|&v| v >> 5) .unwrap_or(self.values.len() as u32) as usize } + fn offset_type(&self, i: usize) -> ValueType { + let raw = (self.offsets[i] >> 2) & 0b111; + ValueType::from_num(raw) + } + fn size(&self, i: usize) -> u32 { + let start_raw = self.offsets[i]; + let end_raw = self + .offsets + .get(i + 1) + .copied() + .unwrap_or((self.values.len() as u32) << 5); + + let u32_len = (end_raw >> 5) - (start_raw >> 5); + let padding = start_raw & 0b11; + u32_len * 4 - padding + } fn get_aligned(&self, index: usize) -> Option<&'a [u32]> { let start_raw = self.offsets[index]; let end_raw = self .offsets .get(index + 1) .copied() - .unwrap_or((self.values.len() as u32) << 2); + .unwrap_or((self.values.len() as u32) << 5); - let start = start_raw >> 2; - let end = end_raw >> 2; + let start = start_raw >> 5; + let end = end_raw >> 5; Some(&self.values[start as usize..end as usize]) } + fn get_unaligned(&self, index: usize) -> Option<&'a [u8]> { let start_raw = self.offsets[index]; let end_raw = self .offsets .get(index + 1) .copied() - .unwrap_or((self.values.len() as u32) << 2); + .unwrap_or((self.values.len() as u32) << 5); - let start = (start_raw >> 2) * 4; + let start = (start_raw >> 5) * 4; let padding = start_raw & 0b11; - let end = (end_raw >> 2) * 4 - padding; + let end = (end_raw >> 5) * 4 - padding; let values_u8: &[u8] = bytemuck::cast_slice(self.values); Some(&values_u8[start as usize..end as usize]) @@ -228,8 +261,9 @@ impl<'a> Object<'a> { let mut temp = Vec::new(); let values_new = buf.len(); for (i, val) in values.iter().enumerate() { - let off = (buf.len() as u32 - values_start) << 2; - if val.is_aligned() { + let ty = val.get_type(); + let off = (buf.len() as u32 - values_start) << 5 | (ty as u32) << 2; + if ty.is_aligned() { buf[new_offs + i] = off; val.store_aligned(&mut buf); } else { @@ -242,7 +276,7 @@ impl<'a> Object<'a> { } let values_insert_size = buf.len() - values_new; let values_cut_size = values_suffix - values_prefix; - let suffix_offset = (values_insert_size as i32 - values_cut_size as i32) * 4; + let suffix_offset = (values_insert_size as i32 - values_cut_size as i32) << 5; if suffix_offset != 0 { buf[suffix_offs..suffix_end] .iter_mut() diff --git a/common/object/src/registry.rs b/common/object/src/registry.rs index 5f1f36e..af028e8 100644 --- a/common/object/src/registry.rs +++ b/common/object/src/registry.rs @@ -4,8 +4,7 @@ Copyright (C) 2026 metamuffin <metamuffin.org> */ -use crate::Tag; -use std::{any::TypeId, collections::BTreeMap}; +use std::any::TypeId; pub mod types { use crate::Object; @@ -20,31 +19,6 @@ pub mod types { pub const F64: TypeId = TypeId::of::<f64>(); } -#[derive(Default, Clone)] -pub struct Registry { - tags: BTreeMap<Tag, TagInfo>, -} -impl Registry { - pub fn add(&mut self, tag: Tag, info: TagInfo) { - if let Some(other) = self.tags.get(&tag) { - panic!( - "Conflicting names for tag {}: {:?} vs {:?}", - tag.0, info.name, other.name - ) - } - self.tags.insert(tag, info); - } - pub fn info(&self, tag: Tag) -> Option<&TagInfo> { - self.tags.get(&tag) - } - pub fn name(&self, tag: Tag) -> &str { - match self.tags.get(&tag) { - Some(inf) => inf.name, - None => "unknown", - } - } -} - #[derive(Clone)] pub struct TagInfo { pub name: &'static str, @@ -53,19 +27,13 @@ pub struct TagInfo { #[macro_export] macro_rules! fields { - ($($id:ident: $type:ty = $tag:literal $name:literal;)*) => { - $(pub const $id: $crate::TypedTag<$type> = $crate::TypedTag($crate::Tag($tag), std::marker::PhantomData);)* - pub(crate) fn register_fields(reg: &mut $crate::Registry) { - $(reg.add($crate::Tag($tag), $crate::TagInfo { name: $name, r#type: Some(std::any::TypeId::of::<$type>()) });)* - } + ($($id:ident: $type:ty = $tag:literal;)*) => { + $(pub const $id: $crate::TypedTag<$type> = $crate::TypedTag($crate::Tag::new($tag), std::marker::PhantomData);)* }; } #[macro_export] macro_rules! enums { - ($($id:ident = $tag:literal $name:literal;)*) => { - $(pub const $id: $crate::Tag = $crate::Tag($tag);)* - pub(crate) fn register_enums(reg: &mut $crate::Registry) { - $(reg.add($crate::Tag($tag), $crate::TagInfo { name: $name, r#type: None });)* - } + ($($id:ident = $tag:literal;)*) => { + $(pub const $id: $crate::Tag = $crate::Tag::new($tag);)* }; } diff --git a/common/object/src/tests.rs b/common/object/src/tests.rs index 616ac69..73f7b6f 100644 --- a/common/object/src/tests.rs +++ b/common/object/src/tests.rs @@ -4,19 +4,13 @@ Copyright (C) 2026 metamuffin <metamuffin.org> */ -use crate::{Object, ObjectBuffer, Registry, fields, inspect::Inspector}; -use std::sync::LazyLock; +use crate::{Object, ObjectBuffer, fields}; -pub static TAGREG: LazyLock<Registry> = LazyLock::new(|| { - let mut reg = Registry::default(); - register_fields(&mut reg); - reg -}); fields! { - NAME: &str = 15 "name"; - AGE: u32 = 13 "age"; - FRIEND: &str = 54321 "friend"; - STUFF: Object = 3 "stuff"; + NAME: &str = b"name"; + AGE: u32 = b"age1"; + FRIEND: &str = b"frnd"; + STUFF: Object = b"stff"; } fn test_object() -> ObjectBuffer { @@ -86,21 +80,9 @@ fn insert_empty() { } #[test] -fn inspect_object() { - let bob = test_object(); - eprintln!("{:#?}", Inspector(&TAGREG, bob.as_object())); - // panic!() -} - -#[test] -fn inspect_tag() { - assert_eq!( - format!("{:?}", Inspector(&TAGREG, FRIEND)), - "TypedTag<&str>(\"friend\")" - ); +fn debug() { assert_eq!( - format!("{:?}", Inspector(&TAGREG, AGE)), - "TypedTag<u32>(\"age\")" + format!("{:?}", test_object()), + "Object { age1: 35, frnd: \"Alice\", frnd: \"Charlie\", name: \"Bob\" }" ); - assert_eq!(format!("{:?}", Inspector(&TAGREG, NAME.0)), "Tag(\"name\")"); } diff --git a/common/object/src/value.rs b/common/object/src/value.rs index 733e3a0..eb9de7c 100644 --- a/common/object/src/value.rs +++ b/common/object/src/value.rs @@ -17,8 +17,44 @@ pub trait Value<'a>: ValueStore + Sized { unimplemented!() } } + +#[derive(Debug, Clone, Copy, PartialEq, Eq)] +pub enum ValueType { + Binary, + String, + Object, + UInt, + Int, + Tag, + Float, + Bool, +} + +impl ValueType { + #[inline] + pub fn is_aligned(self) -> bool { + match self { + ValueType::Binary | ValueType::String => false, + _ => true, + } + } + pub fn from_num(n: u32) -> Self { + match n { + 0 => Self::Binary, + 1 => Self::String, + 2 => Self::Object, + 3 => Self::UInt, + 4 => Self::Int, + 5 => Self::Tag, + 6 => Self::Float, + 7 => Self::Bool, + _ => unreachable!(), + } + } +} + pub trait ValueStore { - fn is_aligned(&self) -> bool; + fn get_type(&self) -> ValueType; fn store_aligned(&self, _buf: &mut Vec<u32>) {} fn store_unaligned(&self, _buf: &mut Vec<u8>) {} fn size(&self) -> usize; @@ -30,8 +66,8 @@ impl<'a> Value<'a> for &'a str { } } impl ValueStore for &str { - fn is_aligned(&self) -> bool { - false + fn get_type(&self) -> ValueType { + ValueType::String } fn store_unaligned(&self, buf: &mut Vec<u8>) { buf.extend(self.as_bytes()); @@ -47,8 +83,8 @@ impl Value<'_> for u32 { } } impl ValueStore for u32 { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::UInt } fn store_aligned(&self, buf: &mut Vec<u32>) { buf.push(self.to_be()); @@ -64,8 +100,8 @@ impl Value<'_> for Tag { } } impl ValueStore for Tag { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::String } fn store_aligned(&self, buf: &mut Vec<u32>) { buf.push(self.0.to_be()); @@ -83,8 +119,8 @@ impl Value<'_> for u64 { } } impl ValueStore for u64 { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::UInt } fn store_aligned(&self, buf: &mut Vec<u32>) { buf.push(((self >> 32) as u32).to_be()); @@ -108,8 +144,8 @@ impl Value<'_> for f64 { } } impl ValueStore for f64 { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::Float } fn store_aligned(&self, buf: &mut Vec<u32>) { let b = self.to_be_bytes(); @@ -127,8 +163,8 @@ impl Value<'_> for i64 { } } impl ValueStore for i64 { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::Int } fn store_aligned(&self, buf: &mut Vec<u32>) { (*self as u64).store_aligned(buf); @@ -144,8 +180,8 @@ impl<'a> Value<'a> for Object<'a> { } } impl ValueStore for Object<'_> { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::Object } fn store_aligned(&self, buf: &mut Vec<u32>) { buf.push(self.tags.len() as u32); @@ -158,8 +194,8 @@ impl ValueStore for Object<'_> { } } impl ValueStore for ObjectBuffer { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::Object } fn store_aligned(&self, buf: &mut Vec<u32>) { buf.extend(&self.0); @@ -175,8 +211,8 @@ impl<'a> Value<'a> for &'a [u8] { } } impl ValueStore for &[u8] { - fn is_aligned(&self) -> bool { - false + fn get_type(&self) -> ValueType { + ValueType::Binary } fn store_unaligned(&self, buf: &mut Vec<u8>) { buf.extend(*self); @@ -192,8 +228,8 @@ impl<'a> Value<'a> for () { } } impl ValueStore for () { - fn is_aligned(&self) -> bool { - true + fn get_type(&self) -> ValueType { + ValueType::Binary } fn store_aligned(&self, _buf: &mut Vec<u32>) {} fn size(&self) -> usize { diff --git a/common/src/api.rs b/common/src/api.rs index 2aac57b..13962a3 100644 --- a/common/src/api.rs +++ b/common/src/api.rs @@ -7,54 +7,54 @@ use jellyobject::{Object, Tag, enums, fields}; fields! { - QUERY_PARENT: u64 = 2000 "parent"; - QUERY_SEARCH: &str = 2001 "search"; - QUERY_KIND: Tag = 2004 "kind"; // multi - QUERY_SORT: Tag = 2002 "sort"; // one of RTYP_*, NU_RATING, NO_DURATION, NO_NAME - QUERY_SORT_ASCENDING: () = 2003 "sort_ascending"; + QUERY_PARENT: u64 = b"prnt"; + QUERY_SEARCH: &str = b"sear"; + QUERY_KIND: Tag = b"kind"; // multi + QUERY_SORT: Tag = b"sort"; // one of RTYP_*, NU_RATING, NO_DURATION, NO_NAME + QUERY_SORT_ASCENDING: () = b"sasc"; - VIEW_TITLE: &str = 2005 "title"; - VIEW_MESSAGE: Object = 2010 "message"; - VIEW_NODE_PAGE: Object = 2011 "node_page"; - VIEW_NODE_LIST: Object = 2012 "node_list"; // multi - VIEW_PLAYER: u64 = 2028 "player"; - VIEW_STATGROUP: Object = 2041 "statgroup"; - VIEW_STATTEXT: Object = 2042 "stattext"; - VIEW_ACCOUNT_LOGIN: () = 2043 "account_login"; - VIEW_ACCOUNT_LOGOUT: () = 2044 "account_logout"; - VIEW_ACCOUNT_SET_PASSWORD: &str = 2045 "account_set_password"; - VIEW_ADMIN_DASHBOARD: () = 2046 "admin_dashboard"; - VIEW_ADMIN_IMPORT: Object = 2047 "admin_import"; + VIEW_TITLE: &str = b"titl"; + VIEW_MESSAGE: Object = b"mesg"; + VIEW_NODE_PAGE: Object = b"npag"; + VIEW_NODE_LIST: Object = b"nlis"; // multi + VIEW_PLAYER: u64 = b"play"; + VIEW_STATGROUP: Object = b"stag"; + VIEW_STATTEXT: Object = b"stat"; + VIEW_ACCOUNT_LOGIN: () = b"acli"; + VIEW_ACCOUNT_LOGOUT: () = b"aclo"; + VIEW_ACCOUNT_SET_PASSWORD: &str = b"acsp"; + VIEW_ADMIN_DASHBOARD: () = b"adda"; + VIEW_ADMIN_IMPORT: Object = b"adim"; - ADMIN_IMPORT_BUSY: () = 2048 "busy"; - ADMIN_IMPORT_ERROR: &str = 2049 "error"; // multi + ADMIN_IMPORT_BUSY: () = b"busy"; + ADMIN_IMPORT_ERROR: &str = b"erro"; // multi - NKU_NODE: Object = 2025 "node"; - NKU_UDATA: Object = 2026 "udata"; - NKU_ROLE: &str = 2027 "role"; + NKU_NODE: Object = b"node"; + NKU_UDATA: Object = b"udat"; + NKU_ROLE: &str = b"role"; - NODELIST_TITLE: &str = 2007 "title"; - NODELIST_DISPLAYSTYLE: Tag = 2008 "displaystyle"; - NODELIST_ITEM: Object = 2009 "item"; + NODELIST_TITLE: &str = b"titl"; + NODELIST_DISPLAYSTYLE: Tag = b"dsty"; + NODELIST_ITEM: Object = b"item"; - MESSAGE_KIND: &str = 2029 "kind"; - MESSAGE_TEXT: &str = 2030 "text"; + MESSAGE_KIND: &str = b"kind"; + MESSAGE_TEXT: &str = b"text"; - STATGROUP_TITLE: &str = 2039 "title"; - STATGROUP_BIN: Object = 2040 "bin"; + STATGROUP_TITLE: &str = b"titl"; + STATGROUP_BIN: Object = b"bin1"; - STAT_NAME: &str = 2038 "name"; - STAT_COUNT: u64 = 2031 "count"; - STAT_TOTAL_SIZE: u64 = 2032 "total_size"; - STAT_TOTAL_DURATION: f64 = 2033 "total_duration"; - STAT_MAX_SIZE: u64 = 2036 "max_size"; - STAT_MAX_DURATION: f64 = 2037 "max_duration"; + STAT_NAME: &str = b"name"; + STAT_COUNT: u64 = b"cont"; + STAT_TOTAL_SIZE: u64 = b"tlsz"; + STAT_TOTAL_DURATION: f64 = b"tldu"; + STAT_MAX_SIZE: u64 = b"mxsz"; + STAT_MAX_DURATION: f64 = b"mxdu"; } enums! { - NLSTYLE_GRID = 1023 "grid"; - NLSTYLE_INLINE = 1024 "inline"; - NLSTYLE_LIST = 1025 "list"; + NLSTYLE_GRID = b"grid"; + NLSTYLE_INLINE = b"inli"; + NLSTYLE_LIST = b"list"; } // use crate::user::{NodeUserData, User}; diff --git a/common/src/internal.rs b/common/src/internal.rs index 94876f1..58a2dae 100644 --- a/common/src/internal.rs +++ b/common/src/internal.rs @@ -7,6 +7,6 @@ use jellyobject::fields; fields! { - IM_PATH: &str = 0x11001 "path"; - IM_MTIME: u64 = 0x11002 "mtime"; + IM_PATH: &str = b"Ipth"; + IM_MTIME: u64 = b"Imtm"; } diff --git a/common/src/lib.rs b/common/src/lib.rs index 4f8ffca..d94c72c 100644 --- a/common/src/lib.rs +++ b/common/src/lib.rs @@ -15,24 +15,3 @@ pub use jellystream_types as stream; pub use api::*; pub use node::*; pub use user::*; - -use jellyobject::{Registry, TypedTag}; -use std::sync::LazyLock; - -pub static TAGREG: LazyLock<Registry> = LazyLock::new(|| { - let mut reg = Registry::default(); - node::register_fields(&mut reg); - node::register_enums(&mut reg); - user::register_fields(&mut reg); - api::register_fields(&mut reg); - api::register_enums(&mut reg); - internal::register_fields(&mut reg); - reg -}); - -#[test] -fn check_tag_conflicts() { - let _ = &*TAGREG; -} - -pub struct Identifier(pub TypedTag<&'static str>, pub String); diff --git a/common/src/node.rs b/common/src/node.rs index 60544e2..42e07ca 100644 --- a/common/src/node.rs +++ b/common/src/node.rs @@ -9,125 +9,123 @@ use jellyobject::{Object, Tag, enums, fields}; fields! { // Tag counter: 111 - NO_KIND: Tag = 1 "kind"; - NO_TITLE: &str = 2 "title"; - NO_PARENT: u64 = 3 "parent"; // multi - NO_SUBTITLE: &str = 38 "subtitle"; - NO_TAGLINE: &str = 4 "tagline"; - NO_DESCRIPTION: &str = 5 "description"; - NO_RELEASEDATE: i64 = 6 "releasedate"; - NO_DURATION: f64 = 39 "duration"; - NO_INDEX: u64 = 7 "index"; - NO_SEASON_INDEX: u64 = 8 "season_index"; - NO_TRACK: Object = 9 "track"; // multi - NO_CHAPTER: Object = 32 "chapter"; // multi - NO_TAG: &str = 10 "tag"; // multi - NO_RATINGS: Object = 11 "ratings"; - NO_PICTURES: Object = 12 "pictures"; - NO_IDENTIFIERS: Object = 13 "identifiers"; - NO_VISIBILITY: Tag = 14 "visibility"; - NO_STORAGE_SIZE: u64 = 15 "storage_size"; - NO_CREDIT: Object = 33 "credit"; // multi - NO_SLUG: &str = 37 "slug"; + NO_KIND: Tag = b"kind"; + NO_TITLE: &str = b"titl"; + NO_PARENT: u64 = b"prnt"; // multi + NO_SUBTITLE: &str = b"sbtl"; + NO_TAGLINE: &str = b"tgln"; + NO_DESCRIPTION: &str = b"desc"; + NO_RELEASEDATE: i64 = b"rldt"; + NO_DURATION: f64 = b"durn"; + NO_INDEX: u64 = b"indx"; + NO_SEASON_INDEX: u64 = b"sidx"; + NO_TRACK: Object = b"trak"; // multi + NO_CHAPTER: Object = b"chpt"; // multi + NO_TAG: &str = b"tag1"; // multi + NO_RATINGS: Object = b"rtng"; + NO_PICTURES: Object = b"pict"; + NO_IDENTIFIERS: Object = b"iden"; + NO_VISIBILITY: Tag = b"visi"; + NO_STORAGE_SIZE: u64 = b"stsz"; + NO_CREDIT: Object = b"crdt"; // multi + NO_SLUG: &str = b"slug"; - CR_NODE: u64 = 34 "node"; - CR_KIND: Tag = 35 "kind"; - CR_ROLE: &str = 36 "role"; // multi + CR_NODE: u64 = b"node"; + CR_KIND: Tag = b"kind"; + CR_ROLE: &str = b"role"; // multi - TR_KIND: Tag = 16 "kind"; - TR_SOURCE: Object = 17 "source"; - TR_NAME: &str = 18 "name"; - TR_CODEC: &str = 19 "codec"; - TR_LANGUAGE: &str = 20 "language"; // BCP 47 - TR_RATE: f64 = 23 "rate"; - TR_BIT_DEPTH: u32 = 25 "bit_depth"; - TR_CHANNELS: u32 = 28 "channels"; - TR_PIXEL_WIDTH: u32 = 26 "pixel_width"; - TR_PIXEL_HEIGHT: u32 = 27 "pixel_height"; + TR_KIND: Tag = b"kind"; + TR_SOURCE: Object = b"sour"; + TR_NAME: &str = b"name"; + TR_CODEC: &str = b"codc"; + TR_LANGUAGE: &str = b"lang"; // BCP 47 + TR_RATE: f64 = b"rate"; + TR_BIT_DEPTH: u32 = b"bdep"; + TR_CHANNELS: u32 = b"chnl"; + TR_PIXEL_WIDTH: u32 = b"pwid"; + TR_PIXEL_HEIGHT: u32 = b"phei"; - TRSOURCE_LOCAL_PATH: &str = 21 "local_path"; - TRSOURCE_LOCAL_TRACKNUM: u64 = 22 "local_tracknum"; + TRSOURCE_LOCAL_PATH: &str = b"lpat"; + TRSOURCE_LOCAL_TRACKNUM: u64 = b"ltrn"; - CH_START: f64 = 29 "start"; - CH_END: f64 = 30 "end"; - CH_NAME: &str = 31 "name"; + CH_START: f64 = b"strt"; + CH_END: f64 = b"end1"; + CH_NAME: &str = b"name"; - PICT_COVER: &str = 45 "cover"; - PICT_BACKDROP: &str = 46 "backdrop"; + PICT_COVER: &str = b"covr"; + PICT_BACKDROP: &str = b"bdro"; - RTYP_IMDB: f64 = 47 "imdb"; - RTYP_TMDB: f64 = 48 "tmdb"; - RTYP_ROTTEN_TOMATOES: f64 = 49 "rotten_tomatoes"; - RTYP_METACRITIC: f64 = 50 "metacritic"; - RTYP_YOUTUBE_VIEWS: f64 = 51 "youtube_views"; - RTYP_YOUTUBE_LIKES: f64 = 52 "youtube_likes"; - RTYP_YOUTUBE_FOLLOWERS: f64 = 53 "youtube_followers"; - RTYP_TRAKT: f64 = 54 "trakt"; + RTYP_IMDB: f64 = b"imdb"; + RTYP_TMDB: f64 = b"tmdb"; + RTYP_ROTTEN_TOMATOES: f64 = b"rtom"; + RTYP_METACRITIC: f64 = b"mcri"; + RTYP_YOUTUBE_VIEWS: f64 = b"ytvi"; + RTYP_YOUTUBE_LIKES: f64 = b"ytli"; + RTYP_YOUTUBE_SUBSCRIBERS: f64 = b"ytsu"; + RTYP_TRAKT: f64 = b"trkt"; - IDENT_MUSICBRAINZ_RECORDING: &str = 55 "musicbrainz_recording"; - IDENT_MUSICBRAINZ_ARTIST: &str = 56 "musicbrainz_artist"; - IDENT_MUSICBRAINZ_RELEASE: &str = 57 "musicbrainz_release"; - IDENT_MUSICBRAINZ_RELEASE_GROUP: &str = 58 "musicbrainz_release_group"; - IDENT_ACOUST_ID_TRACK: &str = 59 "acoust_id_track"; - IDENT_YOUTUBE_VIDEO: &str = 60 "youtube_video"; - IDENT_YOUTUBE_CHANNEL: &str = 61 "youtube_channel"; - IDENT_YOUTUBE_CHANNEL_HANDLE: &str = 62 "youtube_channel_handle"; - IDENT_BANDCAMP: &str = 63 "bandcamp"; - IDENT_ISRC: &str = 64 "isrc"; - IDENT_BARCODE: &str = 65 "barcode"; - IDENT_TRAKT_MOVIE: &str = 66 "trakt_movie"; - IDENT_TRAKT_SHOW: &str = 67 "trakt_show"; - IDENT_TRAKT_SEASON: &str = 68 "trakt_season"; - IDENT_TRAKT_EPISODE: &str = 69 "trakt_episode"; - IDENT_IMDB: &str = 70 "imdb"; - IDENT_TMDB_SERIES: &str = 71 "tmdb_series"; - IDENT_TMDB_MOVIE: &str = 72 "tmdb_movie"; - IDENT_TVDB: &str = 73 "tvdb"; - IDENT_OMDB: &str = 74 "omdb"; - IDENT_VGMDB_ARTIST: &str = 75 "vgmdb_artist"; + IDENT_MUSICBRAINZ_RECORDING: &str = b"mbrc"; + IDENT_MUSICBRAINZ_ARTIST: &str = b"mbar"; + IDENT_MUSICBRAINZ_RELEASE: &str = b"mbrl"; + IDENT_MUSICBRAINZ_RELEASE_GROUP: &str = b"mbrg"; + IDENT_ACOUST_ID_TRACK: &str = b"actr"; + IDENT_YOUTUBE_VIDEO: &str = b"ytvi"; + IDENT_YOUTUBE_CHANNEL: &str = b"ytc1"; + IDENT_YOUTUBE_CHANNEL_HANDLE: &str = b"ytch"; + IDENT_BANDCAMP: &str = b"bcmp"; + IDENT_ISRC: &str = b"isrc"; + IDENT_BARCODE: &str = b"barc"; + IDENT_TRAKT_MOVIE: &str = b"trmv"; + IDENT_TRAKT_SHOW: &str = b"trsh"; + IDENT_TRAKT_SEASON: &str = b"trse"; + IDENT_TRAKT_EPISODE: &str = b"trep"; + IDENT_IMDB: &str = b"imdb"; + IDENT_TMDB_SERIES: &str = b"tmse"; + IDENT_TMDB_MOVIE: &str = b"tmmv"; + IDENT_TVDB: &str = b"tvdb"; + IDENT_OMDB: &str = b"omdb"; + IDENT_VGMDB_ARTIST: &str = b"vgar"; } -pub type Kind = Tag; - enums! { - VISI_HIDDEN = 76 "hidden"; - VISI_REDUCED = 77 "reduced"; - VISI_VISIBLE = 78 "visible"; + VISI_HIDDEN = b"hidn"; + VISI_REDUCED = b"rdcd"; + VISI_VISIBLE = b"visi"; - TRKIND_VIDEO = 79 "video"; - TRKIND_AUDIO = 80 "audio"; - TRKIND_TEXT = 81 "text"; - TRKIND_UNKNOWN = 82 "unknown"; + TRKIND_VIDEO = b"vide"; + TRKIND_AUDIO = b"audi"; + TRKIND_TEXT = b"text"; + TRKIND_UNKNOWN = b"unkn"; - KIND_MOVIE = 83 "movie"; - KIND_VIDEO = 84 "video"; - KIND_MUSIC = 85 "music"; - KIND_SHORTFORMVIDEO = 86 "shortformvideo"; - KIND_COLLECTION = 87 "collection"; - KIND_CHANNEL = 88 "channel"; - KIND_SHOW = 89 "show"; - KIND_SERIES = 90 "series"; - KIND_SEASON = 91 "season"; - KIND_EPISODE = 92 "episode"; + KIND_MOVIE = b"movi"; + KIND_VIDEO = b"vide"; + KIND_MUSIC = b"musi"; + KIND_SHORTFORMVIDEO = b"sfvi"; + KIND_COLLECTION = b"coll"; + KIND_CHANNEL = b"chnl"; + KIND_SHOW = b"show"; + KIND_SERIES = b"seri"; + KIND_SEASON = b"sesn"; + KIND_EPISODE = b"epsd"; - CRCAT_CAST = 93 "cast"; - CRCAT_WRITING = 94 "writing"; - CRCAT_DIRECTING = 95 "directing"; - CRCAT_ART = 96 "art"; - CRCAT_SOUND = 97 "sound"; - CRCAT_CAMERA = 98 "camera"; - CRCAT_LIGHTING = 99 "lighting"; - CRCAT_CREW = 100 "crew"; - CRCAT_EDITING = 101 "editing"; - CRCAT_PRODUCTION = 102 "production"; - CRCAT_VFX = 0x200b "vfx"; - CRCAT_COSTUME_MAKEUP = 103 "costume_makeup"; - CRCAT_CREATED_BY = 104 "created_by"; - CRCAT_PERFORMANCE = 105 "performance"; - CRCAT_INSTRUMENT = 106 "instrument"; - CRCAT_VOCAL = 107 "vocal"; - CRCAT_ARRANGER = 108 "arranger"; - CRCAT_PRODUCER = 109 "producer"; - CRCAT_ENGINEER = 110 "engineer"; + CRCAT_CAST = b"cast"; + CRCAT_WRITING = b"writ"; + CRCAT_DIRECTING = b"dire"; + CRCAT_ART = b"art1"; + CRCAT_SOUND = b"sond"; + CRCAT_CAMERA = b"came"; + CRCAT_LIGHTING = b"ligh"; + CRCAT_CREW = b"crew"; + CRCAT_EDITING = b"edit"; + CRCAT_PRODUCTION = b"prod"; + CRCAT_VFX = b"vfx1"; + CRCAT_COSTUME_MAKEUP = b"coma"; + CRCAT_CREATED_BY = b"crby"; + CRCAT_PERFORMANCE = b"perf"; + CRCAT_INSTRUMENT = b"inst"; + CRCAT_VOCAL = b"voca"; + CRCAT_ARRANGER = b"arra"; + CRCAT_PRODUCER = b"pro2"; + CRCAT_ENGINEER = b"engi"; } diff --git a/common/src/user.rs b/common/src/user.rs index 47716da..fcb8eea 100644 --- a/common/src/user.rs +++ b/common/src/user.rs @@ -7,11 +7,11 @@ use jellyobject::fields; fields! { - USER_LOGIN: &str = 1001 "login"; - USER_PASSWORD: &[u8] = 1002 "password"; - USER_NAME: &str = 1003 "name"; - USER_ADMIN: () = 1004 "admin"; + USER_LOGIN: &str = b"Ulgn"; + USER_PASSWORD: &[u8] = b"Upwd"; + USER_NAME: &str = b"Unam"; + USER_ADMIN: () = b"Uadm"; - UDATA_WATCHED: () = 1005 "watched"; - UDATA_RATING: f64 = 1006 "rating"; + UDATA_WATCHED: () = b"Dwat"; + UDATA_RATING: f64 = b"Drat"; } diff --git a/database/src/kv/mod.rs b/database/src/kv/mod.rs index 90b6686..f5dcc72 100644 --- a/database/src/kv/mod.rs +++ b/database/src/kv/mod.rs @@ -17,7 +17,7 @@ pub mod tests; use std::borrow::Cow; use crate::{ - DEBUG_TAGREG, Database, Query, RowNum, Transaction, + Database, Query, RowNum, Transaction, kv::{ helpers::{read_counter, write_counter}, index::{iter_index, read_count_index, update_index}, @@ -27,7 +27,7 @@ use crate::{ }, }; use anyhow::{Result, anyhow}; -use jellyobject::{ObjectBuffer, inspect::Inspector}; +use jellyobject::ObjectBuffer; use log::{debug, info}; pub type SubtreeNum = u32; @@ -47,9 +47,7 @@ impl<T: jellykv::Store> Database for T { impl Transaction for &mut dyn jellykv::Transaction { fn insert(&mut self, entry: ObjectBuffer) -> Result<RowNum> { - if let Some(tr) = DEBUG_TAGREG.get() { - debug!("insert {:?}", Inspector(tr, entry.as_object())) - } + debug!("insert {entry:?}"); let mut id_counter = read_counter(*self, &T_ROW_COUNTER.to_be_bytes(), 0)?; let row = id_counter; id_counter += 1; @@ -105,7 +103,7 @@ impl Transaction for &mut dyn jellykv::Transaction { &'a mut self, query: Query, ) -> Result<Box<dyn Iterator<Item = Result<(RowNum, Vec<u8>)>> + 'a>> { - debug!("query: {}", query.show_debug()); + debug!("query: {}", query.show()); let mut prefixes = Vec::new(); for (binning, mut prefix) in query.filter.get_bins() { let ik = IndexKey(binning, query.sort.key()); diff --git a/database/src/lib.rs b/database/src/lib.rs index 984502e..9b76c58 100644 --- a/database/src/lib.rs +++ b/database/src/lib.rs @@ -8,12 +8,8 @@ pub mod query_ser; #[cfg(test)] pub mod test_shared; -use std::sync::OnceLock; - use anyhow::Result; -use jellyobject::{ObjectBuffer, Path, Registry}; - -pub static DEBUG_TAGREG: OnceLock<Registry> = OnceLock::new(); +use jellyobject::{ObjectBuffer, Path}; pub type RowNum = u64; pub type RowIter = Box<dyn Iterator<Item = Result<(RowNum, Vec<u8>)>>>; diff --git a/database/src/query_ser.rs b/database/src/query_ser.rs index 498f2ad..d76dea7 100644 --- a/database/src/query_ser.rs +++ b/database/src/query_ser.rs @@ -4,37 +4,30 @@ Copyright (C) 2026 metamuffin <metamuffin.org> */ -use crate::{DEBUG_TAGREG, Filter, MultiBehaviour, Query, Sort, SortOrder}; -use jellyobject::{Path, Registry, Tag}; +use crate::{Filter, MultiBehaviour, Query, Sort, SortOrder}; +use jellyobject::{Path, Tag}; impl Query { - pub fn show_debug(&self) -> String { - if let Some(r) = DEBUG_TAGREG.get() { - self.show(r) - } else { - "[debug tag registry disabled]".to_string() - } - } - pub fn show(&self, reg: &Registry) -> String { + pub fn show(&self) -> String { let mut o = String::new(); if !matches!(self.filter, Filter::True) { - o += &format!("FILTER {} ", self.filter.show(reg)) + o += &format!("FILTER {} ", self.filter.show()) } if !matches!(self.sort, Sort::None) { - o += &format!("SORT {} ", self.sort.show(reg)) + o += &format!("SORT {} ", self.sort.show()) } o } } impl Filter { - pub fn show(&self, reg: &Registry) -> String { + pub fn show(&self) -> String { match self { Filter::True => "TRUE".to_string(), Filter::All(filters) => format!( "({})", filters .iter() - .map(|f| f.show(reg)) + .map(|f| f.show()) .collect::<Vec<_>>() .join(" AND ") ), @@ -42,23 +35,23 @@ impl Filter { "({})", filters .iter() - .map(|f| f.show(reg)) + .map(|f| f.show()) .collect::<Vec<_>>() .join(" OR ") ), Filter::Match(path, value) => { format!( "{} = {}", - show_path(reg, path), - show_value(reg, *path.0.last().unwrap(), value) + show_path(path), + show_value(*path.0.last().unwrap(), value) ) } - Filter::Has(path) => show_path(reg, path), + Filter::Has(path) => show_path(path), } } } impl Sort { - pub fn show(&self, reg: &Registry) -> String { + pub fn show(&self) -> String { match self { Sort::None => "NONE".to_string(), Sort::Value(vs) => { @@ -75,36 +68,23 @@ impl Sort { MultiBehaviour::Max => "MAX", MultiBehaviour::Min => "MIN", }, - show_path(reg, &vs.path), + show_path(&vs.path), ) } Sort::TextSearch(path, value) => { - format!("TEXT SEARCH {} = {value:?}", show_path(reg, path),) + format!("TEXT SEARCH {} = {value:?}", show_path(path),) } } } } -fn show_path(reg: &Registry, path: &Path) -> String { +fn show_path(path: &Path) -> String { path.0 .iter() - .map(|s| reg.name(*s)) + .map(|s| str::from_utf8(&s.0.to_be_bytes()).unwrap().to_string()) .collect::<Vec<_>>() .join(".") } -fn show_value(reg: &Registry, tag: Tag, value: &[u8]) -> String { - if let Some(info) = reg.info(tag) - && let Some(ty) = info.r#type - { - use jellyobject::types::*; - match () { - () if ty == STR => format!("{:?}", str::from_utf8(value).unwrap()), - () if ty == U32 => format!("{:?}", u32::from_be_bytes(value.try_into().unwrap())), - () if ty == U64 => format!("{:?}", u64::from_be_bytes(value.try_into().unwrap())), - () if ty == F64 => format!("{:?}", f64::from_be_bytes(value.try_into().unwrap())), - () => format!("{value:?}"), - } - } else { - format!("{value:?}") - } +fn show_value(_tag: Tag, value: &[u8]) -> String { + format!("{value:?}") // TODO } diff --git a/database/src/test_shared.rs b/database/src/test_shared.rs index 8216113..81d2e60 100644 --- a/database/src/test_shared.rs +++ b/database/src/test_shared.rs @@ -4,21 +4,12 @@ Copyright (C) 2026 metamuffin <metamuffin.org> */ -use jellyobject::{ObjectBuffer, Registry, fields}; -use std::sync::LazyLock; +use jellyobject::{ObjectBuffer, fields}; -use crate::DEBUG_TAGREG; - -pub static TAGREG: LazyLock<Registry> = LazyLock::new(|| { - let mut reg = Registry::default(); - register_fields(&mut reg); - DEBUG_TAGREG.set(reg.clone()).ok().unwrap(); - reg -}); fields! { - NAME: &str = 15 "name"; - AGE: u32 = 13 "age"; - FRIEND: &str = 54321 "friend"; + NAME: &str = b"name"; + AGE: u32 = b"age1"; + FRIEND: &str = b"frnd"; } pub(crate) fn new_bob() -> ObjectBuffer { diff --git a/import/src/plugins/infojson.rs b/import/src/plugins/infojson.rs index a48fca5..abfadc0 100644 --- a/import/src/plugins/infojson.rs +++ b/import/src/plugins/infojson.rs @@ -194,7 +194,7 @@ impl ImportPlugin for Infojson { } if let Some(followers) = data.channel_follower_count { node = node.as_object().update(NO_RATINGS, |rat| { - rat.insert(RTYP_YOUTUBE_FOLLOWERS, followers as f64) + rat.insert(RTYP_YOUTUBE_SUBSCRIBERS, followers as f64) }); } diff --git a/import/src/plugins/misc.rs b/import/src/plugins/misc.rs index ea5054e..309e0b1 100644 --- a/import/src/plugins/misc.rs +++ b/import/src/plugins/misc.rs @@ -6,7 +6,7 @@ use crate::plugins::{ImportPlugin, PluginContext, PluginInfo}; use anyhow::{Context, Result, bail}; use jellycache::HashKey; -use jellycommon::{jellyobject::inspect::Inspector, *}; +use jellycommon::*; use jellydb::RowNum; use jellyremuxer::matroska::{AttachedFile, Segment}; use log::info; @@ -29,13 +29,9 @@ impl ImportPlugin for ImageFiles { "backdrop.jpeg" | "backdrop.webp" | "backdrop.png" => PICT_BACKDROP, _ => return Ok(()), }; - info!("import {:?} at {path:?}", Inspector(&TAGREG, slot)); + info!("import {slot} at {path:?}"); let asset = ct.ic.cache.store( - format!( - "media/literal/{}-{}.image", - HashKey(path), - TAGREG.name(slot.0) - ), + format!("media/literal/{}-{slot}.image", HashKey(path)), || { let mut data = Vec::new(); File::open(path)?.read_to_end(&mut data)?; diff --git a/server/src/main.rs b/server/src/main.rs index b180d79..335b960 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -14,7 +14,7 @@ use crate::{ use anyhow::{Result, anyhow}; use jellycache::Cache; use jellycommon::{ - TAGREG, USER_ADMIN, USER_LOGIN, USER_PASSWORD, + USER_ADMIN, USER_LOGIN, USER_PASSWORD, jellyobject::{ObjectBuffer, Path}, }; use jellydb::{Database, Filter, Query, Sort}; @@ -37,8 +37,6 @@ pub mod ui_responder; #[rocket::main] async fn main() { setup_logger(); - jellydb::DEBUG_TAGREG.set(TAGREG.clone()).ok().unwrap(); - let state = match create_state() { Ok(s) => s, Err(e) => { diff --git a/server/src/ui_responder.rs b/server/src/ui_responder.rs index aed91a2..7333175 100644 --- a/server/src/ui_responder.rs +++ b/server/src/ui_responder.rs @@ -6,7 +6,6 @@ use crate::request_info::RequestInfo; use jellycommon::{ - TAGREG, jellyobject::{ObjectBuffer, json::object_to_json}, }; use jellyui::render_view; @@ -24,7 +23,7 @@ pub enum UiResponse { impl RequestInfo<'_> { pub fn respond_ui(&self, view: ObjectBuffer) -> UiResponse { if self.debug == "json" { - let value = object_to_json(&TAGREG, view.as_object()); + let value = object_to_json(view.as_object()); UiResponse::Json(serde_json::to_string(&value).unwrap()) } else if self.debug == "raw" { UiResponse::Object(view) diff --git a/ui/src/components/node_page.rs b/ui/src/components/node_page.rs index 921f65d..17e923c 100644 --- a/ui/src/components/node_page.rs +++ b/ui/src/components/node_page.rs @@ -119,7 +119,7 @@ markup::define! { table { @for (key, value) in idents.entries::<&str>() { tr { tr { - td { @tr(ri.lang, &format!("id.{}", TAGREG.name(key))) } + td { @tr(ri.lang, &format!("id.{key}")) } @if let Some(url) = external_id_url(key, value) { td { a[href=url] { pre { @value } } } } else { diff --git a/ui/src/components/props.rs b/ui/src/components/props.rs index fa078e7..8f7bfc3 100644 --- a/ui/src/components/props.rs +++ b/ui/src/components/props.rs @@ -46,7 +46,7 @@ markup::define! { @match TypedTag(kind, PhantomData) { RTYP_YOUTUBE_LIKES => {p.likes{ @format_count(value as usize) " Likes" }} RTYP_YOUTUBE_VIEWS => {p{ @format_count(value as usize) " Views" }} - RTYP_YOUTUBE_FOLLOWERS => {p{ @format_count(value as usize) " Subscribers" }} + RTYP_YOUTUBE_SUBSCRIBERS => {p{ @format_count(value as usize) " Subscribers" }} RTYP_ROTTEN_TOMATOES => {p.rating{ @value " Tomatoes" }} RTYP_METACRITIC if *full => {p{ "Metacritic Score: " @value }} RTYP_IMDB => {p.rating{ "IMDb " @value }} |