From 818aff46d40d444fef40277dd3b4cade4987ddc4 Mon Sep 17 00:00:00 2001 From: appflowy Date: Thu, 28 Oct 2021 13:42:39 +0800 Subject: [PATCH] [server]: delete the trash's target --- app_flowy/.vscode/settings.json | 2 +- .../scrolling/styled_scroll_bar.dart | 2 +- backend/scripts/database/database.mk | 2 +- backend/src/service/trash/router.rs | 2 +- backend/src/service/trash/trash.rs | 45 ++++++++++++++- .../src/entities/trash/trash_create.rs | 10 ++++ .../flowy-workspace/src/services/trash_can.rs | 55 +++++++++++-------- .../src/services/view_controller.rs | 3 +- 8 files changed, 92 insertions(+), 29 deletions(-) diff --git a/app_flowy/.vscode/settings.json b/app_flowy/.vscode/settings.json index 3af73866a3..0d913b05e6 100644 --- a/app_flowy/.vscode/settings.json +++ b/app_flowy/.vscode/settings.json @@ -1,6 +1,6 @@ { "[dart]": { - "editor.formatOnSave": true, + "editor.formatOnSave": false, "editor.formatOnType": true, "editor.rulers": [ 120 diff --git a/app_flowy/packages/flowy_infra_ui/lib/style_widget/scrolling/styled_scroll_bar.dart b/app_flowy/packages/flowy_infra_ui/lib/style_widget/scrolling/styled_scroll_bar.dart index db91b600ef..5309f3deaa 100644 --- a/app_flowy/packages/flowy_infra_ui/lib/style_widget/scrolling/styled_scroll_bar.dart +++ b/app_flowy/packages/flowy_infra_ui/lib/style_widget/scrolling/styled_scroll_bar.dart @@ -173,7 +173,7 @@ class ScrollbarState extends State { ), ), ) - ]).opacity(showHandle ? 1.0 : 0.0, animate: true); + ]).opacity(showHandle ? 1.0 : 0.0, animate: false); }, ); } diff --git a/backend/scripts/database/database.mk b/backend/scripts/database/database.mk index 6b44a8b195..5792873a49 100644 --- a/backend/scripts/database/database.mk +++ b/backend/scripts/database/database.mk @@ -9,7 +9,7 @@ export ROOT = "./scripts/database" init_postgres: ${ROOT}/init_postgres.sh -init_database: +init_database: init_postgres ${ROOT}/init_database.sh reset_db: diff --git a/backend/src/service/trash/router.rs b/backend/src/service/trash/router.rs index dc5061268d..58331246c1 100644 --- a/backend/src/service/trash/router.rs +++ b/backend/src/service/trash/router.rs @@ -31,7 +31,7 @@ pub async fn create_handler( .begin() .await .context("Failed to acquire a Postgres connection to create trash")?; - log::error!("😁create handler: {:?}", params); + let _ = create_trash(&mut transaction, make_records(params)?, logged_user).await?; transaction diff --git a/backend/src/service/trash/trash.rs b/backend/src/service/trash/trash.rs index 0fbb263147..2468dd73cc 100644 --- a/backend/src/service/trash/trash.rs +++ b/backend/src/service/trash/trash.rs @@ -9,7 +9,7 @@ use crate::{ use ::protobuf::ProtobufEnum; use flowy_net::errors::ServerError; use flowy_workspace::protobuf::{RepeatedTrash, Trash, TrashType}; -use sqlx::{postgres::PgArguments, Postgres}; +use sqlx::{postgres::PgArguments, Postgres, Row}; use uuid::Uuid; pub(crate) async fn create_trash( @@ -33,10 +33,25 @@ pub(crate) async fn create_trash( Ok(()) } +#[tracing::instrument(skip(transaction, user), fields(delete_rows), err)] pub(crate) async fn delete_all_trash( transaction: &mut DBTransaction<'_>, user: &LoggedUser, ) -> Result<(), ServerError> { + let (sql, args) = SqlBuilder::select(TRASH_TABLE) + .and_where_eq("user_id", &user.user_id) + .build()?; + let rows = sqlx::query_with(&sql, args) + .fetch_all(transaction as &mut DBTransaction<'_>) + .await + .map_err(map_sqlx_error)? + .into_iter() + .map(|row| (row.get("id"), row.get("ty"))) + .collect::>(); + tracing::Span::current().record("delete_rows", &format!("{:?}", rows).as_str()); + let affected_row_count = rows.len(); + let _ = delete_trash_targets(transaction as &mut DBTransaction<'_>, rows).await?; + let (sql, args) = SqlBuilder::delete(TRASH_TABLE) .and_where_eq("user_id", &user.user_id) .build()?; @@ -44,8 +59,9 @@ pub(crate) async fn delete_all_trash( .execute(transaction as &mut DBTransaction<'_>) .await .map_err(map_sqlx_error)?; - tracing::Span::current().record("affected_row", &result.rows_affected()); + debug_assert_eq!(affected_row_count as u64, result.rows_affected()); + Ok(()) } @@ -76,6 +92,12 @@ pub(crate) async fn delete_trash( }, } + let _ = delete_trash_targets( + transaction as &mut DBTransaction<'_>, + vec![(trash_table.id.clone(), trash_table.ty)], + ) + .await?; + // Delete the trash table let (sql, args) = SqlBuilder::delete(TRASH_TABLE).and_where_eq("id", &trash_id).build()?; let _ = sqlx::query_with(&sql, args) @@ -86,6 +108,25 @@ pub(crate) async fn delete_trash( Ok(()) } +async fn delete_trash_targets( + transaction: &mut DBTransaction<'_>, + targets: Vec<(Uuid, i32)>, +) -> Result<(), ServerError> { + for (id, ty) in targets { + match TrashType::from_i32(ty) { + None => log::error!("Parser trash type with value: {} failed", ty), + Some(ty) => match ty { + TrashType::Unknown => {}, + TrashType::View => { + let _ = delete_view(transaction as &mut DBTransaction<'_>, vec![id]).await; + }, + }, + } + } + + Ok(()) +} + pub(crate) async fn read_trash_ids( user: &LoggedUser, transaction: &mut DBTransaction<'_>, diff --git a/rust-lib/flowy-workspace/src/entities/trash/trash_create.rs b/rust-lib/flowy-workspace/src/entities/trash/trash_create.rs index 61735dd3d3..d78099ed87 100644 --- a/rust-lib/flowy-workspace/src/entities/trash/trash_create.rs +++ b/rust-lib/flowy-workspace/src/entities/trash/trash_create.rs @@ -1,5 +1,6 @@ use crate::impl_def_and_def_mut; use flowy_derive::{ProtoBuf, ProtoBuf_Enum}; +use std::fmt::Formatter; #[derive(PartialEq, Debug, ProtoBuf_Enum, Clone)] pub enum TrashType { @@ -32,6 +33,15 @@ pub struct TrashIdentifiers { pub delete_all: bool, } +impl std::fmt::Display for TrashIdentifiers { + fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { + f.write_str(&format!( + "{:?}", + &self.items.iter().map(|item| &item.id).collect::>() + )) + } +} + impl TrashIdentifiers { pub fn all() -> TrashIdentifiers { TrashIdentifiers { diff --git a/rust-lib/flowy-workspace/src/services/trash_can.rs b/rust-lib/flowy-workspace/src/services/trash_can.rs index 58489cb048..f215436076 100644 --- a/rust-lib/flowy-workspace/src/services/trash_can.rs +++ b/rust-lib/flowy-workspace/src/services/trash_can.rs @@ -67,7 +67,16 @@ impl TrashCan { #[tracing::instrument(level = "debug", skip(self) err)] pub async fn restore_all(&self) -> WorkspaceResult<()> { - let repeated_trash = self.delete_all_trash_on_local()?; + let repeated_trash = thread::scope(|_s| { + let conn = self.database.db_connection()?; + conn.immediate_transaction::<_, WorkspaceError, _>(|| { + let repeated_trash = TrashTableSql::read_all(&*conn)?; + let _ = TrashTableSql::delete_all(&*conn)?; + Ok(repeated_trash) + }) + }) + .unwrap()?; + let identifiers: TrashIdentifiers = repeated_trash.items.clone().into(); let (tx, mut rx) = mpsc::channel::>(1); let _ = self.notify.send(TrashEvent::Putback(identifiers, tx)); @@ -78,34 +87,39 @@ impl TrashCan { Ok(()) } - #[tracing::instrument(level = "debug", skip(self) err)] + #[tracing::instrument(level = "debug", skip(self), err)] pub async fn delete_all(&self) -> WorkspaceResult<()> { - let repeated_trash = self.delete_all_trash_on_local()?; - let identifiers: TrashIdentifiers = repeated_trash.items.clone().into(); - - let (tx, mut rx) = mpsc::channel::>(1); - let _ = self.notify.send(TrashEvent::Delete(identifiers, tx)); - let _ = rx.recv().await; + let repeated_trash = TrashTableSql::read_all(&*(self.database.db_connection()?))?; + let trash_identifiers: TrashIdentifiers = repeated_trash.items.clone().into(); + let _ = self.delete_with_identifiers(trash_identifiers.clone()).await?; notify_trash_num_changed(RepeatedTrash { items: vec![] }); let _ = self.delete_all_trash_on_server().await?; Ok(()) } - fn delete_all_trash_on_local(&self) -> WorkspaceResult { - let conn = self.database.db_connection()?; - conn.immediate_transaction::<_, WorkspaceError, _>(|| { - let repeated_trash = TrashTableSql::read_all(&*conn)?; - let _ = TrashTableSql::delete_all(&*conn)?; - Ok(repeated_trash) - }) + #[tracing::instrument(level = "debug", skip(self), err)] + pub async fn delete(&self, trash_identifiers: TrashIdentifiers) -> WorkspaceResult<()> { + let _ = self.delete_with_identifiers(trash_identifiers.clone()).await?; + notify_trash_num_changed(TrashTableSql::read_all(&*(self.database.db_connection()?))?); + let _ = self.delete_trash_on_server(trash_identifiers)?; + + Ok(()) } - #[tracing::instrument(level = "debug", skip(self) err)] - pub async fn delete(&self, trash_identifiers: TrashIdentifiers) -> WorkspaceResult<()> { + #[tracing::instrument(level = "debug", skip(self), fields(delete_trash_ids), err)] + pub async fn delete_with_identifiers(&self, trash_identifiers: TrashIdentifiers) -> WorkspaceResult<()> { let (tx, mut rx) = mpsc::channel::>(1); + tracing::Span::current().record("delete_trash_ids", &format!("{}", trash_identifiers).as_str()); let _ = self.notify.send(TrashEvent::Delete(trash_identifiers.clone(), tx)); - let _ = rx.recv().await; + + match rx.recv().await { + None => {}, + Some(result) => match result { + Ok(_) => {}, + Err(e) => log::error!("{}", e), + }, + } let conn = self.database.db_connection()?; conn.immediate_transaction::<_, WorkspaceError, _>(|| { @@ -114,10 +128,6 @@ impl TrashCan { } Ok(()) })?; - - notify_trash_num_changed(TrashTableSql::read_all(&conn)?); - let _ = self.delete_trash_on_server(trash_identifiers)?; - Ok(()) } @@ -212,6 +222,7 @@ impl TrashCan { spawn(async move { match server.read_trash(&token).await { Ok(repeated_trash) => { + log::debug!("Remote trash count: {}", repeated_trash.items.len()); match pool.get() { Ok(conn) => { let result = conn.immediate_transaction::<_, WorkspaceError, _>(|| { diff --git a/rust-lib/flowy-workspace/src/services/view_controller.rs b/rust-lib/flowy-workspace/src/services/view_controller.rs index 6a6271a75b..d5c9fb326b 100644 --- a/rust-lib/flowy-workspace/src/services/view_controller.rs +++ b/rust-lib/flowy-workspace/src/services/view_controller.rs @@ -302,8 +302,9 @@ async fn handle_trash_event( } } -#[tracing::instrument(skip(repeated_view), err)] +#[tracing::instrument(skip(repeated_view), fields(view_count), err)] fn notify_view_num_changed(belong_to_id: &str, repeated_view: RepeatedView) -> WorkspaceResult<()> { + tracing::Span::current().record("view_count", &format!("{}", repeated_view.len()).as_str()); send_dart_notification(&belong_to_id, WorkspaceNotification::AppViewsChanged) .payload(repeated_view) .send();