diff --git a/acrate_astreams/src/linkeddata/jsonld.rs b/acrate_astreams/src/linkeddata/jsonld.rs index 5a97af2..a601925 100644 --- a/acrate_astreams/src/linkeddata/jsonld.rs +++ b/acrate_astreams/src/linkeddata/jsonld.rs @@ -17,7 +17,7 @@ impl LinkedData for Node { self.has_type(id) } - fn ld_get_one_string(&self, id: &Id) -> ResultGetOne<String> { + fn ld_get_string(&self, id: &Id) -> ResultGetOne<String> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -35,7 +35,7 @@ impl LinkedData for Node { Some(Ok(string)) } - fn ld_get_id_string(&self, id: &Id) -> ResultGetOne<String> { + fn ld_get_string_id(&self, id: &Id) -> ResultGetOne<String> { let property = self.properties.get_any(id)?; let node = match property.as_node() { @@ -53,7 +53,7 @@ impl LinkedData for Node { Some(Ok(string)) } - fn ld_get_one_mediatype(&self, id: &Id) -> ResultGetOne<MediaType> { + fn ld_get_mediatype(&self, id: &Id) -> ResultGetOne<MediaType> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -74,7 +74,7 @@ impl LinkedData for Node { Some(Ok(mediatype)) } - fn ld_get_one_langtag(&self, id: &Id) -> ResultGetOne<LangTagBuf> { + fn ld_get_langtag(&self, id: &Id) -> ResultGetOne<LangTagBuf> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -97,7 +97,7 @@ impl LinkedData for Node { Some(Ok(langtag)) } - fn ld_get_one_u32(&self, id: &Id) -> ResultGetOne<u32> { + fn ld_get_u32(&self, id: &Id) -> ResultGetOne<u32> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -118,7 +118,7 @@ impl LinkedData for Node { Some(Ok(r#u32)) } - fn ld_get_one_u64(&self, id: &Id) -> ResultGetOne<u64> { + fn ld_get_u64(&self, id: &Id) -> ResultGetOne<u64> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -139,7 +139,7 @@ impl LinkedData for Node { Some(Ok(r#u64)) } - fn ld_get_one_timedelta(&self, id: &Id) -> ResultGetOne<TimeDelta> { + fn ld_get_timedelta(&self, id: &Id) -> ResultGetOne<TimeDelta> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -168,7 +168,7 @@ impl LinkedData for Node { Some(Ok(duration_chrono)) } - fn ld_get_one_datetime_local(&self, id: &Id) -> ResultGetOne<DateTime<Local>> { + fn ld_get_datetime_local(&self, id: &Id) -> ResultGetOne<DateTime<Local>> { let property = self.properties.get_any(id)?; let value = match property.as_value() { @@ -191,7 +191,7 @@ impl LinkedData for Node { Some(Ok(datetime_local)) } - fn ld_get_many_strings(&self, id: &Id) -> ResultGetMany<String> { + fn ld_get_strings(&self, id: &Id) -> ResultGetMany<String> { let properties = self.properties.get(id); let values = properties.map(|v| v @@ -215,7 +215,7 @@ impl LinkedData for Node { strings.collect() } - fn ld_get_many_langstrings(&self, id: &Id) -> ResultGetMany<LangString> { + fn ld_get_langstrings(&self, id: &Id) -> ResultGetMany<LangString> { let properties = self.properties.get(id); let values = properties.map(|v| v @@ -259,38 +259,7 @@ impl LinkedData for Node { values.collect() } - fn ld_get_many_self(&self, id: &Id) -> ResultGetMany<&Self> { - let properties = self.properties.get(id); - - let nodes = properties.map(|v| v - .as_node() - .ok_or(anyhow!("Couldn't process property as JSON-LD node")) - ) - .collect(); - - nodes - } - - fn ld_get_many_self_mut(&mut self, id: &Id) -> ResultGetMany<&mut Self> { - let properties = self.properties_mut(); - - // TODO: Replace with a get_mut or similar when available - let nodes = properties - .iter_mut() - .filter(|(cid, _)| cid == &id) - .flat_map(|(_, prop)| prop - .iter_mut() - .map(|obj| obj - .as_node_mut() - .ok_or(anyhow!("Couldn't process property as JSON-LD node")) - ) - ) - .collect(); - - nodes - } - - fn ld_set_one_string(&mut self, id: Id, value: String) -> ResultSetOne { + fn ld_set_string(&mut self, id: Id, value: String) -> ResultSetOne { let string = SynString::from(value); let json = SynValue::String(string); @@ -308,7 +277,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_id_string(&mut self, id: Id, value: String) -> ResultSetOne { + fn ld_set_string_id(&mut self, id: Id, value: String) -> ResultSetOne { let value_iri = IriBuf::new(value) .context("Couldn't convert string into an IRI")?; @@ -332,7 +301,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_one_mediatype(&mut self, id: Id, value: MediaType) -> ResultSetOne { + fn ld_set_mediatype(&mut self, id: Id, value: MediaType) -> ResultSetOne { let stringified = value.to_string(); let string = SynString::from(stringified); @@ -352,7 +321,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_one_langtag(&mut self, id: Id, value: LangTagBuf) -> ResultSetOne { + fn ld_set_langtag(&mut self, id: Id, value: LangTagBuf) -> ResultSetOne { let stringified = value.as_str(); let string = SynString::from(stringified); @@ -372,7 +341,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_one_u32(&mut self, id: Id, value: u32) -> ResultSetOne { + fn ld_set_u32(&mut self, id: Id, value: u32) -> ResultSetOne { let number = SynNumber::from(value); let json = SynValue::Number(number); @@ -390,7 +359,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_one_u64(&mut self, id: Id, value: u64) -> ResultSetOne { + fn ld_set_u64(&mut self, id: Id, value: u64) -> ResultSetOne { let number = SynNumber::from(value); let json = SynValue::Number(number); @@ -408,7 +377,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_one_timedelta(&mut self, id: Id, value: TimeDelta) -> ResultSetOne { + fn ld_set_timedelta(&mut self, id: Id, value: TimeDelta) -> ResultSetOne { let total_seconds = value.num_seconds(); if total_seconds.is_negative() { @@ -434,7 +403,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_one_datetime_local(&mut self, id: Id, value: DateTime<Local>) -> ResultSetOne { + fn ld_set_datetime_local(&mut self, id: Id, value: DateTime<Local>) -> ResultSetOne { let stringified = value.to_rfc3339(); let string = SynString::from(stringified); @@ -454,7 +423,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_many_strings(&mut self, id: Id, values: Vec<String>) -> ResultSetMany { + fn ld_set_strings(&mut self, id: Id, values: Vec<String>) -> ResultSetMany { let indexed_objects = values .into_iter() .map(|value| { @@ -479,7 +448,7 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_many_langstrings(&mut self, id: Id, values: Vec<LangString>) -> ResultSetMany { + fn ld_set_langstrings(&mut self, id: Id, values: Vec<LangString>) -> ResultSetMany { let indexed_objects = values .into_iter() .map(|(string, langdir)| { @@ -513,7 +482,36 @@ impl LinkedData for Node { Ok(()) } - fn ld_set_many_self(&mut self, id: Id, values: Vec<Self>) -> ResultSetMany { + fn ld_get_children(&self, id: &Id) -> ResultGetMany<&Self> { + let properties = self.properties.get(id); + + let nodes = properties.map(|v| v + .as_node() + .ok_or(anyhow!("Couldn't process property as JSON-LD node")) + ) + .collect(); + + nodes + } + + fn ld_into_children_mut(&mut self, id: &Id) -> ResultGetMany<&mut Self> { + // TODO: Replace with a get_mut or similar when available + let nodes = self.properties_mut() + .iter_mut() + .filter(|(cid, _)| cid == &id) + .flat_map(|(_, prop)| prop + .iter_mut() + .map(|obj| obj + .as_node_mut() + .ok_or(anyhow!("Couldn't process property as JSON-LD node")) + ) + ) + .collect(); + + nodes + } + + fn ld_set_children(&mut self, id: Id, values: Vec<Self>) -> ResultSetMany { let indexed_objects = values .into_iter() .map(|value| { diff --git a/acrate_astreams/src/linkeddata/mod.rs b/acrate_astreams/src/linkeddata/mod.rs index e4da730..0026eb3 100644 --- a/acrate_astreams/src/linkeddata/mod.rs +++ b/acrate_astreams/src/linkeddata/mod.rs @@ -35,28 +35,29 @@ pub trait LinkedData: Sized { fn ld_has_type(&self, id: &Id) -> bool; - fn ld_get_one_string(&self, id: &Id) -> ResultGetOne<String>; - fn ld_get_id_string(&self, id: &Id) -> ResultGetOne<String>; - fn ld_get_one_mediatype(&self, id: &Id) -> ResultGetOne<MediaType>; - fn ld_get_one_langtag(&self, id: &Id) -> ResultGetOne<LangTagBuf>; - fn ld_get_one_u32(&self, id: &Id) -> ResultGetOne<u32>; - fn ld_get_one_u64(&self, id: &Id) -> ResultGetOne<u64>; - fn ld_get_one_timedelta(&self, id: &Id) -> ResultGetOne<TimeDelta>; - fn ld_get_one_datetime_local(&self, id: &Id) -> ResultGetOne<DateTime<Local>>; - fn ld_get_many_strings(&self, id: &Id) -> ResultGetMany<String>; - fn ld_get_many_langstrings(&self, id: &Id) -> ResultGetMany<LangString>; - fn ld_get_many_self(&self, id: &Id) -> ResultGetMany<&Self>; - fn ld_get_many_self_mut(&mut self, id: &Id) -> ResultGetMany<&mut Self>; + fn ld_get_string(&self, id: &Id) -> ResultGetOne<String>; + fn ld_get_string_id(&self, id: &Id) -> ResultGetOne<String>; + fn ld_get_mediatype(&self, id: &Id) -> ResultGetOne<MediaType>; + fn ld_get_langtag(&self, id: &Id) -> ResultGetOne<LangTagBuf>; + fn ld_get_u32(&self, id: &Id) -> ResultGetOne<u32>; + fn ld_get_u64(&self, id: &Id) -> ResultGetOne<u64>; + fn ld_get_timedelta(&self, id: &Id) -> ResultGetOne<TimeDelta>; + fn ld_get_datetime_local(&self, id: &Id) -> ResultGetOne<DateTime<Local>>; + fn ld_get_strings(&self, id: &Id) -> ResultGetMany<String>; + fn ld_get_langstrings(&self, id: &Id) -> ResultGetMany<LangString>; - fn ld_set_one_string(&mut self, id: Id, value: String) -> ResultSetOne; - fn ld_set_id_string(&mut self, id: Id, value: String) -> ResultSetOne; - fn ld_set_one_mediatype(&mut self, id: Id, value: MediaType) -> ResultSetOne; - fn ld_set_one_langtag(&mut self, id: Id, value: LangTagBuf) -> ResultSetOne; - fn ld_set_one_u32(&mut self, id: Id, value: u32) -> ResultSetOne; - fn ld_set_one_u64(&mut self, id: Id, value: u64) -> ResultSetOne; - fn ld_set_one_timedelta(&mut self, id: Id, value: TimeDelta) -> ResultSetOne; - fn ld_set_one_datetime_local(&mut self, id: Id, value: DateTime<Local>) -> ResultSetOne; - fn ld_set_many_strings(&mut self, id: Id, values: Vec<String>) -> ResultSetMany; - fn ld_set_many_langstrings(&mut self, id: Id, values: Vec<LangString>) -> ResultSetMany; - fn ld_set_many_self(&mut self, id: Id, values: Vec<Self>) -> ResultSetMany; + fn ld_set_string(&mut self, id: Id, value: String) -> ResultSetOne; + fn ld_set_string_id(&mut self, id: Id, value: String) -> ResultSetOne; + fn ld_set_mediatype(&mut self, id: Id, value: MediaType) -> ResultSetOne; + fn ld_set_langtag(&mut self, id: Id, value: LangTagBuf) -> ResultSetOne; + fn ld_set_u32(&mut self, id: Id, value: u32) -> ResultSetOne; + fn ld_set_u64(&mut self, id: Id, value: u64) -> ResultSetOne; + fn ld_set_timedelta(&mut self, id: Id, value: TimeDelta) -> ResultSetOne; + fn ld_set_datetime_local(&mut self, id: Id, value: DateTime<Local>) -> ResultSetOne; + fn ld_set_strings(&mut self, id: Id, values: Vec<String>) -> ResultSetMany; + fn ld_set_langstrings(&mut self, id: Id, values: Vec<LangString>) -> ResultSetMany; + + fn ld_get_children(&self, id: &Id) -> ResultGetMany<&Self>; + fn ld_into_children_mut(&mut self, id: &Id) -> ResultGetMany<&mut Self>; + fn ld_set_children(&mut self, id: Id, values: Vec<Self>) -> ResultSetMany; } diff --git a/acrate_astreams/src/vocabulary/activitystreams.rs b/acrate_astreams/src/vocabulary/activitystreams.rs index 82b3a81..e777f86 100644 --- a/acrate_astreams/src/vocabulary/activitystreams.rs +++ b/acrate_astreams/src/vocabulary/activitystreams.rs @@ -17,18 +17,23 @@ use chrono::TimeDelta; vocab!( "https://www.w3.org/ns/activitystreams#Object", - ref Object, + ref ObjectRef, mut ObjectMut, - one - [ + one [ { "https://www.w3.org/ns/activitystreams#duration", - duration: TimeDelta, - get ld_get_one_timedelta, - put ld_set_one_timedelta, + -> TimeDelta, + get_timedelta @ ld_get_timedelta, + set_timedelta @ ld_set_timedelta, } ], - many - [ + many [], + children [ + { + "https://www.w3.org/ns/activitystreams#attachment", + get_attachments, + into_attachments_mut, + set_attachments, + } ], ); diff --git a/acrate_astreams/src/vocabulary/mod.rs b/acrate_astreams/src/vocabulary/mod.rs index 626efe2..645468f 100644 --- a/acrate_astreams/src/vocabulary/mod.rs +++ b/acrate_astreams/src/vocabulary/mod.rs @@ -20,14 +20,14 @@ macro_rules! vocab { $( { $one_iri:literal, - - $one:ident: $one_type:ty, + + -> $one_type:ty, $( #[ $one_get_meta:meta ] )* - get $one_get:ident, + $one_get_name:ident @ $one_get_via:ident, - $( #[ $one_put_meta:meta ] )* - put $one_put:ident, + $( #[ $one_set_meta:meta ] )* + $one_set_name:ident @ $one_set_via:ident, } ),* ], @@ -39,19 +39,33 @@ macro_rules! vocab { { $many_iri:literal, - $many:ident: $many_type:ty, + -> $many_type:ty, $( #[ $many_get_meta:meta ] )* - get $many_get:ident, - - $( #[ $many_patch_meta:meta ] )* - patch $many_patch:ident, + $many_get_name:ident @ $many_get_via:ident, - $( #[ $many_put_meta:meta ] )* - put $many_put:ident, + $( #[ $many_set_meta:meta ] )* + $many_set_name:ident @ $many_set_via:ident, } ),* ], + children [ + $( + { + $children_iri:literal, + + $( #[ $children_get_meta:meta ] )* + $children_get_name:ident, + + $( #[ $children_into_meta:meta ] )* + $children_into_name:ident, + + $( #[ $children_set_meta:meta ] )* + $children_set_name:ident, + } + ),* + + ], )? ) => { $( #[ $vocab_ref_meta ] )* @@ -70,86 +84,34 @@ macro_rules! vocab { backend: &'b mut B } - impl<'b, B> TryFrom<&'b B> for $vocab_ref<'b, B> + impl<'b, B> $vocab_ref<'b, B> where B: $crate::linkeddata::LinkedData { - type Error = anyhow::Error; - - fn try_from(value: &'b B) -> Result<Self, Self::Error> { - match value.ld_has_type( &iri_id!($vocab_iri) ) { - false => Err(anyhow::anyhow!("Required JSON-LD type is missing: {}", $vocab_iri)), - true => Ok(Self { backend: value }), - } - } - } - - impl<'b, B> TryFrom<&'b mut B> for $vocab_mut<'b, B> - where B: $crate::linkeddata::LinkedData - { - type Error = anyhow::Error; - - fn try_from(value: &'b mut B) -> Result<Self, Self::Error> { - match value.ld_has_type( &iri_id!($vocab_iri) ) { - false => Err(anyhow::anyhow!("Required JSON-LD type is missing: {}", $vocab_iri)), - true => Ok(Self { backend: value }), - } - } - } - - impl<'b, B> From<$vocab_mut<'b, B>> for $vocab_ref<'b, B> - where B: $crate::linkeddata::LinkedData - { - fn from(value: $vocab_mut<'b, B>) -> Self { + pub fn new(backend: &'b B) -> Self { Self { - backend: value.backend + backend } } } - impl<'b, B> From<&'b B> for $vocab_ref<'b, B> + impl<'b, B> $vocab_mut<'b, B> where B: $crate::linkeddata::LinkedData { - fn from(value: &'b B) -> Self { + pub fn new(backend: &'b mut B) -> Self { Self { - backend: value + backend } } } - impl<'b, B> From<&'b mut B> for $vocab_mut<'b, B> - where B: $crate::linkeddata::LinkedData - { - fn from(value: &'b mut B) -> Self { - Self { - backend: value - } - } - } - - impl<'b, B> From<$vocab_ref<'b, B>> for &'b B - where B: $crate::linkeddata::LinkedData - { - fn from(value: $vocab_ref<'b, B>) -> Self { - value.backend - } - } - - impl<'b, B> From<$vocab_mut<'b, B>> for &'b mut B - where B: $crate::linkeddata::LinkedData - { - fn from(value: $vocab_mut<'b, B>) -> Self { - value.backend - } - } - $( impl<'b, B> $vocab_ref<'b, B> where B: $crate::linkeddata::LinkedData { $( $( #[ $one_get_meta ] )* - fn $one(&'b self) -> $crate::linkeddata::ResultGetOne<$one_type> { - self.backend.$one_get( + pub fn $one_get_name(&'b self) -> $crate::linkeddata::ResultGetOne<$one_type> { + self.backend.$one_get_via( &iri_id!( $one_iri ) ) } @@ -160,9 +122,18 @@ macro_rules! vocab { where B: $crate::linkeddata::LinkedData { $( - $( #[ $one_put_meta ] )* - fn $one(&'b self, value: $one_type) -> $crate::linkeddata::ResultSetOne { - self.backend.$one_put( + $( #[ $one_get_meta ] )* + pub fn $one_get_name(&'b self) -> $crate::linkeddata::ResultGetOne<$one_type> { + self.backend.$one_get_via( + &iri_id!( $one_iri ) + ) + } + ),* + + $( + $( #[ $one_set_meta ] )* + pub fn $one_set_name(&'b mut self, value: $one_type) -> $crate::linkeddata::ResultSetOne { + self.backend.$one_set_via( iri_id!( $one_iri ), value ) @@ -178,8 +149,8 @@ macro_rules! vocab { { $( $( #[ $many_get_meta ] )* - fn $many(&'b self) -> $crate::linkeddata::ResultGetMany<$many_type> { - self.backend.$many_get( + pub fn $many_get_name(&'b self) -> $crate::linkeddata::ResultGetMany<&'b $many_type> { + self.backend.$many_get_via( &iri_id!( $many_iri ) ) } @@ -190,11 +161,67 @@ macro_rules! vocab { where B: $crate::linkeddata::LinkedData { $( - $( #[ $many_put_meta ] )* - fn $many(&'b self, value: Vec<$many_type>) -> $crate::linkeddata::ResultSetMany { - self.backend.$many_put( + $( #[ $many_get_meta ] )* + pub fn $many_get_name(&'b self) -> $crate::linkeddata::ResultGetMany<&'b $many_type> { + self.backend.$many_get_via( + &iri_id!( $many_iri ) + ) + } + ),* + + $( + $( #[ $many_set_meta ] )* + pub fn $many_set_name(&'b self, values: Vec<$many_type>) -> $crate::linkeddata::ResultSetMany { + self.backend.$many_set_via( iri_id!( $many_iri ), - value + values + ) + } + ),* + } + )? + + $( + impl<'b, B> $vocab_ref<'b, B> + where B: $crate::linkeddata::LinkedData + { + $( + $( #[ $children_get_meta ] )* + pub fn $children_get_name(&'b self) -> $crate::linkeddata::ResultGetMany<&'b B> { + self.backend.ld_get_children( + &iri_id!( $children_iri ) + ) + } + ),* + } + + impl<'b, B> $vocab_mut<'b, B> + where B: $crate::linkeddata::LinkedData + { + $( + $( #[ $children_get_meta ] )* + pub fn $children_get_name(&'b self) -> $crate::linkeddata::ResultGetMany<&'b B> { + self.backend.ld_get_children( + &iri_id!( $children_iri ) + ) + } + ),* + + $( + $( #[ $children_into_meta ] )* + pub fn $children_into_name(self) -> $crate::linkeddata::ResultGetMany<&'b mut B> { + self.backend.ld_into_children_mut( + &iri_id!( $children_iri ) + ) + } + ),* + + $( + $( #[ $children_into_meta ] )* + pub fn $children_set_name(&'b mut self, values: Vec<B>) -> $crate::linkeddata::ResultSetMany { + self.backend.ld_set_children( + iri_id!( $children_iri ), + values ) } ),*