Ignore deserialization errors when parsing object tags
This commit is contained in:
parent
a22ae40d8e
commit
143879caf9
2 changed files with 39 additions and 24 deletions
|
@ -16,7 +16,7 @@ use crate::activitypub::{
|
||||||
},
|
},
|
||||||
identifiers::parse_local_actor_id,
|
identifiers::parse_local_actor_id,
|
||||||
receiver::{parse_array, parse_property_value, HandlerError},
|
receiver::{parse_array, parse_property_value, HandlerError},
|
||||||
types::{Attachment, Link, Object, Tag},
|
types::{Attachment, Link, LinkTag, Object, Tag},
|
||||||
vocabulary::*,
|
vocabulary::*,
|
||||||
};
|
};
|
||||||
use crate::config::{Config, Instance};
|
use crate::config::{Config, Instance};
|
||||||
|
@ -218,9 +218,15 @@ pub async fn handle_note(
|
||||||
let list: Vec<JsonValue> = parse_property_value(&value)
|
let list: Vec<JsonValue> = parse_property_value(&value)
|
||||||
.map_err(|_| ValidationError("invalid tag property"))?;
|
.map_err(|_| ValidationError("invalid tag property"))?;
|
||||||
for tag_value in list {
|
for tag_value in list {
|
||||||
let tag: Tag = serde_json::from_value(tag_value.clone())
|
let tag_type = tag_value["type"].as_str().unwrap_or(HASHTAG);
|
||||||
.map_err(|_| ValidationError("invalid tag"))?;
|
if tag_type == HASHTAG {
|
||||||
if tag.tag_type == HASHTAG {
|
let tag: Tag = match serde_json::from_value(tag_value) {
|
||||||
|
Ok(tag) => tag,
|
||||||
|
Err(_) => {
|
||||||
|
log::warn!("invalid hashtag");
|
||||||
|
continue;
|
||||||
|
},
|
||||||
|
};
|
||||||
if let Some(tag_name) = tag.name {
|
if let Some(tag_name) = tag.name {
|
||||||
// Ignore invalid tags
|
// Ignore invalid tags
|
||||||
if let Ok(tag_name) = normalize_hashtag(&tag_name) {
|
if let Ok(tag_name) = normalize_hashtag(&tag_name) {
|
||||||
|
@ -229,7 +235,14 @@ pub async fn handle_note(
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
} else if tag.tag_type == MENTION {
|
} else if tag_type == MENTION {
|
||||||
|
let tag: Tag = match serde_json::from_value(tag_value) {
|
||||||
|
Ok(tag) => tag,
|
||||||
|
Err(_) => {
|
||||||
|
log::warn!("invalid mention");
|
||||||
|
continue;
|
||||||
|
},
|
||||||
|
};
|
||||||
// Try to find profile by actor ID.
|
// Try to find profile by actor ID.
|
||||||
if let Some(href) = tag.href {
|
if let Some(href) = tag.href {
|
||||||
if let Ok(username) = parse_local_actor_id(&instance.url(), &href) {
|
if let Ok(username) = parse_local_actor_id(&instance.url(), &href) {
|
||||||
|
@ -299,15 +312,21 @@ pub async fn handle_note(
|
||||||
} else {
|
} else {
|
||||||
log::warn!("failed to parse mention {}", tag_name);
|
log::warn!("failed to parse mention {}", tag_name);
|
||||||
};
|
};
|
||||||
} else if tag.tag_type == LINK {
|
} else if tag_type == LINK {
|
||||||
if tag.media_type != Some(AP_MEDIA_TYPE.to_string()) &&
|
let tag: LinkTag = match serde_json::from_value(tag_value) {
|
||||||
tag.media_type != Some(AS_MEDIA_TYPE.to_string())
|
Ok(tag) => tag,
|
||||||
|
Err(_) => {
|
||||||
|
log::warn!("invalid link tag");
|
||||||
|
continue;
|
||||||
|
},
|
||||||
|
};
|
||||||
|
if tag.media_type != AP_MEDIA_TYPE &&
|
||||||
|
tag.media_type != AS_MEDIA_TYPE
|
||||||
{
|
{
|
||||||
// Unknown media type
|
// Unknown media type
|
||||||
continue;
|
continue;
|
||||||
};
|
};
|
||||||
if let Some(ref href) = tag.href {
|
let href = redirects.get(&tag.href).unwrap_or(&tag.href);
|
||||||
let href = redirects.get(href).unwrap_or(href);
|
|
||||||
let linked = get_post_by_object_id(
|
let linked = get_post_by_object_id(
|
||||||
db_client,
|
db_client,
|
||||||
&instance.url(),
|
&instance.url(),
|
||||||
|
@ -316,13 +335,12 @@ pub async fn handle_note(
|
||||||
if !links.contains(&linked.id) {
|
if !links.contains(&linked.id) {
|
||||||
links.push(linked.id);
|
links.push(linked.id);
|
||||||
};
|
};
|
||||||
};
|
} else if tag_type == EMOJI {
|
||||||
} else if tag.tag_type == EMOJI {
|
|
||||||
log::info!("found emoji tag: {}", tag_value);
|
log::info!("found emoji tag: {}", tag_value);
|
||||||
} else {
|
} else {
|
||||||
log::warn!(
|
log::warn!(
|
||||||
"skipping tag of type {}",
|
"skipping tag of type {}",
|
||||||
tag.tag_type,
|
tag_type,
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
|
@ -32,9 +32,6 @@ pub struct Tag {
|
||||||
pub tag_type: String,
|
pub tag_type: String,
|
||||||
|
|
||||||
pub href: Option<String>,
|
pub href: Option<String>,
|
||||||
|
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
|
||||||
pub media_type: Option<String>,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Serialize)]
|
#[derive(Serialize)]
|
||||||
|
@ -47,7 +44,7 @@ pub struct SimpleTag {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// https://codeberg.org/fediverse/fep/src/branch/main/feps/fep-e232.md
|
/// https://codeberg.org/fediverse/fep/src/branch/main/feps/fep-e232.md
|
||||||
#[derive(Serialize)]
|
#[derive(Deserialize, Serialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
pub struct LinkTag {
|
pub struct LinkTag {
|
||||||
#[serde(rename = "type")]
|
#[serde(rename = "type")]
|
||||||
|
|
Loading…
Reference in a new issue