Refactor receive_activity() function

This commit is contained in:
silverpill 2021-11-29 20:45:36 +00:00
parent a9b7426be4
commit db0b49fe79

View file

@ -73,11 +73,11 @@ fn parse_object_id(
.map_err(|_| ValidationError("error"))?; .map_err(|_| ValidationError("error"))?;
let url_caps = url_regexp.captures(object_id) let url_caps = url_regexp.captures(object_id)
.ok_or(ValidationError("invalid object ID"))?; .ok_or(ValidationError("invalid object ID"))?;
let object_uuid: Uuid = url_caps.name("uuid") let internal_object_id: Uuid = url_caps.name("uuid")
.ok_or(ValidationError("invalid object ID"))? .ok_or(ValidationError("invalid object ID"))?
.as_str().parse() .as_str().parse()
.map_err(|_| ValidationError("invalid object ID"))?; .map_err(|_| ValidationError("invalid object ID"))?;
Ok(object_uuid) Ok(internal_object_id)
} }
fn parse_array(value: &Value) -> Result<Vec<String>, ValidationError> { fn parse_array(value: &Value) -> Result<Vec<String>, ValidationError> {
@ -93,6 +93,19 @@ fn parse_array(value: &Value) -> Result<Vec<String>, ValidationError> {
Ok(result) Ok(result)
} }
/// Parses object json value and returns its ID as string
fn get_object_id(object: Value) -> Result<String, ValidationError> {
let object_id = match object.as_str() {
Some(object_id) => object_id.to_owned(),
None => {
let object: Object = serde_json::from_value(object)
.map_err(|_| ValidationError("invalid object"))?;
object.id
},
};
Ok(object_id)
}
async fn get_or_fetch_profile_by_actor_id( async fn get_or_fetch_profile_by_actor_id(
db_client: &impl GenericClient, db_client: &impl GenericClient,
instance: &Instance, instance: &Instance,
@ -279,15 +292,13 @@ pub async fn receive_activity(
let db_client = &mut **get_database_client(db_pool).await?; let db_client = &mut **get_database_client(db_pool).await?;
match (activity_type.as_str(), object_type.as_str()) { match (activity_type.as_str(), object_type.as_str()) {
(ACCEPT, FOLLOW) => { (ACCEPT, FOLLOW) => {
let object: Object = serde_json::from_value(activity.object) let object_id = get_object_id(activity.object)?;
.map_err(|_| ValidationError("invalid object"))?; let follow_request_id = parse_object_id(&config.instance_url(), &object_id)?;
let follow_request_id = parse_object_id(&config.instance_url(), &object.id)?;
follow_request_accepted(db_client, &follow_request_id).await?; follow_request_accepted(db_client, &follow_request_id).await?;
}, },
(REJECT, FOLLOW) => { (REJECT, FOLLOW) => {
let object: Object = serde_json::from_value(activity.object) let object_id = get_object_id(activity.object)?;
.map_err(|_| ValidationError("invalid object"))?; let follow_request_id = parse_object_id(&config.instance_url(), &object_id)?;
let follow_request_id = parse_object_id(&config.instance_url(), &object.id)?;
follow_request_rejected(db_client, &follow_request_id).await?; follow_request_rejected(db_client, &follow_request_id).await?;
}, },
(CREATE, NOTE) => { (CREATE, NOTE) => {
@ -302,14 +313,7 @@ pub async fn receive_activity(
&activity.actor, &activity.actor,
&config.media_dir(), &config.media_dir(),
).await?; ).await?;
let object_id = match activity.object.as_str() { let object_id = get_object_id(activity.object)?;
Some(object_id) => object_id.to_owned(),
None => {
let object: Object = serde_json::from_value(activity.object)
.map_err(|_| ValidationError("invalid object"))?;
object.id
},
};
let post_id = match parse_object_id(&config.instance_url(), &object_id) { let post_id = match parse_object_id(&config.instance_url(), &object_id) {
Ok(post_id) => post_id, Ok(post_id) => post_id,
Err(_) => { Err(_) => {
@ -325,14 +329,7 @@ pub async fn receive_activity(
create_post(db_client, &author.id, repost_data).await?; create_post(db_client, &author.id, repost_data).await?;
}, },
(DELETE, _) => { (DELETE, _) => {
let object_id = match activity.object.as_str() { let object_id = get_object_id(activity.object)?;
Some(object_id) => object_id.to_owned(),
None => {
let object: Object = serde_json::from_value(activity.object)
.map_err(|_| ValidationError("invalid object"))?;
object.id
},
};
let post = get_post_by_object_id(db_client, &object_id).await?; let post = get_post_by_object_id(db_client, &object_id).await?;
let deletion_queue = delete_post(db_client, &post.id).await?; let deletion_queue = delete_post(db_client, &post.id).await?;
let config = config.clone(); let config = config.clone();
@ -347,14 +344,7 @@ pub async fn receive_activity(
&activity.actor, &activity.actor,
&config.media_dir(), &config.media_dir(),
).await?; ).await?;
let object_id = match activity.object.as_str() { let object_id = get_object_id(activity.object)?;
Some(object_id) => object_id.to_owned(),
None => {
let object: Object = serde_json::from_value(activity.object)
.map_err(|_| ValidationError("invalid object"))?;
object.id
},
};
let post_id = match parse_object_id(&config.instance_url(), &object_id) { let post_id = match parse_object_id(&config.instance_url(), &object_id) {
Ok(post_id) => post_id, Ok(post_id) => post_id,
Err(_) => { Err(_) => {
@ -378,14 +368,7 @@ pub async fn receive_activity(
).await?; ).await?;
let source_actor = source_profile.remote_actor().ok().flatten() let source_actor = source_profile.remote_actor().ok().flatten()
.ok_or(HttpError::InternalError)?; .ok_or(HttpError::InternalError)?;
let target_actor_id = match activity.object.as_str() { let target_actor_id = get_object_id(activity.object)?;
Some(object_id) => object_id.to_owned(),
None => {
let object: Object = serde_json::from_value(activity.object)
.map_err(|_| ValidationError("invalid object"))?;
object.id
},
};
let target_username = parse_actor_id(&config.instance_url(), &target_actor_id)?; let target_username = parse_actor_id(&config.instance_url(), &target_actor_id)?;
let target_profile = get_profile_by_acct(db_client, &target_username).await?; let target_profile = get_profile_by_acct(db_client, &target_username).await?;
// Create and send 'Accept' activity // Create and send 'Accept' activity
@ -482,8 +465,8 @@ mod tests {
"https://example.org/objects/{}", "https://example.org/objects/{}",
expected_uuid, expected_uuid,
); );
let object_uuid = parse_object_id(INSTANCE_URL, &object_id).unwrap(); let internal_object_id = parse_object_id(INSTANCE_URL, &object_id).unwrap();
assert_eq!(object_uuid, expected_uuid); assert_eq!(internal_object_id, expected_uuid);
} }
#[test] #[test]
@ -510,4 +493,16 @@ mod tests {
vec!["test1".to_string(), "test2".to_string()], vec!["test1".to_string(), "test2".to_string()],
); );
} }
#[test]
fn test_get_object_id_from_string() {
let value = json!("test_id");
assert_eq!(get_object_id(value).unwrap(), "test_id");
}
#[test]
fn test_get_object_id_from_object() {
let value = json!({"id": "test_id", "type": "Note"});
assert_eq!(get_object_id(value).unwrap(), "test_id");
}
} }