diff --git a/frontend/appflowy_flutter/assets/translations/en.json b/frontend/appflowy_flutter/assets/translations/en.json
index 8518f7a4e2..f4da7002e9 100644
--- a/frontend/appflowy_flutter/assets/translations/en.json
+++ b/frontend/appflowy_flutter/assets/translations/en.json
@@ -231,7 +231,7 @@
       "addFilter": "Add Filter",
       "deleteFilter": "Delete filter",
       "filterBy": "Filter by...",
-      "typeAValue": "Type a value...", 
+      "typeAValue": "Type a value...",
       "layout": "Layout",
       "databaseLayout": "Layout"
     },
@@ -414,7 +414,13 @@
       },
       "optionAction": {
         "click": "Click",
-        "toOpenMenu": " to open menu"
+        "toOpenMenu": " to open menu",
+        "delete": "Delete",
+        "duplicate": "Duplicate",
+        "turnInto": "Turn into",
+        "moveUp": "Move up",
+        "moveDown": "Move down",
+        "color": "Color"
       }
     }
   },
diff --git a/frontend/appflowy_flutter/integration_test/document_test.dart b/frontend/appflowy_flutter/integration_test/document_test.dart
new file mode 100644
index 0000000000..93e753a9a1
--- /dev/null
+++ b/frontend/appflowy_flutter/integration_test/document_test.dart
@@ -0,0 +1,90 @@
+import 'package:appflowy/generated/locale_keys.g.dart';
+import 'package:appflowy_editor/appflowy_editor.dart';
+import 'package:easy_localization/easy_localization.dart';
+import 'package:flutter_test/flutter_test.dart';
+import 'package:integration_test/integration_test.dart';
+
+import 'util/util.dart';
+
+void main() {
+  IntegrationTestWidgetsFlutterBinding.ensureInitialized();
+
+  group('document', () {
+    const location = 'appflowy';
+
+    setUp(() async {
+      await TestFolder.cleanTestLocation(location);
+      await TestFolder.setTestLocation(location);
+    });
+
+    tearDown(() async {
+      await TestFolder.cleanTestLocation(location);
+    });
+
+    tearDownAll(() async {
+      await TestFolder.cleanTestLocation(null);
+    });
+
+    testWidgets('create a new document when launching app in first time',
+        (tester) async {
+      await tester.initializeAppFlowy();
+
+      await tester.tapGoButton();
+
+      // create a new document
+      await tester.tapAddButton();
+      await tester.tapCreateDocumentButton();
+      await tester.pumpAndSettle();
+
+      // expect to see a new document
+      tester.expectToSeePageName(
+        LocaleKeys.menuAppHeader_defaultNewPageName.tr(),
+      );
+      // and with one paragraph block
+      expect(find.byType(TextBlockComponentWidget), findsOneWidget);
+    });
+
+    testWidgets('delete the readme page and restore it', (tester) async {
+      await tester.initializeAppFlowy();
+
+      await tester.tapGoButton();
+
+      // delete the readme page
+      await tester.hoverOnPageName(readme);
+      await tester.tapDeletePageButton();
+
+      // the banner should show up and the readme page should be gone
+      tester.expectToSeeDocumentBanner();
+      tester.expectNotToSeePageName(readme);
+
+      // restore the readme page
+      await tester.tapRestoreButton();
+
+      // the banner should be gone and the readme page should be back
+      tester.expectNotToSeeDocumentBanner();
+      tester.expectToSeePageName(readme);
+    });
+
+    testWidgets('delete the readme page and delete it permanently',
+        (tester) async {
+      await tester.initializeAppFlowy();
+
+      await tester.tapGoButton();
+
+      // delete the readme page
+      await tester.hoverOnPageName(readme);
+      await tester.tapDeletePageButton();
+
+      // the banner should show up and the readme page should be gone
+      tester.expectToSeeDocumentBanner();
+      tester.expectNotToSeePageName(readme);
+
+      // delete the page permanently
+      await tester.tapDeletePermanentlyButton();
+
+      // the banner should be gone and the readme page should be gone
+      tester.expectNotToSeeDocumentBanner();
+      tester.expectNotToSeePageName(readme);
+    });
+  });
+}
diff --git a/frontend/appflowy_flutter/integration_test/runner.dart b/frontend/appflowy_flutter/integration_test/runner.dart
index b848ce1fc3..41a78d4eef 100644
--- a/frontend/appflowy_flutter/integration_test/runner.dart
+++ b/frontend/appflowy_flutter/integration_test/runner.dart
@@ -4,6 +4,7 @@ import 'board_test.dart' as board_test;
 import 'switch_folder_test.dart' as switch_folder_test;
 import 'empty_document_test.dart' as empty_document_test;
 import 'open_ai_smart_menu_test.dart' as smart_menu_test;
+import 'document_test.dart' as document_test;
 
 /// The main task runner for all integration tests in AppFlowy.
 ///
@@ -18,4 +19,5 @@ void main() {
   board_test.main();
   empty_document_test.main();
   smart_menu_test.main();
+  document_test.main();
 }
diff --git a/frontend/appflowy_flutter/integration_test/switch_folder_test.dart b/frontend/appflowy_flutter/integration_test/switch_folder_test.dart
index 6dcd41b081..40862b5c0d 100644
--- a/frontend/appflowy_flutter/integration_test/switch_folder_test.dart
+++ b/frontend/appflowy_flutter/integration_test/switch_folder_test.dart
@@ -51,7 +51,7 @@ void main() {
       // Click create button again
       await tester.tapCreateButton();
 
-      await tester.expectToSeeWelcomePage();
+      tester.expectToSeeWelcomePage();
 
       await TestFolder.cleanTestLocation(folderName);
     });
@@ -69,7 +69,7 @@ void main() {
       await tester.tapOpenFolderButton();
 
       await tester.wait(1000);
-      await tester.expectToSeeWelcomePage();
+      tester.expectToSeeWelcomePage();
 
       await TestFolder.cleanTestLocation(folderName);
     });
@@ -84,7 +84,7 @@ void main() {
       await tester.initializeAppFlowy();
 
       await tester.tapGoButton();
-      await tester.expectToSeeWelcomePage();
+      tester.expectToSeeWelcomePage();
 
       // switch to user B
       {
@@ -99,7 +99,7 @@ void main() {
         await mockGetDirectoryPath(userB);
         await tester.tapCustomLocationButton();
         await tester.pumpAndSettle();
-        await tester.expectToSeeWelcomePage();
+        tester.expectToSeeWelcomePage();
       }
 
       // switch to the userA
@@ -116,7 +116,7 @@ void main() {
         await tester.tapCustomLocationButton();
 
         await tester.pumpAndSettle();
-        await tester.expectToSeeWelcomePage();
+        tester.expectToSeeWelcomePage();
         expect(find.textContaining(userA), findsOneWidget);
       }
 
@@ -131,7 +131,7 @@ void main() {
         await tester.tapCustomLocationButton();
 
         await tester.pumpAndSettle();
-        await tester.expectToSeeWelcomePage();
+        tester.expectToSeeWelcomePage();
         expect(find.textContaining(userB), findsOneWidget);
       }
 
@@ -145,7 +145,7 @@ void main() {
       await tester.tapGoButton();
 
       // home and readme document
-      await tester.expectToSeeWelcomePage();
+      tester.expectToSeeWelcomePage();
 
       // open settings and restore the location
       await tester.openSettings();
diff --git a/frontend/appflowy_flutter/integration_test/util/base.dart b/frontend/appflowy_flutter/integration_test/util/base.dart
index ec7dd07fa0..be426a61c3 100644
--- a/frontend/appflowy_flutter/integration_test/util/base.dart
+++ b/frontend/appflowy_flutter/integration_test/util/base.dart
@@ -91,7 +91,7 @@ extension AppFlowyTestBase on WidgetTester {
     String tr, {
     int milliseconds = 500,
   }) async {
-    final button = find.text(tr);
+    final button = find.text(tr, findRichText: true);
     await tapButton(
       button,
       milliseconds: milliseconds,
diff --git a/frontend/appflowy_flutter/integration_test/util/launch.dart b/frontend/appflowy_flutter/integration_test/util/launch.dart
index 5f2cc6ba09..7d2f9cdb33 100644
--- a/frontend/appflowy_flutter/integration_test/util/launch.dart
+++ b/frontend/appflowy_flutter/integration_test/util/launch.dart
@@ -1,23 +1,100 @@
+import 'dart:ui';
+
 import 'package:appflowy/generated/locale_keys.g.dart';
+import 'package:appflowy/plugins/document/presentation/banner.dart';
+import 'package:appflowy/user/presentation/skip_log_in_screen.dart';
 import 'package:appflowy/workspace/presentation/home/home_stack.dart';
+import 'package:appflowy/workspace/presentation/home/menu/app/header/add_button.dart';
+import 'package:appflowy/workspace/presentation/home/menu/app/section/item.dart';
 import 'package:easy_localization/easy_localization.dart';
 import 'package:flutter_test/flutter_test.dart';
 
 import 'base.dart';
 
+const String readme = 'Read me';
+
 extension AppFlowyLaunch on WidgetTester {
   Future<void> tapGoButton() async {
-    await tapButtonWithName(LocaleKeys.letsGoButtonText.tr());
-    return;
+    final goButton = find.byType(GoButton);
+    await tapButton(goButton);
   }
 
   Future<void> tapCreateButton() async {
     await tapButtonWithName(LocaleKeys.settings_files_create.tr());
-    return;
   }
 
-  Future<void> expectToSeeWelcomePage() async {
+  void expectToSeeWelcomePage() {
     expect(find.byType(HomeStack), findsOneWidget);
     expect(find.textContaining('Read me'), findsNWidgets(2));
   }
+
+  Future<void> tapAddButton() async {
+    final addButton = find.byType(AddButton);
+    await tapButton(addButton);
+  }
+
+  Future<void> tapCreateDocumentButton() async {
+    await tapButtonWithName(LocaleKeys.document_menuName.tr());
+  }
+
+  Finder findPageName(String name) {
+    return find.byWidgetPredicate(
+      (widget) => widget is ViewSectionItem && widget.view.name == name,
+    );
+  }
+
+  void expectToSeePageName(String name) {
+    final pageName = findPageName(name);
+    expect(pageName, findsOneWidget);
+  }
+
+  void expectNotToSeePageName(String name) {
+    final pageName = findPageName(name);
+    expect(pageName, findsNothing);
+  }
+
+  Future<void> hoverOnPageName(String name) async {
+    final pageName = find.byWidgetPredicate(
+      (widget) => widget is ViewSectionItem && widget.view.name == name,
+    );
+
+    final gesture = await createGesture(kind: PointerDeviceKind.mouse);
+    await gesture.addPointer(location: Offset.zero);
+    addTearDown(gesture.removePointer);
+    await pump();
+    await gesture.moveTo(getCenter(pageName));
+    await pumpAndSettle();
+  }
+
+  Future<void> tapPageOptionButton() async {
+    final optionButton = find.byType(ViewDisclosureButton);
+    await tapButton(optionButton);
+  }
+
+  Future<void> tapDeletePageButton() async {
+    await tapPageOptionButton();
+    await tapButtonWithName(ViewDisclosureAction.delete.name);
+  }
+
+  void expectToSeeDocumentBanner() {
+    expect(find.byType(DocumentBanner), findsOneWidget);
+  }
+
+  void expectNotToSeeDocumentBanner() {
+    expect(find.byType(DocumentBanner), findsNothing);
+  }
+
+  Future<void> tapRestoreButton() async {
+    final restoreButton = find.textContaining(
+      LocaleKeys.deletePagePrompt_restore.tr(),
+    );
+    await tapButton(restoreButton);
+  }
+
+  Future<void> tapDeletePermanentlyButton() async {
+    final restoreButton = find.textContaining(
+      LocaleKeys.deletePagePrompt_deletePermanent.tr(),
+    );
+    await tapButton(restoreButton);
+  }
 }
diff --git a/frontend/appflowy_flutter/lib/plugins/document/application/doc_bloc.dart b/frontend/appflowy_flutter/lib/plugins/document/application/doc_bloc.dart
index 7518548309..8f2b77b591 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/application/doc_bloc.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/application/doc_bloc.dart
@@ -66,7 +66,7 @@ class DocumentBloc extends Bloc<DocumentEvent, DocumentState> {
         await _subscribe(state);
         emit(state);
       },
-      deleted: (Deleted value) async {
+      moveToTrash: (MoveToTrash value) async {
         emit(state.copyWith(isDeleted: true));
       },
       restore: (Restore value) async {
@@ -74,11 +74,13 @@ class DocumentBloc extends Bloc<DocumentEvent, DocumentState> {
       },
       deletePermanently: (DeletePermanently value) async {
         final result = await _trashService.deleteViews([view.id]);
-        emit(state.copyWith(forceClose: result.swap().isLeft()));
+        final forceClose = result.fold((l) => true, (r) => false);
+        emit(state.copyWith(forceClose: forceClose));
       },
       restorePage: (RestorePage value) async {
         final result = await _trashService.putback(view.id);
-        emit(state.copyWith(isDeleted: result.swap().isRight()));
+        final isDeleted = result.fold((l) => false, (r) => true);
+        emit(state.copyWith(isDeleted: isDeleted));
       },
     );
   }
@@ -98,8 +100,12 @@ class DocumentBloc extends Bloc<DocumentEvent, DocumentState> {
   /// subscribe to the view(document page) change
   void _onViewChanged() {
     _viewListener.start(
-      onViewDeleted: (r) =>
-          r.swap().map((r) => add(const DocumentEvent.deleted())),
+      onViewMoveToTrash: (r) {
+        r.swap().map((r) => add(const DocumentEvent.moveToTrash()));
+      },
+      onViewDeleted: (r) {
+        r.swap().map((r) => add(const DocumentEvent.moveToTrash()));
+      },
       onViewRestored: (r) =>
           r.swap().map((r) => add(const DocumentEvent.restore())),
     );
@@ -161,7 +167,7 @@ class DocumentBloc extends Bloc<DocumentEvent, DocumentState> {
 @freezed
 class DocumentEvent with _$DocumentEvent {
   const factory DocumentEvent.initial() = Initial;
-  const factory DocumentEvent.deleted() = Deleted;
+  const factory DocumentEvent.moveToTrash() = MoveToTrash;
   const factory DocumentEvent.restore() = Restore;
   const factory DocumentEvent.restorePage() = RestorePage;
   const factory DocumentEvent.deletePermanently() = DeletePermanently;
diff --git a/frontend/appflowy_flutter/lib/plugins/document/application/document_data_pb_extension.dart b/frontend/appflowy_flutter/lib/plugins/document/application/document_data_pb_extension.dart
index 67767939da..36b852b11b 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/application/document_data_pb_extension.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/application/document_data_pb_extension.dart
@@ -88,35 +88,22 @@ extension DocumentDataPBFromTo on DocumentDataPB {
   }
 }
 
-class _BackendKeys {
-  const _BackendKeys._();
-
-  static const String text = 'text';
-}
-
 extension BlockToNode on BlockPB {
   Node toNode({
     Iterable<Node>? children,
   }) {
     return Node(
       id: id,
-      type: _typeAdapter(ty),
+      type: ty,
       attributes: _dataAdapter(ty, data),
       children: children ?? [],
     );
   }
 
-  String _typeAdapter(String ty) {
-    final adapter = {
-      _BackendKeys.text: ParagraphBlockKeys.type,
-    };
-    return adapter[ty] ?? ty;
-  }
-
   Attributes _dataAdapter(String ty, String data) {
     final map = Attributes.from(jsonDecode(data));
     final adapter = {
-      'text': (Attributes map) => map
+      ParagraphBlockKeys.type: (Attributes map) => map
         ..putIfAbsent(
           'delta',
           () => Delta().toJson(),
@@ -134,7 +121,7 @@ extension NodeToBlock on Node {
     assert(id.isNotEmpty);
     final block = BlockPB.create()
       ..id = id
-      ..ty = _typeAdapter(type)
+      ..ty = type
       ..data = _dataAdapter(type, attributes);
     if (childrenId != null && childrenId.isNotEmpty) {
       block.childrenId = childrenId;
@@ -145,13 +132,6 @@ extension NodeToBlock on Node {
     return block;
   }
 
-  String _typeAdapter(String type) {
-    final adapter = {
-      'paragraph': 'text',
-    };
-    return adapter[type] ?? type;
-  }
-
   String _dataAdapter(String type, Attributes attributes) {
     return jsonEncode(attributes);
   }
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_page.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_page.dart
index f2e8f10afa..85f432cfcb 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_page.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_page.dart
@@ -112,6 +112,7 @@ class _AppFlowyEditorPageState extends State<AppFlowyEditorPage> {
       child: ConstrainedBox(
         constraints: const BoxConstraints(
           maxWidth: double.infinity,
+          maxHeight: double.infinity,
         ),
         child: FloatingToolbar(
           style: styleCustomizer.floatingToolbarStyleBuilder(),
@@ -225,7 +226,7 @@ class _AppFlowyEditorPageState extends State<AppFlowyEditorPage> {
       ];
 
       final colorAction = [
-        // OptionAction.divider,
+        OptionAction.divider,
         OptionAction.color,
       ];
 
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/actions/option_action.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/actions/option_action.dart
index 403b7cd709..2e15776b59 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/actions/option_action.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/actions/option_action.dart
@@ -1,9 +1,11 @@
+import 'package:appflowy/generated/locale_keys.g.dart';
 import 'package:appflowy/plugins/database_view/grid/presentation/widgets/header/type_option/select_option_editor.dart';
 import 'package:appflowy/plugins/database_view/widgets/row/cells/select_option_cell/extension.dart';
 import 'package:appflowy/workspace/presentation/widgets/pop_up_action.dart';
 import 'package:appflowy_backend/protobuf/flowy-database2/protobuf.dart';
 import 'package:appflowy_editor/appflowy_editor.dart' hide FlowySvg;
 import 'package:appflowy_popover/appflowy_popover.dart';
+import 'package:easy_localization/easy_localization.dart';
 import 'package:flowy_infra/image.dart';
 import 'package:flutter/material.dart';
 import 'package:styled_widget/styled_widget.dart';
@@ -45,7 +47,7 @@ class ColorOptionAction extends PopoverActionCell {
 
   @override
   String get name {
-    return 'Color'; // todo: l10n
+    return LocaleKeys.toolbar_color.tr();
   }
 
   @override
@@ -55,7 +57,6 @@ class ColorOptionAction extends PopoverActionCell {
             if (selection == null) {
               return const SizedBox.shrink();
             }
-            // TODO: should we support multiple selection?
             final node = editorState.getNodeAtPath(selection.start.path);
             if (node == null) {
               return const SizedBox.shrink();
@@ -70,6 +71,8 @@ class ColorOptionAction extends PopoverActionCell {
             return SelectOptionColorList(
               selectedColor: selectedColor,
               onSelectedColor: (color) {
+                controller.close();
+
                 final nodes = editorState.getNodesInSelection(selection);
                 final transaction = editorState.transaction;
                 for (final node in nodes) {
@@ -79,8 +82,6 @@ class ColorOptionAction extends PopoverActionCell {
                   });
                 }
                 editorState.apply(transaction);
-
-                controller.close();
               },
             );
           };
@@ -141,22 +142,22 @@ class OptionActionWrapper extends ActionCell {
     switch (inner) {
       // TODO: l10n
       case OptionAction.delete:
-        description = 'Delete';
+        description = LocaleKeys.document_plugins_optionAction_delete.tr();
         break;
       case OptionAction.duplicate:
-        description = 'Duplicate';
+        description = LocaleKeys.document_plugins_optionAction_duplicate.tr();
         break;
       case OptionAction.turnInto:
-        description = 'Turn into';
+        description = LocaleKeys.document_plugins_optionAction_turnInto.tr();
         break;
       case OptionAction.moveUp:
-        description = 'Move up';
+        description = LocaleKeys.document_plugins_optionAction_moveUp.tr();
         break;
       case OptionAction.moveDown:
-        description = 'Move down';
+        description = LocaleKeys.document_plugins_optionAction_moveDown.tr();
         break;
       case OptionAction.color:
-        description = 'Color';
+        description = LocaleKeys.document_plugins_optionAction_color.tr();
         break;
       case OptionAction.divider:
         throw UnimplementedError();
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/built_in_page_widget.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/built_in_page_widget.dart
index 0d23510182..8fef6b674a 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/built_in_page_widget.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/built_in_page_widget.dart
@@ -69,6 +69,10 @@ class _BuiltInPageWidgetState extends State<BuiltInPageWidget> {
           return _build(context, page);
         }
         if (snapshot.connectionState == ConnectionState.done) {
+          WidgetsBinding.instance.addPostFrameCallback((timeStamp) {
+            // just delete the page if it is not found
+            _deletePage();
+          });
           return const Center(
             child: FlowyText('Cannot load the page'),
           );
@@ -174,6 +178,12 @@ class _BuiltInPageWidgetState extends State<BuiltInPageWidget> {
       ),
     );
   }
+
+  Future<void> _deletePage() async {
+    final transaction = widget.editorState.transaction;
+    transaction.deleteNode(widget.node);
+    widget.editorState.apply(transaction);
+  }
 }
 
 enum _ActionType {
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/link_to_page_widget.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/link_to_page_widget.dart
index 29168fb3d8..55d633260d 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/link_to_page_widget.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/base/link_to_page_widget.dart
@@ -23,7 +23,8 @@ void showLinkToPageMenu(
   final top = alignment == Alignment.bottomLeft ? offset.dy : null;
   final bottom = alignment == Alignment.topLeft ? offset.dy : null;
 
-  final linkToPageMenuEntry = FullScreenOverlayEntry(
+  late OverlayEntry linkToPageMenuEntry;
+  linkToPageMenuEntry = FullScreenOverlayEntry(
     top: top,
     bottom: bottom,
     left: offset.dx,
@@ -35,6 +36,7 @@ void showLinkToPageMenu(
         hintText: pageType.toHintText(),
         onSelected: (appPB, viewPB) {
           editorState.insertPage(appPB, viewPB);
+          linkToPageMenuEntry.remove();
         },
       ),
     ),
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/change_cover_popover.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/change_cover_popover.dart
index 947a8de00e..1b8ba14620 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/change_cover_popover.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/change_cover_popover.dart
@@ -465,17 +465,11 @@ class _CoverColorPickerState extends State<CoverColorPicker> {
           },
           platform: TargetPlatform.windows,
         ),
-        child: ListView.builder(
-          controller: scrollController,
-          shrinkWrap: true,
-          itemCount: widget.backgroundColorOptions.length,
-          scrollDirection: Axis.horizontal,
-          itemBuilder: (context, index) {
-            return _buildColorItems(
-              widget.backgroundColorOptions,
-              widget.selectedBackgroundColorHex,
-            );
-          },
+        child: SingleChildScrollView(
+          child: _buildColorItems(
+            widget.backgroundColorOptions,
+            widget.selectedBackgroundColorHex,
+          ),
         ),
       ),
     );
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/cover_node_widget.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/cover_node_widget.dart
index 992d0b28ee..8962a0987f 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/cover_node_widget.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/cover/cover_node_widget.dart
@@ -303,10 +303,11 @@ class _CoverImageState extends State<_CoverImage> {
   CoverSelectionType get selectionType => CoverSelectionType.fromString(
         widget.node.attributes[CoverBlockKeys.selectionType],
       );
-  Color get color => Color(
-        int.tryParse(widget.node.attributes[CoverBlockKeys.selection]) ??
-            0xFFFFFFFF,
-      );
+  Color get color {
+    final hex = widget.node.attributes[CoverBlockKeys.selection] as String?;
+    return hex?.toColor() ?? Colors.white;
+  }
+
   bool get hasIcon =>
       widget.node.attributes[CoverBlockKeys.iconSelection] == null
           ? false
diff --git a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/divider/divider_character_shortcut_event.dart b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/divider/divider_character_shortcut_event.dart
index 3fcb6c47a9..d0987eccf1 100644
--- a/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/divider/divider_character_shortcut_event.dart
+++ b/frontend/appflowy_flutter/lib/plugins/document/presentation/editor_plugins/divider/divider_character_shortcut_event.dart
@@ -35,7 +35,7 @@ CharacterShortcutEventHandler _convertMinusesToDividerHandler =
     ..insertNode(path, dividerNode())
     ..insertNode(path, paragraphNode())
     ..deleteNode(node)
-    ..afterSelection = Selection.collapse(path.next, 0);
+    ..afterSelection = Selection.collapse(path, 0);
   editorState.apply(transaction);
   return true;
 };
@@ -61,7 +61,9 @@ SelectionMenuItem dividerMenuItem = SelectionMenuItem(
     }
     final insertedPath = delta.isEmpty ? path : path.next;
     final transaction = editorState.transaction
-      ..insertNode(insertedPath, dividerNode());
+      ..insertNode(insertedPath, dividerNode())
+      ..insertNode(insertedPath, paragraphNode())
+      ..afterSelection = Selection.collapse(insertedPath.next, 0);
     editorState.apply(transaction);
   },
 );
diff --git a/frontend/appflowy_flutter/lib/user/application/user_service.dart b/frontend/appflowy_flutter/lib/user/application/user_service.dart
index 60ec1e26f8..c14ccdd5c3 100644
--- a/frontend/appflowy_flutter/lib/user/application/user_service.dart
+++ b/frontend/appflowy_flutter/lib/user/application/user_service.dart
@@ -70,7 +70,7 @@ class UserBackendService {
   Future<Either<List<WorkspacePB>, FlowyError>> getWorkspaces() {
     final request = WorkspaceIdPB.create();
 
-    return FolderEventReadWorkspaces(request).send().then((result) {
+    return FolderEventReadAllWorkspaces(request).send().then((result) {
       return result.fold(
         (workspaces) => left(workspaces.items),
         (error) => right(error),
diff --git a/frontend/appflowy_flutter/lib/user/presentation/router.dart b/frontend/appflowy_flutter/lib/user/presentation/router.dart
index d0845d41d7..8546172b36 100644
--- a/frontend/appflowy_flutter/lib/user/presentation/router.dart
+++ b/frontend/appflowy_flutter/lib/user/presentation/router.dart
@@ -50,7 +50,7 @@ class AuthRouter {
     BuildContext context,
     UserProfilePB userProfile,
   ) async {
-    final result = await FolderEventReadCurrentWorkspace().send();
+    final result = await FolderEventGetCurrentWorkspace().send();
     result.fold(
       (workspaceSettingPB) => pushHomeScreenWithWorkSpace(
         context,
@@ -75,7 +75,7 @@ class SplashRoute {
       ),
     );
 
-    FolderEventReadCurrentWorkspace().send().then((result) {
+    FolderEventGetCurrentWorkspace().send().then((result) {
       result.fold(
         (workspaceSettingPB) =>
             pushHomeScreen(context, userProfile, workspaceSettingPB),
diff --git a/frontend/appflowy_flutter/lib/user/presentation/skip_log_in_screen.dart b/frontend/appflowy_flutter/lib/user/presentation/skip_log_in_screen.dart
index 7b37e7d226..bb04f39ec0 100644
--- a/frontend/appflowy_flutter/lib/user/presentation/skip_log_in_screen.dart
+++ b/frontend/appflowy_flutter/lib/user/presentation/skip_log_in_screen.dart
@@ -126,7 +126,7 @@ class _SkipLogInScreenState extends State<SkipLogInScreen> {
         Log.error(error);
       },
       (user) {
-        FolderEventReadCurrentWorkspace().send().then((result) {
+        FolderEventGetCurrentWorkspace().send().then((result) {
           _openCurrentWorkspace(context, user, result);
         });
       },
diff --git a/frontend/appflowy_flutter/lib/user/presentation/splash_screen.dart b/frontend/appflowy_flutter/lib/user/presentation/splash_screen.dart
index aefcada89d..3c59bab1ec 100644
--- a/frontend/appflowy_flutter/lib/user/presentation/splash_screen.dart
+++ b/frontend/appflowy_flutter/lib/user/presentation/splash_screen.dart
@@ -70,7 +70,7 @@ class SplashScreen extends StatelessWidget {
     Authenticated authenticated,
   ) async {
     final userProfile = authenticated.userProfile;
-    final result = await FolderEventReadCurrentWorkspace().send();
+    final result = await FolderEventGetCurrentWorkspace().send();
     result.fold(
       (workspaceSetting) {
         getIt<SplashRoute>().pushHomeScreen(
diff --git a/frontend/appflowy_flutter/lib/workspace/application/view/view_service.dart b/frontend/appflowy_flutter/lib/workspace/application/view/view_service.dart
index f8e0ae8962..1e8849673e 100644
--- a/frontend/appflowy_flutter/lib/workspace/application/view/view_service.dart
+++ b/frontend/appflowy_flutter/lib/workspace/application/view/view_service.dart
@@ -122,7 +122,7 @@ class ViewBackendService {
     ViewLayoutPB layoutType,
   ) async {
     final result = <(ViewPB, List<ViewPB>)>[];
-    return FolderEventReadCurrentWorkspace().send().then((value) async {
+    return FolderEventGetCurrentWorkspace().send().then((value) async {
       final workspaces = value.getLeftOrNull<WorkspaceSettingPB>();
       if (workspaces != null) {
         final views = workspaces.workspace.views;
diff --git a/frontend/appflowy_flutter/lib/workspace/application/workspace/workspace_service.dart b/frontend/appflowy_flutter/lib/workspace/application/workspace/workspace_service.dart
index 525302af34..47b45141f6 100644
--- a/frontend/appflowy_flutter/lib/workspace/application/workspace/workspace_service.dart
+++ b/frontend/appflowy_flutter/lib/workspace/application/workspace/workspace_service.dart
@@ -35,7 +35,7 @@ class WorkspaceService {
 
   Future<Either<WorkspacePB, FlowyError>> getWorkspace() {
     final payload = WorkspaceIdPB.create()..value = workspaceId;
-    return FolderEventReadWorkspaces(payload).send().then((result) {
+    return FolderEventReadAllWorkspaces(payload).send().then((result) {
       return result.fold(
         (workspaces) {
           assert(workspaces.items.length == 1);
diff --git a/frontend/appflowy_flutter/lib/workspace/presentation/settings/widgets/settings_file_exporter_widget.dart b/frontend/appflowy_flutter/lib/workspace/presentation/settings/widgets/settings_file_exporter_widget.dart
index da15ee74c8..46cda916e3 100644
--- a/frontend/appflowy_flutter/lib/workspace/presentation/settings/widgets/settings_file_exporter_widget.dart
+++ b/frontend/appflowy_flutter/lib/workspace/presentation/settings/widgets/settings_file_exporter_widget.dart
@@ -35,7 +35,7 @@ class _FileExporterWidgetState extends State<FileExporterWidget> {
   @override
   Widget build(BuildContext context) {
     return FutureBuilder<dartz.Either<WorkspaceSettingPB, FlowyError>>(
-      future: FolderEventReadCurrentWorkspace().send(),
+      future: FolderEventGetCurrentWorkspace().send(),
       builder: (context, snapshot) {
         if (snapshot.hasData &&
             snapshot.connectionState == ConnectionState.done) {
diff --git a/frontend/appflowy_flutter/lib/workspace/presentation/widgets/pop_up_action.dart b/frontend/appflowy_flutter/lib/workspace/presentation/widgets/pop_up_action.dart
index 761877f239..2d1d699a2d 100644
--- a/frontend/appflowy_flutter/lib/workspace/presentation/widgets/pop_up_action.dart
+++ b/frontend/appflowy_flutter/lib/workspace/presentation/widgets/pop_up_action.dart
@@ -179,7 +179,6 @@ class PopoverActionCellWidget<T extends PopoverAction> extends StatelessWidget {
     final rightIcon =
         actionCell.rightIcon(Theme.of(context).colorScheme.onSurface);
     return AppFlowyPopover(
-      // mutex: mutex,
       controller: popoverController,
       asBarrier: true,
       popupBuilder: (context) => actionCell.builder(
diff --git a/frontend/appflowy_flutter/test/bloc_test/home_test/app_bloc_test.dart b/frontend/appflowy_flutter/test/bloc_test/home_test/app_bloc_test.dart
index 878bf71d23..b99f532e25 100644
--- a/frontend/appflowy_flutter/test/bloc_test/home_test/app_bloc_test.dart
+++ b/frontend/appflowy_flutter/test/bloc_test/home_test/app_bloc_test.dart
@@ -127,7 +127,7 @@ void main() {
       ..add(const DocumentEvent.initial());
     await blocResponseFuture();
 
-    final workspaceSetting = await FolderEventReadCurrentWorkspace()
+    final workspaceSetting = await FolderEventGetCurrentWorkspace()
         .send()
         .then((result) => result.fold((l) => l, (r) => throw Exception()));
     workspaceSetting.latestView.id == document1.id;
@@ -148,7 +148,7 @@ void main() {
     final grid = bloc.state.latestCreatedView;
     assert(grid!.name == "grid 2");
 
-    var workspaceSetting = await FolderEventReadCurrentWorkspace()
+    var workspaceSetting = await FolderEventGetCurrentWorkspace()
         .send()
         .then((result) => result.fold((l) => l, (r) => throw Exception()));
     workspaceSetting.latestView.id == grid!.id;
@@ -159,7 +159,7 @@ void main() {
       ..add(const DocumentEvent.initial());
     await blocResponseFuture();
 
-    workspaceSetting = await FolderEventReadCurrentWorkspace()
+    workspaceSetting = await FolderEventGetCurrentWorkspace()
         .send()
         .then((result) => result.fold((l) => l, (r) => throw Exception()));
     workspaceSetting.latestView.id == document.id;
diff --git a/frontend/appflowy_flutter/test/bloc_test/home_test/home_bloc_test.dart b/frontend/appflowy_flutter/test/bloc_test/home_test/home_bloc_test.dart
index e072466de7..6360e6f9c3 100644
--- a/frontend/appflowy_flutter/test/bloc_test/home_test/home_bloc_test.dart
+++ b/frontend/appflowy_flutter/test/bloc_test/home_test/home_bloc_test.dart
@@ -15,7 +15,7 @@ void main() {
   });
 
   test('initi home screen', () async {
-    final workspaceSetting = await FolderEventReadCurrentWorkspace()
+    final workspaceSetting = await FolderEventGetCurrentWorkspace()
         .send()
         .then((result) => result.fold((l) => l, (r) => throw Exception()));
     await blocResponseFuture();
@@ -28,7 +28,7 @@ void main() {
   });
 
   test('open the document', () async {
-    final workspaceSetting = await FolderEventReadCurrentWorkspace()
+    final workspaceSetting = await FolderEventGetCurrentWorkspace()
         .send()
         .then((result) => result.fold((l) => l, (r) => throw Exception()));
     await blocResponseFuture();
diff --git a/frontend/appflowy_tauri/src-tauri/Cargo.lock b/frontend/appflowy_tauri/src-tauri/Cargo.lock
index 1becda17cb..3f9d86f3ec 100644
--- a/frontend/appflowy_tauri/src-tauri/Cargo.lock
+++ b/frontend/appflowy_tauri/src-tauri/Cargo.lock
@@ -99,7 +99,7 @@ checksum = "9c7d0618f0e0b7e8ff11427422b64564d5fb0be1940354bfe2e0529b18a9d9b8"
 [[package]]
 name = "appflowy-integrate"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "anyhow",
  "collab",
@@ -1024,7 +1024,7 @@ dependencies = [
 [[package]]
 name = "collab"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "anyhow",
  "bytes",
@@ -1042,7 +1042,7 @@ dependencies = [
 [[package]]
 name = "collab-client-ws"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "bytes",
  "collab-sync",
@@ -1060,7 +1060,7 @@ dependencies = [
 [[package]]
 name = "collab-database"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "anyhow",
  "async-trait",
@@ -1086,7 +1086,7 @@ dependencies = [
 [[package]]
 name = "collab-derive"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "proc-macro2",
  "quote",
@@ -1098,7 +1098,7 @@ dependencies = [
 [[package]]
 name = "collab-document"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "anyhow",
  "collab",
@@ -1115,7 +1115,7 @@ dependencies = [
 [[package]]
 name = "collab-folder"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "anyhow",
  "collab",
@@ -1134,7 +1134,7 @@ dependencies = [
 [[package]]
 name = "collab-persistence"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "bincode",
  "chrono",
@@ -1154,7 +1154,7 @@ dependencies = [
 [[package]]
 name = "collab-plugins"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "anyhow",
  "async-trait",
@@ -1184,7 +1184,7 @@ dependencies = [
 [[package]]
 name = "collab-sync"
 version = "0.1.0"
-source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=12e373#12e373f972d893d5f34b18794e77d3b49783ddcf"
+source = "git+https://github.com/AppFlowy-IO/AppFlowy-Collab?rev=13b178#13b17802de31e75255b4303914042bdbb04361b2"
 dependencies = [
  "bytes",
  "collab",
diff --git a/frontend/appflowy_tauri/src/appflowy_app/components/auth/auth.hooks.ts b/frontend/appflowy_tauri/src/appflowy_app/components/auth/auth.hooks.ts
index 6cb486e35b..1a8104084d 100644
--- a/frontend/appflowy_tauri/src/appflowy_app/components/auth/auth.hooks.ts
+++ b/frontend/appflowy_tauri/src/appflowy_app/components/auth/auth.hooks.ts
@@ -2,7 +2,7 @@ import { currentUserActions } from '../../stores/reducers/current-user/slice';
 import { useAppDispatch, useAppSelector } from '../../stores/store';
 import { UserProfilePB } from '../../../services/backend/events/flowy-user';
 import { AuthBackendService, UserBackendService } from '../../stores/effects/user/user_bd_svc';
-import { FolderEventReadCurrentWorkspace } from '../../../services/backend/events/flowy-folder2';
+import { FolderEventGetCurrentWorkspace } from '../../../services/backend/events/flowy-folder2';
 import { WorkspaceSettingPB } from '../../../services/backend/models/flowy-folder2/workspace';
 import { Log } from '../../utils/log';
 
@@ -90,7 +90,7 @@ export const useAuth = () => {
   }
 
   async function _openWorkspace() {
-    return FolderEventReadCurrentWorkspace();
+    return FolderEventGetCurrentWorkspace();
   }
 
   return { currentUser, checkUser, register, login, logout };
diff --git a/frontend/appflowy_tauri/src/appflowy_app/components/tests/DatabaseTestHelper.ts b/frontend/appflowy_tauri/src/appflowy_app/components/tests/DatabaseTestHelper.ts
index 51080322e6..8712fc8035 100644
--- a/frontend/appflowy_tauri/src/appflowy_app/components/tests/DatabaseTestHelper.ts
+++ b/frontend/appflowy_tauri/src/appflowy_app/components/tests/DatabaseTestHelper.ts
@@ -5,7 +5,7 @@ import {
   ViewPB,
   WorkspaceSettingPB,
 } from '../../../services/backend';
-import { FolderEventReadCurrentWorkspace } from '../../../services/backend/events/flowy-folder2';
+import { FolderEventGetCurrentWorkspace } from '../../../services/backend/events/flowy-folder2';
 import { AppBackendService } from '../../stores/effects/folder/app/app_bd_svc';
 import { DatabaseController } from '../../stores/effects/database/database_controller';
 import { RowInfo } from '../../stores/effects/database/row/row_cache';
@@ -31,7 +31,7 @@ import { Log } from '$app/utils/log';
 // Create a database view for specific layout type
 // Do not use it production code. Just for testing
 export async function createTestDatabaseView(layout: ViewLayoutPB): Promise<ViewPB> {
-  const workspaceSetting: WorkspaceSettingPB = await FolderEventReadCurrentWorkspace().then((result) => result.unwrap());
+  const workspaceSetting: WorkspaceSettingPB = await FolderEventGetCurrentWorkspace().then((result) => result.unwrap());
   const appService = new AppBackendService(workspaceSetting.workspace.id);
   return await appService.createView({ name: 'New Grid', layoutType: layout });
 }
diff --git a/frontend/appflowy_tauri/src/appflowy_app/components/tests/DocumentTestHelper.ts b/frontend/appflowy_tauri/src/appflowy_app/components/tests/DocumentTestHelper.ts
index 4656d06577..f43f22e5a2 100644
--- a/frontend/appflowy_tauri/src/appflowy_app/components/tests/DocumentTestHelper.ts
+++ b/frontend/appflowy_tauri/src/appflowy_app/components/tests/DocumentTestHelper.ts
@@ -1,9 +1,9 @@
 import { ViewLayoutPB, WorkspaceSettingPB } from '@/services/backend';
-import { FolderEventReadCurrentWorkspace } from '@/services/backend/events/flowy-folder2';
+import { FolderEventGetCurrentWorkspace } from '@/services/backend/events/flowy-folder2';
 import { AppBackendService } from '$app/stores/effects/folder/app/app_bd_svc';
 
 export async function createTestDocument() {
-  const workspaceSetting: WorkspaceSettingPB = await FolderEventReadCurrentWorkspace().then((result) => result.unwrap());
+  const workspaceSetting: WorkspaceSettingPB = await FolderEventGetCurrentWorkspace().then((result) => result.unwrap());
   const app = workspaceSetting.workspace.views[0];
   const appService = new AppBackendService(app.id);
   return await appService.createView({ name: 'New Document', layoutType: ViewLayoutPB.Document });
diff --git a/frontend/appflowy_tauri/src/appflowy_app/stores/effects/folder/workspace/workspace_bd_svc.ts b/frontend/appflowy_tauri/src/appflowy_app/stores/effects/folder/workspace/workspace_bd_svc.ts
index 13ee9b3091..be8b1cdde5 100644
--- a/frontend/appflowy_tauri/src/appflowy_app/stores/effects/folder/workspace/workspace_bd_svc.ts
+++ b/frontend/appflowy_tauri/src/appflowy_app/stores/effects/folder/workspace/workspace_bd_svc.ts
@@ -3,7 +3,7 @@ import {
   FolderEventCreateView,
   FolderEventMoveItem,
   FolderEventReadWorkspaceViews,
-  FolderEventReadWorkspaces,
+  FolderEventReadAllWorkspaces,
 } from '@/services/backend/events/flowy-folder2';
 import {
   CreateViewPayloadPB,
@@ -35,7 +35,7 @@ export class WorkspaceBackendService {
 
   getWorkspace = () => {
     const payload = WorkspaceIdPB.fromObject({ value: this.workspaceId });
-    return FolderEventReadWorkspaces(payload).then((result) => {
+    return FolderEventReadAllWorkspaces(payload).then((result) => {
       if (result.ok) {
         const workspaces = result.val.items;
         if (workspaces.length === 0) {
diff --git a/frontend/appflowy_tauri/src/appflowy_app/stores/effects/user/user_bd_svc.ts b/frontend/appflowy_tauri/src/appflowy_app/stores/effects/user/user_bd_svc.ts
index 2159dc761c..e2bcc32e6f 100644
--- a/frontend/appflowy_tauri/src/appflowy_app/stores/effects/user/user_bd_svc.ts
+++ b/frontend/appflowy_tauri/src/appflowy_app/stores/effects/user/user_bd_svc.ts
@@ -21,8 +21,8 @@ import {
 import {
   FolderEventCreateWorkspace,
   FolderEventOpenWorkspace,
-  FolderEventReadCurrentWorkspace,
-  FolderEventReadWorkspaces,
+  FolderEventGetCurrentWorkspace,
+  FolderEventReadAllWorkspaces,
 } from '@/services/backend/events/flowy-folder2';
 
 export class UserBackendService {
@@ -54,7 +54,7 @@ export class UserBackendService {
   };
 
   getCurrentWorkspace = async (): Promise<WorkspaceSettingPB> => {
-    const result = await FolderEventReadCurrentWorkspace();
+    const result = await FolderEventGetCurrentWorkspace();
     if (result.ok) {
       return result.val;
     } else {
@@ -64,7 +64,7 @@ export class UserBackendService {
 
   getWorkspaces = () => {
     const payload = WorkspaceIdPB.fromObject({});
-    return FolderEventReadWorkspaces(payload);
+    return FolderEventReadAllWorkspaces(payload);
   };
 
   openWorkspace = (workspaceId: string) => {
diff --git a/frontend/rust-lib/flowy-folder2/src/event_map.rs b/frontend/rust-lib/flowy-folder2/src/event_map.rs
index 8ef03cac35..95c0a02eeb 100644
--- a/frontend/rust-lib/flowy-folder2/src/event_map.rs
+++ b/frontend/rust-lib/flowy-folder2/src/event_map.rs
@@ -12,10 +12,10 @@ pub fn init(folder: Arc<Folder2Manager>) -> AFPlugin {
     // Workspace
     .event(FolderEvent::CreateWorkspace, create_workspace_handler)
     .event(
-        FolderEvent::ReadCurrentWorkspace,
-        read_cur_workspace_setting_handler,
+      FolderEvent::GetCurrentWorkspace,
+      read_cur_workspace_setting_handler,
     )
-    .event(FolderEvent::ReadWorkspaces, read_workspaces_handler)
+    .event(FolderEvent::ReadAllWorkspaces, read_workspaces_handler)
     .event(FolderEvent::OpenWorkspace, open_workspace_handler)
     .event(FolderEvent::ReadWorkspaceViews, read_workspace_views_handler)
      // View
@@ -45,11 +45,11 @@ pub enum FolderEvent {
 
   /// Read the current opening workspace. Currently, we only support one workspace
   #[event(output = "WorkspaceSettingPB")]
-  ReadCurrentWorkspace = 1,
+  GetCurrentWorkspace = 1,
 
-  /// Return a list of workspaces that the current user can access
+  /// Return a list of workspaces that the current user can access.
   #[event(input = "WorkspaceIdPB", output = "RepeatedWorkspacePB")]
-  ReadWorkspaces = 2,
+  ReadAllWorkspaces = 2,
 
   /// Delete the workspace
   #[event(input = "WorkspaceIdPB")]
@@ -59,7 +59,8 @@ pub enum FolderEvent {
   #[event(input = "WorkspaceIdPB", output = "WorkspacePB")]
   OpenWorkspace = 4,
 
-  /// Return a list of views that belong to this workspace.
+  /// Return a list of views of the current workspace.
+  /// Only the first level of child views are included.
   #[event(input = "WorkspaceIdPB", output = "RepeatedViewPB")]
   ReadWorkspaceViews = 5,
 
diff --git a/frontend/rust-lib/flowy-folder2/src/manager.rs b/frontend/rust-lib/flowy-folder2/src/manager.rs
index 4c204e4c88..2108f052d5 100644
--- a/frontend/rust-lib/flowy-folder2/src/manager.rs
+++ b/frontend/rust-lib/flowy-folder2/src/manager.rs
@@ -18,8 +18,8 @@ use lib_infra::util::timestamp;
 
 use crate::deps::{FolderCloudService, FolderUser};
 use crate::entities::{
-  view_pb_with_child_views, CreateViewParams, CreateWorkspaceParams, RepeatedTrashPB,
-  RepeatedViewPB, RepeatedWorkspacePB, UpdateViewParams, ViewPB,
+  view_pb_with_child_views, CreateViewParams, CreateWorkspaceParams, DeletedViewPB,
+  RepeatedTrashPB, RepeatedViewPB, RepeatedWorkspacePB, UpdateViewParams, ViewPB,
 };
 use crate::notification::{
   send_notification, send_workspace_notification, send_workspace_setting_notification,
@@ -68,6 +68,8 @@ impl Folder2Manager {
     }
   }
 
+  /// Return a list of views of the current workspace.
+  /// Only the first level of child views are included.
   pub async fn get_current_workspace_views(&self) -> FlowyResult<Vec<ViewPB>> {
     let workspace_id = self
       .mutex_folder
@@ -315,6 +317,14 @@ impl Folder2Manager {
           folder.set_current_view("");
         }
       }
+
+      // notify the parent view that the view is moved to trash
+      send_notification(view_id, FolderNotification::DidMoveViewToTrash)
+        .payload(DeletedViewPB {
+          view_id: view_id.to_string(),
+          index: None,
+        })
+        .send();
     });
 
     Ok(())
diff --git a/frontend/rust-lib/flowy-folder2/tests/workspace/folder_test.rs b/frontend/rust-lib/flowy-folder2/tests/workspace/folder_test.rs
index c68da3041c..735f09c52f 100644
--- a/frontend/rust-lib/flowy-folder2/tests/workspace/folder_test.rs
+++ b/frontend/rust-lib/flowy-folder2/tests/workspace/folder_test.rs
@@ -4,14 +4,14 @@ use flowy_folder2::entities::CreateWorkspacePayloadPB;
 use flowy_test::{event_builder::*, FlowyCoreTest};
 
 #[tokio::test]
-async fn workspace_read_all() {
+async fn read_all_workspace_test() {
   let mut test = FolderTest::new().await;
   test.run_scripts(vec![ReadAllWorkspaces]).await;
   assert!(!test.all_workspace.is_empty());
 }
 
 #[tokio::test]
-async fn workspace_create() {
+async fn create_workspace_test() {
   let mut test = FolderTest::new().await;
   let name = "My new workspace".to_owned();
   let desc = "Daily routines".to_owned();
@@ -34,7 +34,7 @@ async fn workspace_create() {
 }
 
 #[tokio::test]
-async fn workspace_read() {
+async fn get_workspace_test() {
   let mut test = FolderTest::new().await;
   let workspace = test.workspace.clone();
 
@@ -47,21 +47,21 @@ async fn workspace_read() {
 }
 
 #[tokio::test]
-async fn workspace_create_with_apps() {
+async fn create_parent_view_test() {
   let mut test = FolderTest::new().await;
   test
-    .run_scripts(vec![CreateApp {
+    .run_scripts(vec![CreateParentView {
       name: "App".to_string(),
       desc: "App description".to_string(),
     }])
     .await;
 
   let app = test.parent_view.clone();
-  test.run_scripts(vec![RefreshRootView(app.id)]).await;
+  test.run_scripts(vec![ReloadParentView(app.id)]).await;
 }
 
 #[tokio::test]
-async fn workspace_create_with_invalid_name() {
+async fn create_parent_view_with_invalid_name() {
   for (name, code) in invalid_workspace_name_test_case() {
     let sdk = FlowyCoreTest::new();
     let request = CreateWorkspacePayloadPB {
@@ -84,46 +84,46 @@ async fn workspace_create_with_invalid_name() {
 
 #[tokio::test]
 #[should_panic]
-async fn app_delete() {
+async fn delete_parent_view_test() {
   let mut test = FolderTest::new().await;
-  let app = test.parent_view.clone();
+  let parent_view = test.parent_view.clone();
   test
-    .run_scripts(vec![DeleteRootView, RefreshRootView(app.id)])
+    .run_scripts(vec![DeleteParentView, ReloadParentView(parent_view.id)])
     .await;
 }
 
 #[tokio::test]
-async fn app_delete_then_restore() {
+async fn delete_parent_view_then_restore() {
   let mut test = FolderTest::new().await;
   test
-    .run_scripts(vec![RefreshRootView(test.parent_view.id.clone())])
+    .run_scripts(vec![ReloadParentView(test.parent_view.id.clone())])
     .await;
 
   let parent_view = test.parent_view.clone();
   test
     .run_scripts(vec![
-      DeleteRootView,
+      DeleteParentView,
       RestoreAppFromTrash,
-      RefreshRootView(parent_view.id.clone()),
-      AssertRootView(parent_view),
+      ReloadParentView(parent_view.id.clone()),
+      AssertParentView(parent_view),
     ])
     .await;
 }
 
 #[tokio::test]
-async fn app_update() {
+async fn update_parent_view_test() {
   let mut test = FolderTest::new().await;
-  let app = test.parent_view.clone();
+  let parent_view = test.parent_view.clone();
   let new_name = "😁 hell world".to_owned();
-  assert_ne!(app.name, new_name);
+  assert_ne!(parent_view.name, new_name);
 
   test
     .run_scripts(vec![
-      UpdateRootView {
+      UpdateParentView {
         name: Some(new_name.clone()),
         desc: None,
       },
-      RefreshRootView(app.id),
+      ReloadParentView(parent_view.id),
     ])
     .await;
   assert_eq!(test.parent_view.name, new_name);
@@ -145,7 +145,7 @@ async fn app_create_with_view() {
         desc: "Grid description".to_owned(),
         layout: ViewLayout::Grid,
       },
-      RefreshRootView(app.id),
+      ReloadParentView(app.id),
     ])
     .await;
 
@@ -212,7 +212,7 @@ async fn view_delete_all() {
         desc: "Grid description".to_owned(),
         layout: ViewLayout::Grid,
       },
-      RefreshRootView(parent_view.id.clone()),
+      ReloadParentView(parent_view.id.clone()),
     ])
     .await;
 
@@ -230,7 +230,7 @@ async fn view_delete_all() {
   test
     .run_scripts(vec![
       DeleteViews(view_ids),
-      RefreshRootView(parent_view.id),
+      ReloadParentView(parent_view.id),
       ReadTrash,
     ])
     .await;
@@ -242,7 +242,7 @@ async fn view_delete_all() {
 #[tokio::test]
 async fn view_delete_all_permanent() {
   let mut test = FolderTest::new().await;
-  let app = test.parent_view.clone();
+  let parent_view = test.parent_view.clone();
   test
     .run_scripts(vec![
       CreateView {
@@ -250,7 +250,7 @@ async fn view_delete_all_permanent() {
         desc: "View A description".to_owned(),
         layout: ViewLayout::Document,
       },
-      RefreshRootView(app.id.clone()),
+      ReloadParentView(parent_view.id.clone()),
     ])
     .await;
 
@@ -263,7 +263,7 @@ async fn view_delete_all_permanent() {
   test
     .run_scripts(vec![
       DeleteViews(view_ids),
-      RefreshRootView(app.id),
+      ReloadParentView(parent_view.id),
       DeleteAllTrash,
       ReadTrash,
     ])
diff --git a/frontend/rust-lib/flowy-folder2/tests/workspace/script.rs b/frontend/rust-lib/flowy-folder2/tests/workspace/script.rs
index dc3e3c0267..25ac6daf01 100644
--- a/frontend/rust-lib/flowy-folder2/tests/workspace/script.rs
+++ b/frontend/rust-lib/flowy-folder2/tests/workspace/script.rs
@@ -16,17 +16,17 @@ pub enum FolderScript {
   ReadWorkspace(Option<String>),
 
   // App
-  CreateApp {
+  CreateParentView {
     name: String,
     desc: String,
   },
-  AssertRootView(ViewPB),
-  RefreshRootView(String),
-  UpdateRootView {
+  AssertParentView(ViewPB),
+  ReloadParentView(String),
+  UpdateParentView {
     name: Option<String>,
     desc: Option<String>,
   },
-  DeleteRootView,
+  DeleteParentView,
 
   // View
   CreateView {
@@ -107,24 +107,23 @@ impl FolderTest {
         let workspace = read_workspace(sdk, workspace_id).await.pop().unwrap();
         self.workspace = workspace;
       },
-      FolderScript::CreateApp { name, desc } => {
+      FolderScript::CreateParentView { name, desc } => {
         let app = create_app(sdk, &self.workspace.id, &name, &desc).await;
         self.parent_view = app;
       },
-      FolderScript::AssertRootView(app) => {
+      FolderScript::AssertParentView(app) => {
         assert_eq!(self.parent_view, app, "App not equal");
       },
-      FolderScript::RefreshRootView(app_id) => {
-        let app = read_view(sdk, &app_id).await;
-        self.parent_view = app;
+      FolderScript::ReloadParentView(parent_view_id) => {
+        let parent_view = read_view(sdk, &parent_view_id).await;
+        self.parent_view = parent_view;
       },
-      FolderScript::UpdateRootView { name, desc } => {
+      FolderScript::UpdateParentView { name, desc } => {
         update_view(sdk, &self.parent_view.id, name, desc).await;
       },
-      FolderScript::DeleteRootView => {
+      FolderScript::DeleteParentView => {
         delete_view(sdk, vec![self.parent_view.id.clone()]).await;
       },
-
       FolderScript::CreateView { name, desc, layout } => {
         let view = create_view(sdk, &self.parent_view.id, &name, &desc, layout).await;
         self.child_view = view;
@@ -189,7 +188,7 @@ pub async fn read_workspace(sdk: &FlowyCoreTest, workspace_id: Option<String>) -
     value: workspace_id,
   };
   let repeated_workspace = EventBuilder::new(sdk.clone())
-    .event(ReadWorkspaces)
+    .event(ReadAllWorkspaces)
     .payload(request.clone())
     .async_send()
     .await
@@ -256,7 +255,7 @@ pub async fn create_view(
 }
 
 pub async fn read_view(sdk: &FlowyCoreTest, view_id: &str) -> ViewPB {
-  let view_id: ViewIdPB = view_id.into();
+  let view_id = ViewIdPB::from(view_id);
   EventBuilder::new(sdk.clone())
     .event(ReadView)
     .payload(view_id)
diff --git a/frontend/rust-lib/flowy-test/tests/user/supabase_test/workspace_test.rs b/frontend/rust-lib/flowy-test/tests/user/supabase_test/workspace_test.rs
index 446e197ac6..5117a6923b 100644
--- a/frontend/rust-lib/flowy-test/tests/user/supabase_test/workspace_test.rs
+++ b/frontend/rust-lib/flowy-test/tests/user/supabase_test/workspace_test.rs
@@ -1,6 +1,6 @@
 use crate::user::supabase_test::helper::get_supabase_config;
 use flowy_folder2::entities::WorkspaceSettingPB;
-use flowy_folder2::event_map::FolderEvent::ReadCurrentWorkspace;
+use flowy_folder2::event_map::FolderEvent::GetCurrentWorkspace;
 
 use flowy_test::{event_builder::EventBuilder, FlowyCoreTest};
 use flowy_user::entities::{AuthTypePB, ThirdPartyAuthPB, UserProfilePB};
@@ -27,7 +27,7 @@ async fn initial_workspace_test() {
       .parse::<UserProfilePB>();
 
     let workspace_settings = EventBuilder::new(test.clone())
-      .event(ReadCurrentWorkspace)
+      .event(GetCurrentWorkspace)
       .async_send()
       .await
       .parse::<WorkspaceSettingPB>();
diff --git a/frontend/scripts/makefile/env.toml b/frontend/scripts/makefile/env.toml
index e797e005ee..5ea2965387 100644
--- a/frontend/scripts/makefile/env.toml
+++ b/frontend/scripts/makefile/env.toml
@@ -1,8 +1,14 @@
 [tasks.appflowy-flutter-deps-tools]
-run_task = { name = ["install_flutter_prerequests","install_diesel"] }
+run_task = { name = ["install_flutter_prerequests"] }
 
 [tasks.appflowy-tauri-deps-tools]
-run_task = { name = ["install_tauri_prerequests","install_diesel"] }
+run_task = { name = ["install_tauri_prerequests"] }
+
+[tasks.appflowy-flutter-dev-tools]
+run_task = { name = ["appflowy-flutter-deps-tools","install_diesel"] }
+
+[tasks.appflowy-tauri-dev-tools]
+run_task = { name = ["appflowy-tauri-deps-tools","install_diesel"] }
 
 [tasks.install_windows_deps.windows]
 dependencies=["check_duckscript_installation", "check_visual_studio_installation", "check_vcpkg", "install_vcpkg_sqlite", "install_rust_vcpkg_cli"]
@@ -78,9 +84,9 @@ dependencies = ["check_vcpkg"]
 
 [tasks.install_targets.mac]
 script = """
-rustup target add x86_64-apple-ios
-rustup target add x86_64-apple-darwin
-rustup target add aarch64-apple-ios
+#rustup target add x86_64-apple-ios
+#rustup target add x86_64-apple-darwin
+#rustup target add aarch64-apple-ios
 rustup target add aarch64-apple-darwin
 """