change expand into a partial expand to remove resolver dependency
This commit is contained in:
parent
271eba8d7b
commit
1e7c59c5a4
|
@ -321,6 +321,7 @@ dependencies = [
|
|||
"async-trait",
|
||||
"axum",
|
||||
"base-62",
|
||||
"flabk-derive",
|
||||
"handlebars",
|
||||
"jsonwebtoken",
|
||||
"mime_guess",
|
||||
|
@ -335,6 +336,16 @@ dependencies = [
|
|||
"tower-cookies",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "flabk-derive"
|
||||
version = "0.1.0"
|
||||
source = "git+https://sectorinf.com/emilis/flabk-derive#d5647801bb9fe24edcb1165c900ce5f3d7f24cee"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fnv"
|
||||
version = "1.0.7"
|
||||
|
|
|
@ -31,6 +31,7 @@ serde_json = "1.0.85"
|
|||
tokio = { version = "1", features = ["full"] }
|
||||
tokio-postgres = { version = "0.7.7", features = ["with-serde_json-1"] }
|
||||
tower-cookies = "0.7.0"
|
||||
flabk-derive = { git = "https://sectorinf.com/emilis/flabk-derive" }
|
||||
|
||||
[patch.crates-io]
|
||||
serde = { git = "https://sectorinf.com/emilis/serde" }
|
||||
|
|
|
@ -1,13 +1,21 @@
|
|||
use super::serde_ext::IriPartial;
|
||||
use serde::Deserialize;
|
||||
|
||||
pub const CONTEXT_ID: &str = "https://www.w3.org/ns/activitystreams";
|
||||
|
||||
#[derive(Default, Debug, Clone, Deserialize)]
|
||||
pub struct Context {
|
||||
pub id: Option<String>,
|
||||
#[serde(rename = "@context")]
|
||||
pub ctx: ContextMap,
|
||||
}
|
||||
|
||||
impl IriPartial for Context {
|
||||
fn set_id(&mut self, new_id: &str) {
|
||||
self.id = Some(new_id.into());
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Deserialize)]
|
||||
#[serde(rename_all = "PascalCase")]
|
||||
pub struct ContextMap {
|
||||
|
|
|
@ -1,11 +1,13 @@
|
|||
use async_trait::async_trait;
|
||||
use flabk_derive::IRI;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use serde_ext::IriPartial;
|
||||
|
||||
use self::{
|
||||
context::Context,
|
||||
note::Note,
|
||||
resolve::ResolveError,
|
||||
serde_ext::{expand, pull_single_into_vec},
|
||||
serde_ext::{expand_partial, pull_single_into_vec},
|
||||
};
|
||||
|
||||
pub mod context;
|
||||
|
@ -54,17 +56,18 @@ pub struct ActivityLD {
|
|||
#[derive(Debug, Clone, Deserialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub struct Activity {
|
||||
#[serde(rename = "@context")]
|
||||
#[serde(deserialize_with = "expand")]
|
||||
pub ap_context: Context,
|
||||
// #[serde(rename = "@context")]
|
||||
// #[serde(deserialize_with = "expand_partial")]
|
||||
// pub ap_context: Context,
|
||||
pub id: String,
|
||||
#[serde(rename = "type")]
|
||||
pub kind: ActivityKind,
|
||||
#[serde(deserialize_with = "expand_partial")]
|
||||
pub attributed_to: Actor,
|
||||
pub content: Option<String>,
|
||||
// pub context: Option<String>,
|
||||
#[serde(deserialize_with = "expand")]
|
||||
pub to: Context,
|
||||
pub context: Option<String>,
|
||||
#[serde(deserialize_with = "pull_single_into_vec")]
|
||||
pub to: Vec<String>,
|
||||
pub url: Option<String>,
|
||||
}
|
||||
|
||||
|
@ -89,7 +92,7 @@ pub struct ObjectLD {
|
|||
|
||||
pub enum ActorType {}
|
||||
|
||||
#[derive(Debug, Clone, Deserialize)]
|
||||
#[derive(Debug, Clone, Deserialize, IRI, Default)]
|
||||
pub struct Actor {
|
||||
id: String,
|
||||
}
|
||||
|
@ -110,7 +113,6 @@ pub async fn test() {
|
|||
}"#;
|
||||
|
||||
let obj = serde_json::from_str::<Activity>(obj).unwrap();
|
||||
println!("to: {:#?}", &obj.to);
|
||||
println!();
|
||||
println!("{:#?}", obj);
|
||||
}
|
||||
|
|
|
@ -1,24 +1,25 @@
|
|||
use super::resolve::Resolver;
|
||||
use std::{fmt, marker::PhantomData};
|
||||
|
||||
use serde::{de::Visitor, Deserialize, Deserializer};
|
||||
|
||||
// Allows a value that's a string to be expanded into an object AND the serialization of that object itself
|
||||
// TODO: deserializing the actual object isnt supported atm LOL
|
||||
pub(super) fn expand<'de, D, Out>(deserializer: D) -> Result<Out, D::Error>
|
||||
pub trait IriPartial: Default {
|
||||
fn set_id(&mut self, new_id: &str);
|
||||
}
|
||||
|
||||
// Allows a value that's a string to be expanded into an object (move string into id property via From<IRI>)
|
||||
// AND the serialization of that object itself
|
||||
pub(super) fn expand_partial<'de, D, Out>(deserializer: D) -> Result<Out, D::Error>
|
||||
where
|
||||
D: Deserializer<'de>,
|
||||
Out: for<'dt> serde::Deserialize<'dt>,
|
||||
Out: for<'dt> serde::Deserialize<'dt> + IriPartial,
|
||||
{
|
||||
let resolver = Resolver::new();
|
||||
struct ResolveVisitor<Out> {
|
||||
resolver: Resolver,
|
||||
_type: PhantomData<Out>,
|
||||
}
|
||||
|
||||
impl<'de, Out> Visitor<'de> for ResolveVisitor<Out>
|
||||
where
|
||||
Out: for<'dt> serde::Deserialize<'dt>,
|
||||
Out: for<'dt> serde::Deserialize<'dt> + IriPartial,
|
||||
{
|
||||
type Value = Out;
|
||||
|
||||
|
@ -30,18 +31,9 @@ where
|
|||
where
|
||||
E: serde::de::Error,
|
||||
{
|
||||
tokio::runtime::Runtime::new()
|
||||
.unwrap()
|
||||
.block_on(self.resolver.resolve_into::<Out>(value.to_string()))
|
||||
.map_err(|e| {
|
||||
let name = std::any::type_name::<Out>();
|
||||
serde::de::Error::invalid_value(
|
||||
serde::de::Unexpected::Other(
|
||||
format!("failed resolving iri [{}]: {}", value, e.0).as_str(),
|
||||
),
|
||||
&name,
|
||||
)
|
||||
})
|
||||
let mut out = Out::default();
|
||||
out.set_id(value);
|
||||
Ok(out)
|
||||
}
|
||||
|
||||
fn visit_seq<S>(self, visitor: S) -> Result<Self::Value, S::Error>
|
||||
|
@ -52,10 +44,7 @@ where
|
|||
}
|
||||
}
|
||||
|
||||
let resolve_visitor = ResolveVisitor {
|
||||
resolver: resolver,
|
||||
_type: PhantomData,
|
||||
};
|
||||
let resolve_visitor = ResolveVisitor { _type: PhantomData };
|
||||
deserializer.deserialize_map_string(resolve_visitor, |des| Out::deserialize(des))
|
||||
}
|
||||
|
||||
|
@ -99,28 +88,38 @@ where
|
|||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use flabk_derive::IRI;
|
||||
use serde::Deserialize;
|
||||
|
||||
use super::expand;
|
||||
use crate::astreams::serde_ext::IriPartial;
|
||||
|
||||
use super::expand_partial;
|
||||
|
||||
#[test]
|
||||
fn expand_context_from_iri() {
|
||||
fn expand_partial_populates_iri_from_string() {
|
||||
#[derive(Deserialize, IRI, Default)]
|
||||
struct Context {
|
||||
pub id: String,
|
||||
pub context: bool,
|
||||
}
|
||||
|
||||
#[derive(Deserialize)]
|
||||
struct WithContext {
|
||||
#[serde(deserialize_with = "expand")]
|
||||
pub context: super::super::context::Context,
|
||||
#[serde(deserialize_with = "expand_partial")]
|
||||
pub context: Context,
|
||||
}
|
||||
|
||||
const JSONLD_INPUT: &str = r#"{"context": "https://www.w3.org/ns/activitystreams"}"#;
|
||||
let result =
|
||||
serde_json::from_str::<WithContext>(JSONLD_INPUT).expect("deserializing with expand");
|
||||
|
||||
assert!(result.context.ctx.xsd == "http://www.w3.org/2001/XMLSchema#")
|
||||
assert!(result.context.id == "https://www.w3.org/ns/activitystreams");
|
||||
assert!(result.context.context == false);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn expand_when_json_isnt_iri_but_the_object_itself() {
|
||||
#[derive(Deserialize)]
|
||||
fn expand_partial_expands_into_object_fully() {
|
||||
#[derive(Deserialize, IRI, Default)]
|
||||
struct Expanded {
|
||||
pub id: String,
|
||||
pub truth: bool,
|
||||
|
@ -128,7 +127,7 @@ mod tests {
|
|||
|
||||
#[derive(Deserialize)]
|
||||
struct Expandable {
|
||||
#[serde(deserialize_with = "expand")]
|
||||
#[serde(deserialize_with = "expand_partial")]
|
||||
pub expansive: Expanded,
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue