mirror of
https://github.com/LemmyNet/lemmy.git
synced 2024-11-30 00:01:25 +00:00
move block/unblock activities
This commit is contained in:
parent
ab5b072e21
commit
e1e54672c6
7 changed files with 161 additions and 284 deletions
|
@ -0,0 +1,76 @@
|
||||||
|
use crate::{activities_new::verify_mod_action, inbox::new_inbox_routing::Activity};
|
||||||
|
use activitystreams::activity::kind::BlockType;
|
||||||
|
use lemmy_api_common::blocking;
|
||||||
|
use lemmy_apub::{
|
||||||
|
check_is_apub_id_valid,
|
||||||
|
fetcher::{community::get_or_fetch_and_upsert_community, person::get_or_fetch_and_upsert_person},
|
||||||
|
};
|
||||||
|
use lemmy_apub_lib::{verify_domains_match, PublicUrl, ReceiveActivity, VerifyActivity};
|
||||||
|
use lemmy_db_queries::{Bannable, Followable};
|
||||||
|
use lemmy_db_schema::source::community::{
|
||||||
|
CommunityFollower,
|
||||||
|
CommunityFollowerForm,
|
||||||
|
CommunityPersonBan,
|
||||||
|
CommunityPersonBanForm,
|
||||||
|
};
|
||||||
|
use lemmy_utils::LemmyError;
|
||||||
|
use lemmy_websocket::LemmyContext;
|
||||||
|
use url::Url;
|
||||||
|
|
||||||
|
#[derive(Clone, Debug, serde::Deserialize, serde::Serialize)]
|
||||||
|
#[serde(rename_all = "camelCase")]
|
||||||
|
pub struct BlockUserFromCommunity {
|
||||||
|
actor: Url,
|
||||||
|
to: PublicUrl,
|
||||||
|
pub(in crate::activities_new::community) object: Url,
|
||||||
|
cc: [Url; 1],
|
||||||
|
#[serde(rename = "type")]
|
||||||
|
kind: BlockType,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[async_trait::async_trait(?Send)]
|
||||||
|
impl VerifyActivity for Activity<BlockUserFromCommunity> {
|
||||||
|
async fn verify(&self, context: &LemmyContext) -> Result<(), LemmyError> {
|
||||||
|
verify_domains_match(&self.inner.actor, self.id_unchecked())?;
|
||||||
|
check_is_apub_id_valid(&self.inner.actor, false)?;
|
||||||
|
verify_mod_action(self.inner.actor.clone(), self.inner.cc[0].clone(), context).await
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[async_trait::async_trait(?Send)]
|
||||||
|
impl ReceiveActivity for Activity<BlockUserFromCommunity> {
|
||||||
|
async fn receive(
|
||||||
|
&self,
|
||||||
|
context: &LemmyContext,
|
||||||
|
request_counter: &mut i32,
|
||||||
|
) -> Result<(), LemmyError> {
|
||||||
|
let community =
|
||||||
|
get_or_fetch_and_upsert_community(&self.inner.cc[0], context, request_counter).await?;
|
||||||
|
let blocked_user =
|
||||||
|
get_or_fetch_and_upsert_person(&self.inner.object, context, request_counter).await?;
|
||||||
|
|
||||||
|
let community_user_ban_form = CommunityPersonBanForm {
|
||||||
|
community_id: community.id,
|
||||||
|
person_id: blocked_user.id,
|
||||||
|
};
|
||||||
|
|
||||||
|
blocking(context.pool(), move |conn: &'_ _| {
|
||||||
|
CommunityPersonBan::ban(conn, &community_user_ban_form)
|
||||||
|
})
|
||||||
|
.await??;
|
||||||
|
|
||||||
|
// Also unsubscribe them from the community, if they are subscribed
|
||||||
|
let community_follower_form = CommunityFollowerForm {
|
||||||
|
community_id: community.id,
|
||||||
|
person_id: blocked_user.id,
|
||||||
|
pending: false,
|
||||||
|
};
|
||||||
|
blocking(context.pool(), move |conn: &'_ _| {
|
||||||
|
CommunityFollower::unfollow(conn, &community_follower_form)
|
||||||
|
})
|
||||||
|
.await?
|
||||||
|
.ok();
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
|
@ -10,8 +10,10 @@ use lemmy_utils::LemmyError;
|
||||||
use lemmy_websocket::{messages::SendCommunityRoomMessage, LemmyContext};
|
use lemmy_websocket::{messages::SendCommunityRoomMessage, LemmyContext};
|
||||||
use url::Url;
|
use url::Url;
|
||||||
|
|
||||||
|
pub mod block_user;
|
||||||
pub mod delete;
|
pub mod delete;
|
||||||
pub mod remove;
|
pub mod remove;
|
||||||
|
pub mod undo_block_user;
|
||||||
pub mod undo_delete;
|
pub mod undo_delete;
|
||||||
pub mod undo_remove;
|
pub mod undo_remove;
|
||||||
pub mod update;
|
pub mod update;
|
||||||
|
@ -38,6 +40,7 @@ async fn send_websocket_message<OP: ToString + Send + lemmy_websocket::Operation
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: why do we have this and verify_mod_action() ?
|
||||||
async fn verify_is_community_mod(
|
async fn verify_is_community_mod(
|
||||||
actor: Url,
|
actor: Url,
|
||||||
community: Url,
|
community: Url,
|
||||||
|
|
|
@ -0,0 +1,64 @@
|
||||||
|
use crate::{
|
||||||
|
activities_new::{community::block_user::BlockUserFromCommunity, verify_mod_action},
|
||||||
|
inbox::new_inbox_routing::Activity,
|
||||||
|
};
|
||||||
|
use activitystreams::activity::kind::BlockType;
|
||||||
|
use lemmy_api_common::blocking;
|
||||||
|
use lemmy_apub::{
|
||||||
|
check_is_apub_id_valid,
|
||||||
|
fetcher::{community::get_or_fetch_and_upsert_community, person::get_or_fetch_and_upsert_person},
|
||||||
|
};
|
||||||
|
use lemmy_apub_lib::{verify_domains_match, PublicUrl, ReceiveActivity, VerifyActivity};
|
||||||
|
use lemmy_db_queries::Bannable;
|
||||||
|
use lemmy_db_schema::source::community::{CommunityPersonBan, CommunityPersonBanForm};
|
||||||
|
use lemmy_utils::LemmyError;
|
||||||
|
use lemmy_websocket::LemmyContext;
|
||||||
|
use url::Url;
|
||||||
|
|
||||||
|
#[derive(Clone, Debug, serde::Deserialize, serde::Serialize)]
|
||||||
|
#[serde(rename_all = "camelCase")]
|
||||||
|
pub struct UndoBlockUserFromCommunity {
|
||||||
|
actor: Url,
|
||||||
|
to: PublicUrl,
|
||||||
|
object: Activity<BlockUserFromCommunity>,
|
||||||
|
cc: [Url; 1],
|
||||||
|
#[serde(rename = "type")]
|
||||||
|
kind: BlockType,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[async_trait::async_trait(?Send)]
|
||||||
|
impl VerifyActivity for Activity<UndoBlockUserFromCommunity> {
|
||||||
|
async fn verify(&self, context: &LemmyContext) -> Result<(), LemmyError> {
|
||||||
|
verify_domains_match(&self.inner.actor, self.id_unchecked())?;
|
||||||
|
check_is_apub_id_valid(&self.inner.actor, false)?;
|
||||||
|
verify_mod_action(self.inner.actor.clone(), self.inner.cc[0].clone(), context).await?;
|
||||||
|
self.inner.object.verify(context).await
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[async_trait::async_trait(?Send)]
|
||||||
|
impl ReceiveActivity for Activity<UndoBlockUserFromCommunity> {
|
||||||
|
async fn receive(
|
||||||
|
&self,
|
||||||
|
context: &LemmyContext,
|
||||||
|
request_counter: &mut i32,
|
||||||
|
) -> Result<(), LemmyError> {
|
||||||
|
let community =
|
||||||
|
get_or_fetch_and_upsert_community(&self.inner.cc[0], context, request_counter).await?;
|
||||||
|
let blocked_user =
|
||||||
|
get_or_fetch_and_upsert_person(&self.inner.object.inner.object, context, request_counter)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
let community_user_ban_form = CommunityPersonBanForm {
|
||||||
|
community_id: community.id,
|
||||||
|
person_id: blocked_user.id,
|
||||||
|
};
|
||||||
|
|
||||||
|
blocking(context.pool(), move |conn: &'_ _| {
|
||||||
|
CommunityPersonBan::unban(conn, &community_user_ban_form)
|
||||||
|
})
|
||||||
|
.await??;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
|
@ -3,18 +3,10 @@ use crate::inbox::{
|
||||||
get_activity_id,
|
get_activity_id,
|
||||||
inbox_verify_http_signature,
|
inbox_verify_http_signature,
|
||||||
is_activity_already_known,
|
is_activity_already_known,
|
||||||
receive_for_community::{
|
receive_for_community::receive_add_for_community,
|
||||||
receive_add_for_community,
|
|
||||||
receive_block_user_for_community,
|
|
||||||
receive_remove_for_community,
|
|
||||||
receive_undo_for_community,
|
|
||||||
},
|
|
||||||
verify_is_addressed_to_public,
|
verify_is_addressed_to_public,
|
||||||
};
|
};
|
||||||
use activitystreams::{
|
use activitystreams::{activity::ActorAndObject, prelude::*};
|
||||||
activity::{kind::FollowType, ActorAndObject},
|
|
||||||
prelude::*,
|
|
||||||
};
|
|
||||||
use actix_web::{web, HttpRequest, HttpResponse};
|
use actix_web::{web, HttpRequest, HttpResponse};
|
||||||
use anyhow::{anyhow, Context};
|
use anyhow::{anyhow, Context};
|
||||||
use lemmy_api_common::blocking;
|
use lemmy_api_common::blocking;
|
||||||
|
@ -32,7 +24,6 @@ use lemmy_websocket::LemmyContext;
|
||||||
use log::info;
|
use log::info;
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
use std::fmt::Debug;
|
use std::fmt::Debug;
|
||||||
use url::Url;
|
|
||||||
|
|
||||||
/// Allowed activities for community inbox.
|
/// Allowed activities for community inbox.
|
||||||
#[derive(Clone, Debug, Eq, Ord, PartialEq, PartialOrd, Deserialize, Serialize)]
|
#[derive(Clone, Debug, Eq, Ord, PartialEq, PartialOrd, Deserialize, Serialize)]
|
||||||
|
@ -122,20 +113,10 @@ pub(crate) async fn community_receive_message(
|
||||||
);
|
);
|
||||||
|
|
||||||
let any_base = activity.clone().into_any_base()?;
|
let any_base = activity.clone().into_any_base()?;
|
||||||
let actor_url = actor.actor_id();
|
|
||||||
let activity_kind = activity.kind().context(location_info!())?;
|
let activity_kind = activity.kind().context(location_info!())?;
|
||||||
let do_announce = match activity_kind {
|
let do_announce = match activity_kind {
|
||||||
CommunityValidTypes::Follow => todo!(),
|
CommunityValidTypes::Follow => todo!(),
|
||||||
CommunityValidTypes::Undo => {
|
CommunityValidTypes::Undo => todo!(),
|
||||||
Box::pin(handle_undo(
|
|
||||||
context,
|
|
||||||
activity.clone(),
|
|
||||||
actor_url,
|
|
||||||
&to_community,
|
|
||||||
request_counter,
|
|
||||||
))
|
|
||||||
.await?
|
|
||||||
}
|
|
||||||
CommunityValidTypes::Create => todo!(),
|
CommunityValidTypes::Create => todo!(),
|
||||||
CommunityValidTypes::Update => todo!(),
|
CommunityValidTypes::Update => todo!(),
|
||||||
CommunityValidTypes::Like => todo!(),
|
CommunityValidTypes::Like => todo!(),
|
||||||
|
@ -151,26 +132,8 @@ pub(crate) async fn community_receive_message(
|
||||||
.await?;
|
.await?;
|
||||||
true
|
true
|
||||||
}
|
}
|
||||||
CommunityValidTypes::Remove => {
|
CommunityValidTypes::Remove => todo!(),
|
||||||
Box::pin(receive_remove_for_community(
|
CommunityValidTypes::Block => todo!(),
|
||||||
context,
|
|
||||||
any_base.clone(),
|
|
||||||
None,
|
|
||||||
request_counter,
|
|
||||||
))
|
|
||||||
.await?;
|
|
||||||
true
|
|
||||||
}
|
|
||||||
CommunityValidTypes::Block => {
|
|
||||||
Box::pin(receive_block_user_for_community(
|
|
||||||
context,
|
|
||||||
any_base.clone(),
|
|
||||||
None,
|
|
||||||
request_counter,
|
|
||||||
))
|
|
||||||
.await?;
|
|
||||||
true
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
if do_announce {
|
if do_announce {
|
||||||
|
@ -195,22 +158,3 @@ pub(crate) async fn community_receive_message(
|
||||||
|
|
||||||
Ok(HttpResponse::Ok().finish())
|
Ok(HttpResponse::Ok().finish())
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn handle_undo(
|
|
||||||
context: &LemmyContext,
|
|
||||||
activity: CommunityAcceptedActivities,
|
|
||||||
actor_url: Url,
|
|
||||||
_to_community: &Community,
|
|
||||||
request_counter: &mut i32,
|
|
||||||
) -> Result<bool, LemmyError> {
|
|
||||||
let inner_kind = activity
|
|
||||||
.object()
|
|
||||||
.is_single_kind(&FollowType::Follow.to_string());
|
|
||||||
let any_base = activity.into_any_base()?;
|
|
||||||
if inner_kind {
|
|
||||||
todo!()
|
|
||||||
} else {
|
|
||||||
receive_undo_for_community(context, any_base, None, &actor_url, request_counter).await?;
|
|
||||||
Ok(true)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
|
@ -68,9 +68,8 @@ impl<Kind> Activity<Kind> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: this is probably wrong, it contains all activities
|
|
||||||
#[derive(Clone, Debug, serde::Deserialize, serde::Serialize)]
|
#[derive(Clone, Debug, serde::Deserialize, serde::Serialize)]
|
||||||
pub enum PersonAcceptedActivitiesNew {
|
pub enum SharedInboxActivities {
|
||||||
FollowCommunity(FollowCommunity),
|
FollowCommunity(FollowCommunity),
|
||||||
AcceptFollowCommunity(AcceptFollowCommunity),
|
AcceptFollowCommunity(AcceptFollowCommunity),
|
||||||
UndoFollowCommunity(UndoFollowCommunity),
|
UndoFollowCommunity(UndoFollowCommunity),
|
||||||
|
@ -107,14 +106,14 @@ pub enum PersonAcceptedActivitiesNew {
|
||||||
|
|
||||||
// todo: can probably get rid of these?
|
// todo: can probably get rid of these?
|
||||||
#[async_trait::async_trait(?Send)]
|
#[async_trait::async_trait(?Send)]
|
||||||
impl VerifyActivity for PersonAcceptedActivitiesNew {
|
impl VerifyActivity for SharedInboxActivities {
|
||||||
async fn verify(&self, context: &LemmyContext) -> Result<(), LemmyError> {
|
async fn verify(&self, context: &LemmyContext) -> Result<(), LemmyError> {
|
||||||
self.verify(context).await
|
self.verify(context).await
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[async_trait::async_trait(?Send)]
|
#[async_trait::async_trait(?Send)]
|
||||||
impl ReceiveActivity for PersonAcceptedActivitiesNew {
|
impl ReceiveActivity for SharedInboxActivities {
|
||||||
async fn receive(
|
async fn receive(
|
||||||
&self,
|
&self,
|
||||||
context: &LemmyContext,
|
context: &LemmyContext,
|
||||||
|
|
|
@ -4,13 +4,8 @@ use crate::{
|
||||||
is_activity_already_known,
|
is_activity_already_known,
|
||||||
is_addressed_to_community_followers,
|
is_addressed_to_community_followers,
|
||||||
is_addressed_to_local_person,
|
is_addressed_to_local_person,
|
||||||
new_inbox_routing::{Activity, PersonAcceptedActivitiesNew},
|
new_inbox_routing::{Activity, SharedInboxActivities},
|
||||||
receive_for_community::{
|
receive_for_community::receive_add_for_community,
|
||||||
receive_add_for_community,
|
|
||||||
receive_block_user_for_community,
|
|
||||||
receive_remove_for_community,
|
|
||||||
receive_undo_for_community,
|
|
||||||
},
|
|
||||||
verify_is_addressed_to_public,
|
verify_is_addressed_to_public,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
@ -51,7 +46,7 @@ pub type PersonAcceptedActivities = ActorAndObject<PersonValidTypes>;
|
||||||
/// Handler for all incoming activities to person inboxes.
|
/// Handler for all incoming activities to person inboxes.
|
||||||
pub async fn person_inbox(
|
pub async fn person_inbox(
|
||||||
_request: HttpRequest,
|
_request: HttpRequest,
|
||||||
input: web::Json<Activity<PersonAcceptedActivitiesNew>>,
|
input: web::Json<Activity<SharedInboxActivities>>,
|
||||||
_path: web::Path<String>,
|
_path: web::Path<String>,
|
||||||
context: web::Data<LemmyContext>,
|
context: web::Data<LemmyContext>,
|
||||||
) -> Result<HttpResponse, LemmyError> {
|
) -> Result<HttpResponse, LemmyError> {
|
||||||
|
@ -217,26 +212,12 @@ pub async fn receive_announce(
|
||||||
Some(Like) => todo!(),
|
Some(Like) => todo!(),
|
||||||
Some(Dislike) => todo!(),
|
Some(Dislike) => todo!(),
|
||||||
Some(Delete) => todo!(),
|
Some(Delete) => todo!(),
|
||||||
Some(Remove) => {
|
Some(Remove) => todo!(),
|
||||||
receive_remove_for_community(context, inner_activity, Some(announce), request_counter).await
|
Some(Undo) => todo!(),
|
||||||
}
|
|
||||||
Some(Undo) => {
|
|
||||||
receive_undo_for_community(
|
|
||||||
context,
|
|
||||||
inner_activity,
|
|
||||||
Some(announce),
|
|
||||||
&inner_id,
|
|
||||||
request_counter,
|
|
||||||
)
|
|
||||||
.await
|
|
||||||
}
|
|
||||||
Some(Add) => {
|
Some(Add) => {
|
||||||
receive_add_for_community(context, inner_activity, Some(announce), request_counter).await
|
receive_add_for_community(context, inner_activity, Some(announce), request_counter).await
|
||||||
}
|
}
|
||||||
Some(Block) => {
|
Some(Block) => todo!(),
|
||||||
receive_block_user_for_community(context, inner_activity, Some(announce), request_counter)
|
|
||||||
.await
|
|
||||||
}
|
|
||||||
_ => receive_unhandled_activity(inner_activity),
|
_ => receive_unhandled_activity(inner_activity),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
use crate::{
|
use crate::{
|
||||||
activities::receive::{receive_unhandled_activity, verify_activity_domains_valid},
|
activities::receive::verify_activity_domains_valid,
|
||||||
inbox::verify_is_addressed_to_public,
|
inbox::verify_is_addressed_to_public,
|
||||||
};
|
};
|
||||||
use activitystreams::{
|
use activitystreams::{
|
||||||
activity::{ActorAndObjectRef, Add, Announce, Block, OptTargetRef, Remove, Undo},
|
activity::{ActorAndObjectRef, Add, Announce, OptTargetRef},
|
||||||
base::AnyBase,
|
base::AnyBase,
|
||||||
object::AsObject,
|
object::AsObject,
|
||||||
prelude::*,
|
prelude::*,
|
||||||
|
@ -15,24 +15,10 @@ use lemmy_apub::{
|
||||||
generate_moderators_url,
|
generate_moderators_url,
|
||||||
CommunityType,
|
CommunityType,
|
||||||
};
|
};
|
||||||
use lemmy_db_queries::{
|
use lemmy_db_queries::{source::community::CommunityModerator_, ApubObject, Joinable};
|
||||||
source::community::CommunityModerator_,
|
|
||||||
ApubObject,
|
|
||||||
Bannable,
|
|
||||||
Followable,
|
|
||||||
Joinable,
|
|
||||||
};
|
|
||||||
use lemmy_db_schema::{
|
use lemmy_db_schema::{
|
||||||
source::{
|
source::{
|
||||||
community::{
|
community::{Community, CommunityModerator, CommunityModeratorForm},
|
||||||
Community,
|
|
||||||
CommunityFollower,
|
|
||||||
CommunityFollowerForm,
|
|
||||||
CommunityModerator,
|
|
||||||
CommunityModeratorForm,
|
|
||||||
CommunityPersonBan,
|
|
||||||
CommunityPersonBanForm,
|
|
||||||
},
|
|
||||||
person::Person,
|
person::Person,
|
||||||
},
|
},
|
||||||
DbUrl,
|
DbUrl,
|
||||||
|
@ -41,7 +27,6 @@ use lemmy_db_views_actor::community_view::CommunityView;
|
||||||
use lemmy_utils::{location_info, LemmyError};
|
use lemmy_utils::{location_info, LemmyError};
|
||||||
use lemmy_websocket::LemmyContext;
|
use lemmy_websocket::LemmyContext;
|
||||||
use strum_macros::EnumString;
|
use strum_macros::EnumString;
|
||||||
use url::Url;
|
|
||||||
|
|
||||||
#[derive(EnumString)]
|
#[derive(EnumString)]
|
||||||
enum PageOrNote {
|
enum PageOrNote {
|
||||||
|
@ -57,48 +42,6 @@ enum ObjectTypes {
|
||||||
Person,
|
Person,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// This file is for post/comment activities received by the community, and for post/comment
|
|
||||||
/// activities announced by the community and received by the person.
|
|
||||||
|
|
||||||
/// A post or comment being removed by a mod/admin
|
|
||||||
pub(in crate::inbox) async fn receive_remove_for_community(
|
|
||||||
context: &LemmyContext,
|
|
||||||
remove_any_base: AnyBase,
|
|
||||||
announce: Option<Announce>,
|
|
||||||
request_counter: &mut i32,
|
|
||||||
) -> Result<(), LemmyError> {
|
|
||||||
let remove = Remove::from_any_base(remove_any_base.to_owned())?.context(location_info!())?;
|
|
||||||
let community = extract_community_from_cc(&remove, context).await?;
|
|
||||||
|
|
||||||
verify_mod_activity(&remove, announce, &community, context).await?;
|
|
||||||
verify_is_addressed_to_public(&remove)?;
|
|
||||||
|
|
||||||
if remove.target().is_some() {
|
|
||||||
let remove_mod = remove
|
|
||||||
.object()
|
|
||||||
.as_single_xsd_any_uri()
|
|
||||||
.context(location_info!())?;
|
|
||||||
let remove_mod = get_or_fetch_and_upsert_person(&remove_mod, context, request_counter).await?;
|
|
||||||
let form = CommunityModeratorForm {
|
|
||||||
community_id: community.id,
|
|
||||||
person_id: remove_mod.id,
|
|
||||||
};
|
|
||||||
blocking(context.pool(), move |conn| {
|
|
||||||
CommunityModerator::leave(conn, &form)
|
|
||||||
})
|
|
||||||
.await??;
|
|
||||||
community
|
|
||||||
.send_announce(
|
|
||||||
remove_any_base,
|
|
||||||
remove.object().clone().single_xsd_any_uri(),
|
|
||||||
context,
|
|
||||||
)
|
|
||||||
.await?;
|
|
||||||
// TODO: send websocket notification about removed mod
|
|
||||||
}
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(EnumString)]
|
#[derive(EnumString)]
|
||||||
enum UndoableActivities {
|
enum UndoableActivities {
|
||||||
Delete,
|
Delete,
|
||||||
|
@ -108,42 +51,6 @@ enum UndoableActivities {
|
||||||
Block,
|
Block,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A post/comment action being reverted (either a delete, remove, upvote or downvote)
|
|
||||||
pub(in crate::inbox) async fn receive_undo_for_community(
|
|
||||||
context: &LemmyContext,
|
|
||||||
activity: AnyBase,
|
|
||||||
announce: Option<Announce>,
|
|
||||||
expected_domain: &Url,
|
|
||||||
request_counter: &mut i32,
|
|
||||||
) -> Result<(), LemmyError> {
|
|
||||||
let undo = Undo::from_any_base(activity)?.context(location_info!())?;
|
|
||||||
verify_activity_domains_valid(&undo, &expected_domain.to_owned(), true)?;
|
|
||||||
verify_is_addressed_to_public(&undo)?;
|
|
||||||
|
|
||||||
use UndoableActivities::*;
|
|
||||||
match undo
|
|
||||||
.object()
|
|
||||||
.as_single_kind_str()
|
|
||||||
.and_then(|s| s.parse().ok())
|
|
||||||
{
|
|
||||||
Some(Delete) => todo!(),
|
|
||||||
Some(Remove) => todo!(),
|
|
||||||
Some(Like) => todo!(),
|
|
||||||
Some(Dislike) => todo!(),
|
|
||||||
Some(Block) => {
|
|
||||||
receive_undo_block_user_for_community(
|
|
||||||
context,
|
|
||||||
undo,
|
|
||||||
announce,
|
|
||||||
expected_domain,
|
|
||||||
request_counter,
|
|
||||||
)
|
|
||||||
.await
|
|
||||||
}
|
|
||||||
_ => receive_unhandled_activity(undo),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Add a new mod to the community (can only be done by an existing mod).
|
/// Add a new mod to the community (can only be done by an existing mod).
|
||||||
pub(in crate::inbox) async fn receive_add_for_community(
|
pub(in crate::inbox) async fn receive_add_for_community(
|
||||||
context: &LemmyContext,
|
context: &LemmyContext,
|
||||||
|
@ -194,85 +101,6 @@ pub(in crate::inbox) async fn receive_add_for_community(
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) async fn receive_block_user_for_community(
|
|
||||||
context: &LemmyContext,
|
|
||||||
block_any_base: AnyBase,
|
|
||||||
announce: Option<Announce>,
|
|
||||||
request_counter: &mut i32,
|
|
||||||
) -> Result<(), LemmyError> {
|
|
||||||
let block = Block::from_any_base(block_any_base.to_owned())?.context(location_info!())?;
|
|
||||||
let community = extract_community_from_cc(&block, context).await?;
|
|
||||||
|
|
||||||
verify_mod_activity(&block, announce, &community, context).await?;
|
|
||||||
verify_is_addressed_to_public(&block)?;
|
|
||||||
|
|
||||||
let blocked_user = block
|
|
||||||
.object()
|
|
||||||
.as_single_xsd_any_uri()
|
|
||||||
.context(location_info!())?;
|
|
||||||
let blocked_user =
|
|
||||||
get_or_fetch_and_upsert_person(&blocked_user, context, request_counter).await?;
|
|
||||||
|
|
||||||
let community_user_ban_form = CommunityPersonBanForm {
|
|
||||||
community_id: community.id,
|
|
||||||
person_id: blocked_user.id,
|
|
||||||
};
|
|
||||||
|
|
||||||
blocking(context.pool(), move |conn: &'_ _| {
|
|
||||||
CommunityPersonBan::ban(conn, &community_user_ban_form)
|
|
||||||
})
|
|
||||||
.await??;
|
|
||||||
|
|
||||||
// Also unsubscribe them from the community, if they are subscribed
|
|
||||||
let community_follower_form = CommunityFollowerForm {
|
|
||||||
community_id: community.id,
|
|
||||||
person_id: blocked_user.id,
|
|
||||||
pending: false,
|
|
||||||
};
|
|
||||||
blocking(context.pool(), move |conn: &'_ _| {
|
|
||||||
CommunityFollower::unfollow(conn, &community_follower_form)
|
|
||||||
})
|
|
||||||
.await?
|
|
||||||
.ok();
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) async fn receive_undo_block_user_for_community(
|
|
||||||
context: &LemmyContext,
|
|
||||||
undo: Undo,
|
|
||||||
announce: Option<Announce>,
|
|
||||||
expected_domain: &Url,
|
|
||||||
request_counter: &mut i32,
|
|
||||||
) -> Result<(), LemmyError> {
|
|
||||||
let object = undo.object().clone().one().context(location_info!())?;
|
|
||||||
let block = Block::from_any_base(object)?.context(location_info!())?;
|
|
||||||
let community = extract_community_from_cc(&block, context).await?;
|
|
||||||
|
|
||||||
verify_activity_domains_valid(&block, &expected_domain, false)?;
|
|
||||||
verify_is_addressed_to_public(&block)?;
|
|
||||||
verify_undo_remove_actor_instance(&undo, &block, &announce, context).await?;
|
|
||||||
|
|
||||||
let blocked_user = block
|
|
||||||
.object()
|
|
||||||
.as_single_xsd_any_uri()
|
|
||||||
.context(location_info!())?;
|
|
||||||
let blocked_user =
|
|
||||||
get_or_fetch_and_upsert_person(&blocked_user, context, request_counter).await?;
|
|
||||||
|
|
||||||
let community_user_ban_form = CommunityPersonBanForm {
|
|
||||||
community_id: community.id,
|
|
||||||
person_id: blocked_user.id,
|
|
||||||
};
|
|
||||||
|
|
||||||
blocking(context.pool(), move |conn: &'_ _| {
|
|
||||||
CommunityPersonBan::unban(conn, &community_user_ban_form)
|
|
||||||
})
|
|
||||||
.await??;
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Searches the activity's cc field for a Community ID, and returns the community.
|
/// Searches the activity's cc field for a Community ID, and returns the community.
|
||||||
async fn extract_community_from_cc<T, Kind>(
|
async fn extract_community_from_cc<T, Kind>(
|
||||||
activity: &T,
|
activity: &T,
|
||||||
|
@ -384,21 +212,3 @@ where
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) async fn verify_undo_remove_actor_instance<T, Kind>(
|
|
||||||
undo: &Undo,
|
|
||||||
inner: &T,
|
|
||||||
announce: &Option<Announce>,
|
|
||||||
context: &LemmyContext,
|
|
||||||
) -> Result<(), LemmyError>
|
|
||||||
where
|
|
||||||
T: ActorAndObjectRef + BaseExt<Kind> + AsObject<Kind>,
|
|
||||||
{
|
|
||||||
if announce.is_none() {
|
|
||||||
let community = extract_community_from_cc(undo, context).await?;
|
|
||||||
verify_mod_activity(undo, announce.to_owned(), &community, context).await?;
|
|
||||||
verify_mod_activity(inner, announce.to_owned(), &community, context).await?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
Loading…
Reference in a new issue