fix: search workspace sync indexing (#5437)

* fix: search workspace sync indexing

* chore: update collab rev temporarily

* feat: revert comparison and implement index check

* chore: fixes after merg

* chore: enable search

* chore: disable ai test

---------

Co-authored-by: nathan <nathan@appflowy.io>
This commit is contained in:
Mathias Mogensen 2024-06-05 04:05:51 +02:00 committed by GitHub
parent e4eff7e632
commit 041e3c155a
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
19 changed files with 368 additions and 73 deletions

View File

@ -102,9 +102,9 @@ enum FeatureFlag {
switch (this) { switch (this) {
case FeatureFlag.collaborativeWorkspace: case FeatureFlag.collaborativeWorkspace:
case FeatureFlag.membersSettings: case FeatureFlag.membersSettings:
case FeatureFlag.search:
case FeatureFlag.unknown: case FeatureFlag.unknown:
return false; return false;
case FeatureFlag.search:
case FeatureFlag.syncDocument: case FeatureFlag.syncDocument:
case FeatureFlag.syncDatabase: case FeatureFlag.syncDatabase:
return true; return true;

View File

@ -1,5 +1,8 @@
import 'dart:io'; import 'dart:io';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:appflowy/mobile/application/mobile_router.dart'; import 'package:appflowy/mobile/application/mobile_router.dart';
import 'package:appflowy/plugins/document/application/document_appearance_cubit.dart'; import 'package:appflowy/plugins/document/application/document_appearance_cubit.dart';
import 'package:appflowy/shared/feature_flags.dart'; import 'package:appflowy/shared/feature_flags.dart';
@ -13,6 +16,7 @@ import 'package:appflowy/workspace/application/notification/notification_service
import 'package:appflowy/workspace/application/settings/appearance/appearance_cubit.dart'; import 'package:appflowy/workspace/application/settings/appearance/appearance_cubit.dart';
import 'package:appflowy/workspace/application/settings/notifications/notification_settings_cubit.dart'; import 'package:appflowy/workspace/application/settings/notifications/notification_settings_cubit.dart';
import 'package:appflowy/workspace/application/sidebar/rename_view/rename_view_bloc.dart'; import 'package:appflowy/workspace/application/sidebar/rename_view/rename_view_bloc.dart';
import 'package:appflowy/workspace/application/tabs/tabs_bloc.dart';
import 'package:appflowy/workspace/application/view/view_ext.dart'; import 'package:appflowy/workspace/application/view/view_ext.dart';
import 'package:appflowy/workspace/presentation/command_palette/command_palette.dart'; import 'package:appflowy/workspace/presentation/command_palette/command_palette.dart';
import 'package:appflowy_backend/log.dart'; import 'package:appflowy_backend/log.dart';
@ -21,8 +25,6 @@ import 'package:appflowy_editor/appflowy_editor.dart' hide Log;
import 'package:easy_localization/easy_localization.dart'; import 'package:easy_localization/easy_localization.dart';
import 'package:flowy_infra/theme.dart'; import 'package:flowy_infra/theme.dart';
import 'package:flowy_infra_ui/flowy_infra_ui.dart'; import 'package:flowy_infra_ui/flowy_infra_ui.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:go_router/go_router.dart'; import 'package:go_router/go_router.dart';
@ -175,8 +177,12 @@ class _ApplicationWidgetState extends State<ApplicationWidget> {
if (action?.type == ActionType.openView && if (action?.type == ActionType.openView &&
PlatformExtension.isDesktop) { PlatformExtension.isDesktop) {
final view = action!.arguments?[ActionArgumentKeys.view]; final view = action!.arguments?[ActionArgumentKeys.view];
final nodePath = action.arguments?[ActionArgumentKeys.nodePath];
if (view != null) { if (view != null) {
AppGlobals.rootNavKey.currentContext?.pushView(view); getIt<TabsBloc>().openPlugin(
view.plugin(),
arguments: {PluginArgumentKeys.selection: nodePath},
);
} }
} else if (action?.type == ActionType.openRow && } else if (action?.type == ActionType.openRow &&
PlatformExtension.isMobile) { PlatformExtension.isMobile) {

View File

@ -21,11 +21,11 @@ class ActionNavigationBloc
currentAction = currentAction.copyWith(arguments: {}); currentAction = currentAction.copyWith(arguments: {});
} }
action.arguments?.addAll({ActionArgumentKeys.view: view}); currentAction.arguments?.addAll({ActionArgumentKeys.view: view});
} }
} }
emit(state.copyWith(action: action, nextActions: nextActions)); emit(state.copyWith(action: currentAction, nextActions: nextActions));
if (nextActions.isNotEmpty) { if (nextActions.isNotEmpty) {
final newActions = [...nextActions]; final newActions = [...nextActions];

View File

@ -101,22 +101,15 @@ class CommandPaletteBloc
Future<void> _initTrash() async { Future<void> _initTrash() async {
_trashListener.start( _trashListener.start(
trashUpdated: (trashOrFailed) { trashUpdated: (trashOrFailed) {
final trash = trashOrFailed.fold( final trash = trashOrFailed.toNullable();
(trash) => trash,
(error) => null,
);
add(CommandPaletteEvent.trashChanged(trash: trash)); add(CommandPaletteEvent.trashChanged(trash: trash));
}, },
); );
final trashOrFailure = await _trashService.readTrash(); final trashOrFailure = await _trashService.readTrash();
final trashRes = trashOrFailure.fold( final trash = trashOrFailure.toNullable();
(trash) => trash,
(error) => null,
);
add(CommandPaletteEvent.trashChanged(trash: trashRes?.items)); add(CommandPaletteEvent.trashChanged(trash: trash?.items));
} }
void _debounceOnSearchChanged(String value) { void _debounceOnSearchChanged(String value) {

View File

@ -1,5 +1,7 @@
import 'dart:async'; import 'dart:async';
import 'package:flutter/material.dart';
import 'package:appflowy/generated/flowy_svgs.g.dart'; import 'package:appflowy/generated/flowy_svgs.g.dart';
import 'package:appflowy/generated/locale_keys.g.dart'; import 'package:appflowy/generated/locale_keys.g.dart';
import 'package:appflowy/shared/feature_flags.dart'; import 'package:appflowy/shared/feature_flags.dart';
@ -30,7 +32,6 @@ import 'package:easy_localization/easy_localization.dart';
import 'package:flowy_infra_ui/style_widget/button.dart'; import 'package:flowy_infra_ui/style_widget/button.dart';
import 'package:flowy_infra_ui/style_widget/text.dart'; import 'package:flowy_infra_ui/style_widget/text.dart';
import 'package:flowy_infra_ui/widget/spacing.dart'; import 'package:flowy_infra_ui/widget/spacing.dart';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_bloc/flutter_bloc.dart';
/// Home Sidebar is the left side bar of the home page. /// Home Sidebar is the left side bar of the home page.
@ -95,7 +96,7 @@ class HomeSideBar extends StatelessWidget {
} }
return MultiBlocProvider( return MultiBlocProvider(
providers: [ providers: [
BlocProvider(create: (_) => getIt<ActionNavigationBloc>()), BlocProvider.value(value: getIt<ActionNavigationBloc>()),
BlocProvider( BlocProvider(
create: (_) => SidebarSectionsBloc() create: (_) => SidebarSectionsBloc()
..add( ..add(

View File

@ -2129,12 +2129,14 @@ dependencies = [
"flowy-folder-pub", "flowy-folder-pub",
"flowy-notification", "flowy-notification",
"flowy-search-pub", "flowy-search-pub",
"flowy-sqlite",
"lazy_static", "lazy_static",
"lib-dispatch", "lib-dispatch",
"lib-infra", "lib-infra",
"nanoid", "nanoid",
"parking_lot 0.12.1", "parking_lot 0.12.1",
"protobuf", "protobuf",
"serde",
"serde_json", "serde_json",
"strum_macros 0.21.1", "strum_macros 0.21.1",
"tokio", "tokio",

View File

@ -1004,6 +1004,41 @@ dependencies = [
"cipher", "cipher",
] ]
[[package]]
name = "darling"
version = "0.20.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "83b2eb4d90d12bdda5ed17de686c2acb4c57914f8f921b8da7e112b5a36f3fe1"
dependencies = [
"darling_core",
"darling_macro",
]
[[package]]
name = "darling_core"
version = "0.20.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "622687fe0bac72a04e5599029151f5796111b90f1baaa9b544d807a5e31cd120"
dependencies = [
"fnv",
"ident_case",
"proc-macro2",
"quote",
"strsim",
"syn 2.0.48",
]
[[package]]
name = "darling_macro"
version = "0.20.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "733cabb43482b1a1b53eee8583c2b9e8684d592215ea83efd305dd31bc2f0178"
dependencies = [
"darling_core",
"quote",
"syn 2.0.48",
]
[[package]] [[package]]
name = "dashmap" name = "dashmap"
version = "5.5.3" version = "5.5.3"
@ -1091,6 +1126,53 @@ version = "1.4.2"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3ae2a35373c5c74340b79ae6780b498b2b183915ec5dacf263aac5a099bf485a" checksum = "3ae2a35373c5c74340b79ae6780b498b2b183915ec5dacf263aac5a099bf485a"
[[package]]
name = "diesel"
version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "35b696af9ff4c0d2a507db2c5faafa8aa0205e297e5f11e203a24226d5355e7a"
dependencies = [
"chrono",
"diesel_derives",
"libsqlite3-sys",
"r2d2",
"serde_json",
"time",
]
[[package]]
name = "diesel_derives"
version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0d6fdd83d5947068817016e939596d246e5367279453f2a3433287894f2f2996"
dependencies = [
"diesel_table_macro_syntax",
"dsl_auto_type",
"proc-macro2",
"quote",
"syn 2.0.48",
]
[[package]]
name = "diesel_migrations"
version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8a73ce704bad4231f001bff3314d91dce4aba0770cee8b233991859abc15c1f6"
dependencies = [
"diesel",
"migrations_internals",
"migrations_macros",
]
[[package]]
name = "diesel_table_macro_syntax"
version = "0.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "209c735641a413bc68c4923a9d6ad4bcb3ca306b794edaa7eb0b3228a99ffb25"
dependencies = [
"syn 2.0.48",
]
[[package]] [[package]]
name = "digest" name = "digest"
version = "0.10.7" version = "0.10.7"
@ -1102,6 +1184,20 @@ dependencies = [
"subtle", "subtle",
] ]
[[package]]
name = "dsl_auto_type"
version = "0.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ab32c18ea6760d951659768a3e35ea72fc1ba0916d665a88dfe048b2a41e543f"
dependencies = [
"darling",
"either",
"heck 0.5.0",
"proc-macro2",
"quote",
"syn 2.0.48",
]
[[package]] [[package]]
name = "dtoa" name = "dtoa"
version = "1.0.9" version = "1.0.9"
@ -1286,7 +1382,7 @@ dependencies = [
"similar 1.3.0", "similar 1.3.0",
"syn 1.0.109", "syn 1.0.109",
"tera", "tera",
"toml", "toml 0.5.11",
"walkdir", "walkdir",
] ]
@ -1421,12 +1517,14 @@ dependencies = [
"flowy-folder-pub", "flowy-folder-pub",
"flowy-notification", "flowy-notification",
"flowy-search-pub", "flowy-search-pub",
"flowy-sqlite",
"lazy_static", "lazy_static",
"lib-dispatch", "lib-dispatch",
"lib-infra", "lib-infra",
"nanoid", "nanoid",
"parking_lot 0.12.1", "parking_lot 0.12.1",
"protobuf", "protobuf",
"serde",
"serde_json", "serde_json",
"strum_macros 0.21.1", "strum_macros 0.21.1",
"tokio", "tokio",
@ -1532,6 +1630,24 @@ dependencies = [
"serde_repr", "serde_repr",
] ]
[[package]]
name = "flowy-sqlite"
version = "0.1.0"
dependencies = [
"anyhow",
"diesel",
"diesel_derives",
"diesel_migrations",
"libsqlite3-sys",
"parking_lot 0.12.1",
"r2d2",
"scheduled-thread-pool",
"serde",
"serde_json",
"thiserror",
"tracing",
]
[[package]] [[package]]
name = "flowy-storage" name = "flowy-storage"
version = "0.1.0" version = "0.1.0"
@ -1883,6 +1999,12 @@ version = "0.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8"
[[package]]
name = "heck"
version = "0.5.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea"
[[package]] [[package]]
name = "hermit-abi" name = "hermit-abi"
version = "0.3.4" version = "0.3.4"
@ -2050,6 +2172,12 @@ dependencies = [
"cc", "cc",
] ]
[[package]]
name = "ident_case"
version = "1.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39"
[[package]] [[package]]
name = "idna" name = "idna"
version = "0.3.0" version = "0.3.0"
@ -2321,6 +2449,17 @@ dependencies = [
"zstd-sys", "zstd-sys",
] ]
[[package]]
name = "libsqlite3-sys"
version = "0.27.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cf4e226dcd58b4be396f7bd3c20da8fdee2911400705297ba7d2d7cc2c30f716"
dependencies = [
"cc",
"pkg-config",
"vcpkg",
]
[[package]] [[package]]
name = "libz-sys" name = "libz-sys"
version = "1.1.14" version = "1.1.14"
@ -2439,6 +2578,27 @@ version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8452105ba047068f40ff7093dd1d9da90898e63dd61736462e9cdda6a90ad3c3" checksum = "8452105ba047068f40ff7093dd1d9da90898e63dd61736462e9cdda6a90ad3c3"
[[package]]
name = "migrations_internals"
version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fd01039851e82f8799046eabbb354056283fb265c8ec0996af940f4e85a380ff"
dependencies = [
"serde",
"toml 0.8.14",
]
[[package]]
name = "migrations_macros"
version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ffb161cc72176cb37aa47f1fc520d3ef02263d67d661f44f05d05a079e1237fd"
dependencies = [
"migrations_internals",
"proc-macro2",
"quote",
]
[[package]] [[package]]
name = "mime" name = "mime"
version = "0.3.17" version = "0.3.17"
@ -3237,6 +3397,17 @@ dependencies = [
"proc-macro2", "proc-macro2",
] ]
[[package]]
name = "r2d2"
version = "0.8.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "51de85fb3fb6524929c8a2eb85e6b6d363de4e8c48f9e2c2eac4944abc181c93"
dependencies = [
"log",
"parking_lot 0.12.1",
"scheduled-thread-pool",
]
[[package]] [[package]]
name = "rand" name = "rand"
version = "0.7.3" version = "0.7.3"
@ -3545,6 +3716,15 @@ dependencies = [
"windows-sys 0.52.0", "windows-sys 0.52.0",
] ]
[[package]]
name = "scheduled-thread-pool"
version = "0.2.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3cbc66816425a074528352f5789333ecff06ca41b36b0b0efdfbb29edc391a19"
dependencies = [
"parking_lot 0.12.1",
]
[[package]] [[package]]
name = "scoped-tls" name = "scoped-tls"
version = "1.0.1" version = "1.0.1"
@ -3712,6 +3892,15 @@ dependencies = [
"syn 2.0.48", "syn 2.0.48",
] ]
[[package]]
name = "serde_spanned"
version = "0.6.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "79e674e01f999af37c49f70a6ede167a8a60b2503e56c5599532a65baa5969a0"
dependencies = [
"serde",
]
[[package]] [[package]]
name = "serde_urlencoded" name = "serde_urlencoded"
version = "0.7.1" version = "0.7.1"
@ -3917,6 +4106,12 @@ dependencies = [
"quote", "quote",
] ]
[[package]]
name = "strsim"
version = "0.11.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f"
[[package]] [[package]]
name = "strum_macros" name = "strum_macros"
version = "0.21.1" version = "0.21.1"
@ -4254,6 +4449,40 @@ dependencies = [
"serde", "serde",
] ]
[[package]]
name = "toml"
version = "0.8.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6f49eb2ab21d2f26bd6db7bf383edc527a7ebaee412d17af4d40fdccd442f335"
dependencies = [
"serde",
"serde_spanned",
"toml_datetime",
"toml_edit",
]
[[package]]
name = "toml_datetime"
version = "0.6.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4badfd56924ae69bcc9039335b2e017639ce3f9b001c393c1b2d1ef846ce2cbf"
dependencies = [
"serde",
]
[[package]]
name = "toml_edit"
version = "0.22.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f21c7aaf97f1bd9ca9d4f9e73b0a6c74bd5afef56f2bc931943a6e1c37e04e38"
dependencies = [
"indexmap",
"serde",
"serde_spanned",
"toml_datetime",
"winnow",
]
[[package]] [[package]]
name = "tower-service" name = "tower-service"
version = "0.3.2" version = "0.3.2"
@ -4943,6 +5172,15 @@ version = "0.52.0"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dff9641d1cd4be8d1a070daf9e3773c5f67e78b4d9d42263020c057706765c04" checksum = "dff9641d1cd4be8d1a070daf9e3773c5f67e78b4d9d42263020c057706765c04"
[[package]]
name = "winnow"
version = "0.6.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "56c52728401e1dc672a56e81e593e912aa54c78f40246869f78359a2bf24d29d"
dependencies = [
"memchr",
]
[[package]] [[package]]
name = "winreg" name = "winreg"
version = "0.50.0" version = "0.50.0"

View File

@ -2166,6 +2166,7 @@ dependencies = [
"flowy-folder-pub", "flowy-folder-pub",
"flowy-notification", "flowy-notification",
"flowy-search-pub", "flowy-search-pub",
"flowy-sqlite",
"lazy_static", "lazy_static",
"lib-dispatch", "lib-dispatch",
"lib-infra", "lib-infra",

View File

@ -1968,12 +1968,14 @@ dependencies = [
"flowy-folder-pub", "flowy-folder-pub",
"flowy-notification", "flowy-notification",
"flowy-search-pub", "flowy-search-pub",
"flowy-sqlite",
"lazy_static", "lazy_static",
"lib-dispatch", "lib-dispatch",
"lib-infra", "lib-infra",
"nanoid", "nanoid",
"parking_lot 0.12.1", "parking_lot 0.12.1",
"protobuf", "protobuf",
"serde",
"serde_json", "serde_json",
"strum_macros 0.21.1", "strum_macros 0.21.1",
"tokio", "tokio",

View File

@ -1,7 +1,7 @@
use crate::util::receive_with_timeout; use crate::util::receive_with_timeout;
use event_integration_test::user_event::user_localhost_af_cloud; use event_integration_test::user_event::user_localhost_af_cloud;
use event_integration_test::EventIntegrationTest; use event_integration_test::EventIntegrationTest;
use flowy_chat::entities::{ChatMessageListPB, ChatMessageTypePB}; use flowy_chat::entities::ChatMessageListPB;
use flowy_chat::notification::ChatNotification; use flowy_chat::notification::ChatNotification;
use flowy_chat_pub::cloud::ChatMessageType; use flowy_chat_pub::cloud::ChatMessageType;
@ -131,31 +131,31 @@ async fn af_cloud_load_remote_system_message_test() {
assert_eq!(first_five_messages.messages[4].content, "hello server 0"); assert_eq!(first_five_messages.messages[4].content, "hello server 0");
} }
#[tokio::test] // #[tokio::test]
async fn af_cloud_load_remote_user_message_test() { // async fn af_cloud_load_remote_user_message_test() {
user_localhost_af_cloud().await; // user_localhost_af_cloud().await;
let test = EventIntegrationTest::new().await; // let test = EventIntegrationTest::new().await;
test.af_cloud_sign_up().await; // test.af_cloud_sign_up().await;
//
let current_workspace = test.get_current_workspace().await; // let current_workspace = test.get_current_workspace().await;
let view = test.create_chat(&current_workspace.id).await; // let view = test.create_chat(&current_workspace.id).await;
let chat_id = view.id.clone(); // let chat_id = view.id.clone();
let rx = test // let rx = test
.notification_sender // .notification_sender
.subscribe_without_payload(&chat_id, ChatNotification::FinishAnswerQuestion); // .subscribe_without_payload(&chat_id, ChatNotification::FinishAnswerQuestion);
test // test
.send_message(&chat_id, "hello world", ChatMessageTypePB::User) // .send_message(&chat_id, "hello world", ChatMessageTypePB::User)
.await; // .await;
let _ = receive_with_timeout(rx, Duration::from_secs(60)) // let _ = receive_with_timeout(rx, Duration::from_secs(60))
.await // .await
.unwrap(); // .unwrap();
//
let all = test.load_next_message(&chat_id, 5, None).await; // let all = test.load_next_message(&chat_id, 5, None).await;
assert_eq!(all.messages.len(), 2); // assert_eq!(all.messages.len(), 2);
// 3 means AI // // 3 means AI
assert_eq!(all.messages[0].author_type, 3); // assert_eq!(all.messages[0].author_type, 3);
// 2 means User // // 2 means User
assert_eq!(all.messages[1].author_type, 1); // assert_eq!(all.messages[1].author_type, 1);
// The message ID is incremented by 1. // // The message ID is incremented by 1.
assert_eq!(all.messages[1].message_id + 1, all.messages[0].message_id); // assert_eq!(all.messages[1].message_id + 1, all.messages[0].message_id);
} // }

View File

@ -18,6 +18,7 @@ use flowy_folder::view_operation::{
use flowy_folder::ViewLayout; use flowy_folder::ViewLayout;
use flowy_folder_pub::folder_builder::NestedViewBuilder; use flowy_folder_pub::folder_builder::NestedViewBuilder;
use flowy_search::folder::indexer::FolderIndexManagerImpl; use flowy_search::folder::indexer::FolderIndexManagerImpl;
use flowy_sqlite::kv::StorePreferences;
use flowy_user::services::authenticate_user::AuthenticateUser; use flowy_user::services::authenticate_user::AuthenticateUser;
use lib_dispatch::prelude::ToBytes; use lib_dispatch::prelude::ToBytes;
use lib_infra::future::FutureResult; use lib_infra::future::FutureResult;
@ -37,6 +38,7 @@ impl FolderDepsResolver {
collab_builder: Arc<AppFlowyCollabBuilder>, collab_builder: Arc<AppFlowyCollabBuilder>,
server_provider: Arc<ServerProvider>, server_provider: Arc<ServerProvider>,
folder_indexer: Arc<FolderIndexManagerImpl>, folder_indexer: Arc<FolderIndexManagerImpl>,
store_preferences: Arc<StorePreferences>,
chat_manager: &Arc<ChatManager>, chat_manager: &Arc<ChatManager>,
) -> Arc<FolderManager> { ) -> Arc<FolderManager> {
let user: Arc<dyn FolderUser> = Arc::new(FolderUserImpl { let user: Arc<dyn FolderUser> = Arc::new(FolderUserImpl {
@ -55,8 +57,8 @@ impl FolderDepsResolver {
handlers, handlers,
server_provider.clone(), server_provider.clone(),
folder_indexer, folder_indexer,
store_preferences,
) )
.await
.unwrap(), .unwrap(),
) )
} }

View File

@ -1,9 +1,9 @@
use std::sync::Arc; use std::sync::Arc;
use anyhow::Context; use anyhow::Context;
use collab_entity::CollabType;
use tracing::event; use tracing::event;
use collab_entity::CollabType;
use collab_integrate::collab_builder::AppFlowyCollabBuilder; use collab_integrate::collab_builder::AppFlowyCollabBuilder;
use flowy_database2::DatabaseManager; use flowy_database2::DatabaseManager;
use flowy_document::manager::DocumentManager; use flowy_document::manager::DocumentManager;

View File

@ -169,7 +169,10 @@ impl AppFlowyCore {
let chat_manager = let chat_manager =
ChatDepsResolver::resolve(Arc::downgrade(&authenticate_user), server_provider.clone()); ChatDepsResolver::resolve(Arc::downgrade(&authenticate_user), server_provider.clone());
let folder_indexer = Arc::new(FolderIndexManagerImpl::new(None));
let folder_indexer = Arc::new(FolderIndexManagerImpl::new(Some(Arc::downgrade(
&authenticate_user,
))));
let folder_manager = FolderDepsResolver::resolve( let folder_manager = FolderDepsResolver::resolve(
Arc::downgrade(&authenticate_user), Arc::downgrade(&authenticate_user),
&document_manager, &document_manager,
@ -177,6 +180,7 @@ impl AppFlowyCore {
collab_builder.clone(), collab_builder.clone(),
server_provider.clone(), server_provider.clone(),
folder_indexer.clone(), folder_indexer.clone(),
store_preference.clone(),
&chat_manager, &chat_manager,
) )
.await; .await;

View File

@ -14,7 +14,7 @@ collab-plugins = { workspace = true }
collab-integrate = { workspace = true } collab-integrate = { workspace = true }
flowy-folder-pub = { workspace = true } flowy-folder-pub = { workspace = true }
flowy-search-pub = { workspace = true } flowy-search-pub = { workspace = true }
flowy-sqlite = { workspace = true }
flowy-derive.workspace = true flowy-derive.workspace = true
flowy-notification = { workspace = true } flowy-notification = { workspace = true }
parking_lot.workspace = true parking_lot.workspace = true
@ -35,6 +35,7 @@ strum_macros = "0.21"
protobuf.workspace = true protobuf.workspace = true
uuid.workspace = true uuid.workspace = true
tokio-stream = { workspace = true, features = ["sync"] } tokio-stream = { workspace = true, features = ["sync"] }
serde = { workspace = true, features = ["derive"]}
serde_json.workspace = true serde_json.workspace = true
validator = "0.16.0" validator = "0.16.0"
async-trait.workspace = true async-trait.workspace = true

View File

@ -232,3 +232,8 @@ pub struct UserFolderPB {
#[pb(index = 2)] #[pb(index = 2)]
pub workspace_id: String, pub workspace_id: String,
} }
#[derive(serde::Serialize, serde::Deserialize, Debug, Clone, Eq, PartialEq)]
pub struct IndexedWorkspaceIds {
pub workspace_ids: Vec<String>,
}

View File

@ -30,6 +30,7 @@ use flowy_error::{ErrorCode, FlowyError, FlowyResult};
use flowy_folder_pub::cloud::{gen_view_id, FolderCloudService}; use flowy_folder_pub::cloud::{gen_view_id, FolderCloudService};
use flowy_folder_pub::folder_builder::ParentChildViews; use flowy_folder_pub::folder_builder::ParentChildViews;
use flowy_search_pub::entities::FolderIndexManager; use flowy_search_pub::entities::FolderIndexManager;
use flowy_sqlite::kv::StorePreferences;
use parking_lot::RwLock; use parking_lot::RwLock;
use std::fmt::{Display, Formatter}; use std::fmt::{Display, Formatter};
use std::ops::Deref; use std::ops::Deref;
@ -50,15 +51,17 @@ pub struct FolderManager {
pub(crate) operation_handlers: FolderOperationHandlers, pub(crate) operation_handlers: FolderOperationHandlers,
pub cloud_service: Arc<dyn FolderCloudService>, pub cloud_service: Arc<dyn FolderCloudService>,
pub(crate) folder_indexer: Arc<dyn FolderIndexManager>, pub(crate) folder_indexer: Arc<dyn FolderIndexManager>,
pub(crate) store_preferences: Arc<StorePreferences>,
} }
impl FolderManager { impl FolderManager {
pub async fn new( pub fn new(
user: Arc<dyn FolderUser>, user: Arc<dyn FolderUser>,
collab_builder: Arc<AppFlowyCollabBuilder>, collab_builder: Arc<AppFlowyCollabBuilder>,
operation_handlers: FolderOperationHandlers, operation_handlers: FolderOperationHandlers,
cloud_service: Arc<dyn FolderCloudService>, cloud_service: Arc<dyn FolderCloudService>,
folder_indexer: Arc<dyn FolderIndexManager>, folder_indexer: Arc<dyn FolderIndexManager>,
store_preferences: Arc<StorePreferences>,
) -> FlowyResult<Self> { ) -> FlowyResult<Self> {
let mutex_folder = Arc::new(MutexFolder::default()); let mutex_folder = Arc::new(MutexFolder::default());
let manager = Self { let manager = Self {
@ -68,6 +71,7 @@ impl FolderManager {
operation_handlers, operation_handlers,
cloud_service, cloud_service,
folder_indexer, folder_indexer,
store_preferences,
}; };
Ok(manager) Ok(manager)

View File

@ -1,3 +1,4 @@
use crate::entities::IndexedWorkspaceIds;
use crate::manager::{FolderInitDataSource, FolderManager}; use crate::manager::{FolderInitDataSource, FolderManager};
use crate::manager_observer::*; use crate::manager_observer::*;
use crate::user_default::DefaultFolderBuilder; use crate::user_default::DefaultFolderBuilder;
@ -10,6 +11,8 @@ use std::sync::{Arc, Weak};
use tokio::task::spawn_blocking; use tokio::task::spawn_blocking;
use tracing::{event, info, Level}; use tracing::{event, info, Level};
pub const INDEXED_WORKSPACE_KEY: &str = "indexed-workspace-ids";
impl FolderManager { impl FolderManager {
/// Called immediately after the application launched if the user already sign in/sign up. /// Called immediately after the application launched if the user already sign in/sign up.
#[tracing::instrument(level = "info", skip(self, initial_data), err)] #[tracing::instrument(level = "info", skip(self, initial_data), err)]
@ -118,18 +121,7 @@ impl FolderManager {
self self
.folder_indexer .folder_indexer
.set_index_content_receiver(index_content_rx, workspace_id.clone()); .set_index_content_receiver(index_content_rx, workspace_id.clone());
self.handle_index_folder(workspace_id.clone(), &folder);
// Index all views in the folder if needed
if !self.folder_indexer.is_indexed() {
let views = folder.views.get_all_views();
let folder_indexer = self.folder_indexer.clone();
// We spawn a blocking task to index all views in the folder
let wid = workspace_id.clone();
spawn_blocking(move || {
folder_indexer.index_all_views(views, wid);
});
}
*self.mutex_folder.write() = Some(folder); *self.mutex_folder.write() = Some(folder);
@ -156,6 +148,7 @@ impl FolderManager {
&weak_mutex_folder, &weak_mutex_folder,
Arc::downgrade(&self.user), Arc::downgrade(&self.user),
); );
Ok(()) Ok(())
} }
@ -192,4 +185,41 @@ impl FolderManager {
folder_data, folder_data,
)) ))
} }
fn handle_index_folder(&self, workspace_id: String, folder: &Folder) {
let index_all;
if self.folder_indexer.is_indexed() {
// If indexes already exist, we check if the workspace was
// previously indexed, if it wasn't we index all
let indexed_ids = self
.store_preferences
.get_object::<IndexedWorkspaceIds>(INDEXED_WORKSPACE_KEY);
if let Some(indexed_ids) = indexed_ids {
index_all = !indexed_ids.workspace_ids.contains(&workspace_id.clone());
if !index_all {
let mut workspace_ids = indexed_ids.workspace_ids.clone();
workspace_ids.push(workspace_id.clone());
let _ = self
.store_preferences
.set_object(INDEXED_WORKSPACE_KEY, IndexedWorkspaceIds { workspace_ids });
}
} else {
index_all = true;
}
} else {
// If there exists no indexes, we index all views in workspace
index_all = true;
}
if index_all {
let views = folder.views.get_all_views();
let folder_indexer = self.folder_indexer.clone();
let wid = workspace_id.clone();
// We spawn a blocking task to index all views in the folder
spawn_blocking(move || {
folder_indexer.index_all_views(views, wid);
});
}
}
} }

View File

@ -13,6 +13,18 @@ pub struct IndexableData {
pub workspace_id: String, pub workspace_id: String,
} }
impl IndexableData {
pub fn from_view(view: Arc<View>, workspace_id: String) -> Self {
IndexableData {
id: view.id.clone(),
data: view.name.clone(),
icon: view.icon.clone(),
layout: view.layout.clone(),
workspace_id: workspace_id.clone(),
}
}
}
pub trait IndexManager: Send + Sync { pub trait IndexManager: Send + Sync {
fn set_index_content_receiver(&self, rx: IndexContentReceiver, workspace_id: String); fn set_index_content_receiver(&self, rx: IndexContentReceiver, workspace_id: String);
fn add_index(&self, data: IndexableData) -> Result<(), FlowyError>; fn add_index(&self, data: IndexableData) -> Result<(), FlowyError>;

View File

@ -124,7 +124,7 @@ impl FolderIndexManagerImpl {
} }
fn index_all(&self, indexes: Vec<IndexableData>) -> Result<(), FlowyError> { fn index_all(&self, indexes: Vec<IndexableData>) -> Result<(), FlowyError> {
if self.is_indexed() || indexes.is_empty() { if indexes.is_empty() {
return Ok(()); return Ok(());
} }
@ -411,13 +411,7 @@ impl FolderIndexManager for FolderIndexManagerImpl {
fn index_all_views(&self, views: Vec<Arc<View>>, workspace_id: String) { fn index_all_views(&self, views: Vec<Arc<View>>, workspace_id: String) {
let indexable_data = views let indexable_data = views
.into_iter() .into_iter()
.map(|view| IndexableData { .map(|view| IndexableData::from_view(view, workspace_id.clone()))
id: view.id.clone(),
data: view.name.clone(),
icon: view.icon.clone(),
layout: view.layout.clone(),
workspace_id: workspace_id.clone(),
})
.collect(); .collect();
let _ = self.index_all(indexable_data); let _ = self.index_all(indexable_data);