Ensure visibility settings are not violated when creating a reply to non-public post

This commit is contained in:
silverpill 2022-01-08 18:49:39 +00:00
parent de37f606e3
commit 19f0a4bed6
2 changed files with 33 additions and 11 deletions

View file

@ -18,7 +18,7 @@ use crate::activitypub::deliverer::deliver_activity;
use crate::activitypub::views::get_object_url; use crate::activitypub::views::get_object_url;
use crate::config::Config; use crate::config::Config;
use crate::database::{Pool, get_database_client}; use crate::database::{Pool, get_database_client};
use crate::errors::{DatabaseError, HttpError}; use crate::errors::{DatabaseError, HttpError, ValidationError};
use crate::ethereum::nft::create_mint_signature; use crate::ethereum::nft::create_mint_signature;
use crate::ipfs::store as ipfs_store; use crate::ipfs::store as ipfs_store;
use crate::ipfs::utils::{IPFS_LOGO, get_ipfs_url}; use crate::ipfs::utils::{IPFS_LOGO, get_ipfs_url};
@ -39,7 +39,7 @@ use crate::models::posts::queries::{
update_post, update_post,
delete_post, delete_post,
}; };
use crate::models::posts::types::PostCreateData; use crate::models::posts::types::{PostCreateData, Visibility};
use crate::models::reactions::queries::{ use crate::models::reactions::queries::{
create_reaction, create_reaction,
delete_reaction, delete_reaction,
@ -78,21 +78,43 @@ async fn create_status(
); );
post_data.mentions = mention_map.values() post_data.mentions = mention_map.values()
.map(|profile| profile.id).collect(); .map(|profile| profile.id).collect();
// Tags
post_data.tags = find_tags(&post_data.content); post_data.tags = find_tags(&post_data.content);
post_data.content = replace_tags( post_data.content = replace_tags(
&instance.url(), &instance.url(),
&post_data.content, &post_data.content,
&post_data.tags, &post_data.tags,
); );
let mut post = create_post(db_client, &current_user.id, post_data).await?; // Reply validation
// Federate let maybe_in_reply_to = if let Some(in_reply_to_id) = post_data.in_reply_to_id.as_ref() {
post.in_reply_to = match post.in_reply_to_id { let in_reply_to = match get_post_by_id(db_client, in_reply_to_id).await {
Some(in_reply_to_id) => { Ok(post) => post,
let in_reply_to = get_post_by_id(db_client, &in_reply_to_id).await?; Err(DatabaseError::NotFound(_)) => {
Some(Box::new(in_reply_to)) return Err(ValidationError("parent post does not exist").into());
}, },
None => None, Err(other_error) => return Err(other_error.into()),
};
if post_data.visibility != in_reply_to.visibility {
return Err(ValidationError("post visibility doesn't match the parent").into());
};
if post_data.visibility != Visibility::Public {
let in_reply_to_mentions: Vec<_> = in_reply_to.mentions.iter()
.map(|profile| profile.id).collect();
if !post_data.mentions.iter().all(|id| in_reply_to_mentions.contains(id)) {
return Err(ValidationError("audience can't be expanded").into());
};
};
Some(in_reply_to)
} else {
None
}; };
// Create post
let mut post = create_post(db_client, &current_user.id, post_data).await?;
post.in_reply_to = maybe_in_reply_to.map(|mut in_reply_to| {
in_reply_to.reply_count += 1;
Box::new(in_reply_to)
});
// Federate
let activity = create_activity_note( let activity = create_activity_note(
&instance.host(), &instance.host(),
&instance.url(), &instance.url(),

View file

@ -12,7 +12,7 @@ use crate::models::attachments::types::DbMediaAttachment;
use crate::models::profiles::types::DbActorProfile; use crate::models::profiles::types::DbActorProfile;
use crate::utils::html::clean_html; use crate::utils::html::clean_html;
#[derive(Clone, Debug)] #[derive(Clone, Debug, PartialEq)]
pub enum Visibility { pub enum Visibility {
Public, Public,
Direct, Direct,