From 6ba8434f407564718b3eec0abce38ed0d7380d55 Mon Sep 17 00:00:00 2001 From: silverpill Date: Mon, 16 Jan 2023 22:52:22 +0000 Subject: [PATCH] Add delete-emoji command --- docs/mitractl.md | 6 ++++++ src/bin/mitractl.rs | 1 + src/cli.rs | 21 ++++++++++++++++++ src/models/cleanup.rs | 4 ++++ src/models/emojis/queries.rs | 42 ++++++++++++++++++++++++++++++++++++ 5 files changed, 74 insertions(+) diff --git a/docs/mitractl.md b/docs/mitractl.md index 1b3059b..cec76ed 100644 --- a/docs/mitractl.md +++ b/docs/mitractl.md @@ -50,6 +50,12 @@ Delete post: mitractl delete-post 55a3005f-f293-4168-ab70-6ab09a879679 ``` +Delete custom emoji: + +```shell +mitractl delete-emoji 55a3005f-f293-4168-ab70-6ab09a879679 +``` + Remove remote posts and media older than 30 days: ```shell diff --git a/src/bin/mitractl.rs b/src/bin/mitractl.rs index 8f9a987..c2f06ca 100644 --- a/src/bin/mitractl.rs +++ b/src/bin/mitractl.rs @@ -29,6 +29,7 @@ async fn main() { SubCommand::RefetchActor(cmd) => cmd.execute(&config, db_client).await.unwrap(), SubCommand::DeleteProfile(cmd) => cmd.execute(&config, db_client).await.unwrap(), SubCommand::DeletePost(cmd) => cmd.execute(&config, db_client).await.unwrap(), + SubCommand::DeleteEmoji(cmd) => cmd.execute(&config, db_client).await.unwrap(), SubCommand::DeleteExtraneousPosts(cmd) => cmd.execute(&config, db_client).await.unwrap(), SubCommand::DeleteUnusedAttachments(cmd) => cmd.execute(&config, db_client).await.unwrap(), SubCommand::DeleteOrphanedFiles(cmd) => cmd.execute(&config, db_client).await.unwrap(), diff --git a/src/cli.rs b/src/cli.rs index 9f200ac..09f2064 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -16,6 +16,7 @@ use crate::ethereum::sync::save_current_block_number; use crate::ethereum::utils::key_to_ethereum_address; use crate::models::attachments::queries::delete_unused_attachments; use crate::models::cleanup::find_orphaned_files; +use crate::models::emojis::queries::delete_emoji; use crate::models::posts::queries::{delete_post, find_extraneous_posts, get_post_by_id}; use crate::models::profiles::queries::{ delete_profile, @@ -62,6 +63,7 @@ pub enum SubCommand { RefetchActor(RefetchActor), DeleteProfile(DeleteProfile), DeletePost(DeletePost), + DeleteEmoji(DeleteEmoji), DeleteExtraneousPosts(DeleteExtraneousPosts), DeleteUnusedAttachments(DeleteUnusedAttachments), DeleteOrphanedFiles(DeleteOrphanedFiles), @@ -251,6 +253,25 @@ impl DeletePost { } } +/// Delete custom emoji +#[derive(Parser)] +pub struct DeleteEmoji { + id: Uuid, +} + +impl DeleteEmoji { + pub async fn execute( + &self, + config: &Config, + db_client: &impl GenericClient, + ) -> Result<(), Error> { + let deletion_queue = delete_emoji(db_client, &self.id).await?; + deletion_queue.process(config).await; + println!("emoji deleted"); + Ok(()) + } +} + /// Delete old remote posts #[derive(Parser)] pub struct DeleteExtraneousPosts { diff --git a/src/models/cleanup.rs b/src/models/cleanup.rs index 9679227..8ffdb63 100644 --- a/src/models/cleanup.rs +++ b/src/models/cleanup.rs @@ -47,6 +47,10 @@ pub async fn find_orphaned_files( WHERE avatar ->> 'file_name' = fname OR banner ->> 'file_name' = fname ) + AND NOT EXISTS ( + SELECT 1 FROM emoji + WHERE image ->> 'file_name' = fname + ) ", &[&files], ).await?; diff --git a/src/models/emojis/queries.rs b/src/models/emojis/queries.rs index a4aff0c..22d28f6 100644 --- a/src/models/emojis/queries.rs +++ b/src/models/emojis/queries.rs @@ -4,6 +4,7 @@ use uuid::Uuid; use crate::database::{catch_unique_violation, DatabaseError}; use crate::models::{ + cleanup::{find_orphaned_files, DeletionQueue}, instances::queries::create_instance, profiles::types::ProfileImage, }; @@ -99,6 +100,29 @@ pub async fn get_emoji_by_remote_object_id( Ok(emoji) } +pub async fn delete_emoji( + db_client: &impl GenericClient, + emoji_id: &Uuid, +) -> Result { + let maybe_row = db_client.query_opt( + " + DELETE FROM emoji WHERE id = $1 + RETURNING emoji + ", + &[&emoji_id], + ).await?; + let row = maybe_row.ok_or(DatabaseError::NotFound("emoji"))?; + let emoji: DbEmoji = row.try_get("emoji")?; + let orphaned_files = find_orphaned_files( + db_client, + vec![emoji.image.file_name], + ).await?; + Ok(DeletionQueue { + files: orphaned_files, + ipfs_objects: vec![], + }) +} + #[cfg(test)] mod tests { use serial_test::serial; @@ -132,4 +156,22 @@ mod tests { assert_eq!(emoji.emoji_name, emoji_name); assert_eq!(emoji.hostname, Some(hostname.to_string())); } + + #[tokio::test] + #[serial] + async fn test_delete_emoji() { + let db_client = &create_test_database().await; + let emoji = create_emoji( + db_client, + "test", + None, + "test.png", + "image/png", + None, + &Utc::now(), + ).await.unwrap(); + let deletion_queue = delete_emoji(db_client, &emoji.id).await.unwrap(); + assert_eq!(deletion_queue.files.len(), 1); + assert_eq!(deletion_queue.ipfs_objects.len(), 0); + } }