mirror of
https://github.com/AppFlowy-IO/AppFlowy.git
synced 2024-08-30 18:12:39 +00:00
feat: search mvp (#5064)
* feat: implement folder indexer * feat: sqlite search views using fts5 * feat: add view indexing to user manager * feat: implement folder indexer * feat: add sqlite search documents * feat: add document indexing to user manager * feat: add document indexing to folder indexer * chore: update collab rev * feat: search frontend integration * refactor: search index * test: add event test * chore: fix ci * feat: initial command palette overlay impl (#4619) * chore: test search engine * chore: initial structure * chore: replace old search request * chore: enable log for lib-dispatch * chore: move search manager to core * feat: move traits and responsibility to search crate * feat: move search to search crate * feat: replace sqlite with tantivy * feat: deserialize tantivy documents * chore: fixes after rebase * chore: clean code * feat: fetch and sort results * fix: code review + cleaning * feat: support custom icons * feat: support view layout icons * feat: rename bloc and fix indexing * fix: prettify dialog * feat: score results * chore: update collab rev * feat: add recent view history to command palette * test: add integration_tests * fix: clippy changes * fix: focus traversal in cmd palette * fix: remove file after merging main * chore: code review and panic-safe * feat: index all views if index does not exist * chore: improve logic with conditional * chore: add is_empty check * chore: abstract logic from folder manager init * chore: update collab rev * chore: code review * chore: fixes after merge + update lock file * chore: revert cargo lock * fix: set icon type when removing icon * fix: code review + dependency inversion * fix: remove icon fix for not persisting icon type * test: simple tests manipulating views * test: create 100 views * fix: tauri build * chore: create 1000 views * chore: create util methods * chore: test * chore: test * chore: remove logs * chore: fix build.rs * chore: export models * chore: enable clear cache on Rust-CI * fix: navigate to newly created views * fix: force disable setting workspace listener on rebuilds * fix: remove late final * fix: missing returns * fix: localization and minor fixes * test: add index assert to large test * fix: missing section param after merging main * chore: try fix unzip file error * chore: lower the test * feat: show hint when result is in trash * feat: one index_writer per index * fix: minor changes after merge * fix: make create_log_filter public after merge * chore: fix test * chore: fix test * chore: flutter analyze * chore: flutter analyze * chore: fix tauri build --------- Co-authored-by: nathan <nathan@appflowy.io> Co-authored-by: Lucas.Xu <lucas.xu@appflowy.io> Co-authored-by: Nathan.fooo <86001920+appflowy@users.noreply.github.com>
This commit is contained in:
@ -8,24 +8,29 @@ edition = "2021"
|
||||
[dependencies]
|
||||
collab = { version = "0.1.0" }
|
||||
collab-folder = { version = "0.1.0" }
|
||||
collab-document = { version = "0.1.0" }
|
||||
collab-entity = { version = "0.1.0" }
|
||||
collab-plugins = { version = "0.1.0" }
|
||||
collab-integrate = { workspace = true }
|
||||
flowy-folder-pub = { workspace = true }
|
||||
flowy-search-pub = { workspace = true }
|
||||
|
||||
flowy-derive.workspace = true
|
||||
flowy-notification = { workspace = true }
|
||||
flowy-notification = { workspace = true }
|
||||
parking_lot.workspace = true
|
||||
unicode-segmentation = "1.10"
|
||||
tracing.workspace = true
|
||||
flowy-error = { path = "../flowy-error", features = ["impl_from_dispatch_error", "impl_from_collab_folder"]}
|
||||
flowy-error = { path = "../flowy-error", features = [
|
||||
"impl_from_dispatch_error",
|
||||
"impl_from_collab_folder",
|
||||
] }
|
||||
lib-dispatch = { workspace = true }
|
||||
bytes.workspace = true
|
||||
lib-infra = { workspace = true }
|
||||
tokio = { workspace = true, features = ["sync"] }
|
||||
nanoid = "0.4.0"
|
||||
lazy_static = "1.4.0"
|
||||
chrono = { workspace = true, default-features = false, features = ["clock"] }
|
||||
chrono = { workspace = true, default-features = false, features = ["clock"] }
|
||||
strum_macros = "0.21"
|
||||
protobuf.workspace = true
|
||||
uuid.workspace = true
|
||||
|
@ -28,6 +28,7 @@ use collab_integrate::{CollabKVDB, CollabPersistenceConfig};
|
||||
use flowy_error::{ErrorCode, FlowyError, FlowyResult};
|
||||
use flowy_folder_pub::cloud::{gen_view_id, FolderCloudService};
|
||||
use flowy_folder_pub::folder_builder::ParentChildViews;
|
||||
use flowy_search_pub::entities::FolderIndexManager;
|
||||
use lib_infra::conditional_send_sync_trait;
|
||||
use parking_lot::{Mutex, RwLock};
|
||||
use std::fmt::{Display, Formatter};
|
||||
@ -44,12 +45,16 @@ conditional_send_sync_trait! {
|
||||
}
|
||||
|
||||
pub struct FolderManager {
|
||||
/// workspace_id represents as the id of the Folder.
|
||||
pub(crate) workspace_id: RwLock<Option<String>>,
|
||||
|
||||
/// MutexFolder is the folder that is used to store the data.
|
||||
pub(crate) mutex_folder: Arc<MutexFolder>,
|
||||
pub(crate) collab_builder: Arc<AppFlowyCollabBuilder>,
|
||||
pub(crate) user: Arc<dyn FolderUser>,
|
||||
pub(crate) operation_handlers: FolderOperationHandlers,
|
||||
pub cloud_service: Arc<dyn FolderCloudService>,
|
||||
pub(crate) folder_indexer: Arc<dyn FolderIndexManager>,
|
||||
}
|
||||
|
||||
impl FolderManager {
|
||||
@ -58,6 +63,7 @@ impl FolderManager {
|
||||
collab_builder: Arc<AppFlowyCollabBuilder>,
|
||||
operation_handlers: FolderOperationHandlers,
|
||||
cloud_service: Arc<dyn FolderCloudService>,
|
||||
folder_indexer: Arc<dyn FolderIndexManager>,
|
||||
) -> FlowyResult<Self> {
|
||||
let mutex_folder = Arc::new(MutexFolder::default());
|
||||
let manager = Self {
|
||||
@ -67,6 +73,7 @@ impl FolderManager {
|
||||
operation_handlers,
|
||||
cloud_service,
|
||||
workspace_id: Default::default(),
|
||||
folder_indexer,
|
||||
};
|
||||
|
||||
Ok(manager)
|
||||
@ -134,7 +141,7 @@ impl FolderManager {
|
||||
if let Some(workspace_id) = workspace_id {
|
||||
self.get_workspace_public_views(&workspace_id).await
|
||||
} else {
|
||||
tracing::warn!("Can't get current workspace views");
|
||||
tracing::warn!("Can't get the workspace id from the folder. Return empty list.");
|
||||
Ok(vec![])
|
||||
}
|
||||
}
|
||||
@ -463,6 +470,13 @@ impl FolderManager {
|
||||
},
|
||||
);
|
||||
|
||||
if let Ok(workspace_id) = self.get_current_workspace_id().await {
|
||||
let folder = &self.mutex_folder.lock();
|
||||
if let Some(folder) = folder.as_ref() {
|
||||
notify_did_update_workspace(&workspace_id, folder);
|
||||
}
|
||||
}
|
||||
|
||||
Ok(view)
|
||||
}
|
||||
|
||||
@ -1301,6 +1315,8 @@ pub(crate) fn get_workspace_private_view_pbs(_workspace_id: &str, folder: &Folde
|
||||
.collect()
|
||||
}
|
||||
|
||||
/// The MutexFolder is a wrapper of the [Folder] that is used to share the folder between different
|
||||
/// threads.
|
||||
#[derive(Clone, Default)]
|
||||
pub struct MutexFolder(Arc<Mutex<Option<Folder>>>);
|
||||
impl Deref for MutexFolder {
|
||||
|
@ -1,6 +1,8 @@
|
||||
use collab_entity::CollabType;
|
||||
|
||||
use collab_folder::{Folder, FolderNotify, UserId};
|
||||
use tokio::task::spawn_blocking;
|
||||
use tracing::{event, Level};
|
||||
|
||||
use collab_integrate::CollabKVDB;
|
||||
|
||||
@ -8,7 +10,6 @@ use flowy_error::{FlowyError, FlowyResult};
|
||||
|
||||
use collab::core::collab::DocStateSource;
|
||||
use std::sync::{Arc, Weak};
|
||||
use tracing::{event, Level};
|
||||
|
||||
use crate::manager::{FolderInitDataSource, FolderManager};
|
||||
use crate::manager_observer::{
|
||||
@ -129,6 +130,22 @@ impl FolderManager {
|
||||
};
|
||||
|
||||
let folder_state_rx = folder.subscribe_sync_state();
|
||||
let index_content_rx = folder.subscribe_index_content();
|
||||
self
|
||||
.folder_indexer
|
||||
.set_index_content_receiver(index_content_rx);
|
||||
|
||||
// Index all views in the folder if needed
|
||||
if !self.folder_indexer.is_indexed() {
|
||||
let views = folder.get_all_views_recursively();
|
||||
let folder_indexer = self.folder_indexer.clone();
|
||||
|
||||
// We spawn a blocking task to index all views in the folder
|
||||
spawn_blocking(move || {
|
||||
folder_indexer.index_all_views(views);
|
||||
});
|
||||
}
|
||||
|
||||
*self.mutex_folder.lock() = Some(folder);
|
||||
|
||||
let weak_mutex_folder = Arc::downgrade(&self.mutex_folder);
|
||||
|
Reference in New Issue
Block a user