Explorar o código

feat: show grid

appflowy %!s(int64=3) %!d(string=hai) anos
pai
achega
05441f865e
Modificáronse 49 ficheiros con 328 adicións e 228 borrados
  1. 1 1
      frontend/app_flowy/lib/plugin/plugin.dart
  2. 1 1
      frontend/app_flowy/lib/workspace/application/doc/doc_bloc.dart
  3. 7 6
      frontend/app_flowy/lib/workspace/application/doc/doc_service.dart
  4. 5 2
      frontend/app_flowy/lib/workspace/application/grid/grid_service.dart
  5. 1 1
      frontend/app_flowy/lib/workspace/presentation/plugins/doc/document.dart
  6. 1 1
      frontend/app_flowy/lib/workspace/presentation/plugins/grid/grid.dart
  7. 20 3
      frontend/app_flowy/packages/flowy_sdk/lib/dispatch/dart_event/flowy-block/dart_event.dart
  8. 5 5
      frontend/app_flowy/packages/flowy_sdk/lib/dispatch/dart_event/flowy-folder/dart_event.dart
  9. 3 3
      frontend/app_flowy/packages/flowy_sdk/lib/dispatch/dart_event/flowy-grid/dart_event.dart
  10. 5 3
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-block/event_map.pbenum.dart
  11. 4 3
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-block/event_map.pbjson.dart
  12. 3 3
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder-data-model/view.pb.dart
  13. 3 5
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder-data-model/view.pbenum.dart
  14. 3 4
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder-data-model/view.pbjson.dart
  15. 2 2
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder/event_map.pbenum.dart
  16. 2 2
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder/event_map.pbjson.dart
  17. 2 2
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-grid/event_map.pbenum.dart
  18. 2 2
      frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-grid/event_map.pbjson.dart
  19. 2 2
      frontend/rust-lib/dart-ffi/Cargo.toml
  20. 14 1
      frontend/rust-lib/flowy-block/src/event_handler.rs
  21. 7 3
      frontend/rust-lib/flowy-block/src/event_map.rs
  22. 12 8
      frontend/rust-lib/flowy-block/src/protobuf/model/event_map.rs
  23. 3 2
      frontend/rust-lib/flowy-block/src/protobuf/proto/event_map.proto
  24. 3 3
      frontend/rust-lib/flowy-folder/src/event_map.rs
  25. 2 2
      frontend/rust-lib/flowy-folder/src/manager.rs
  26. 10 10
      frontend/rust-lib/flowy-folder/src/protobuf/model/event_map.rs
  27. 1 1
      frontend/rust-lib/flowy-folder/src/protobuf/proto/event_map.proto
  28. 9 13
      frontend/rust-lib/flowy-folder/src/services/persistence/version_1/view_sql.rs
  29. 3 12
      frontend/rust-lib/flowy-folder/src/services/view/controller.rs
  30. 4 5
      frontend/rust-lib/flowy-folder/src/services/view/event_handler.rs
  31. 1 1
      frontend/rust-lib/flowy-folder/tests/workspace/helper.rs
  32. 2 2
      frontend/rust-lib/flowy-folder/tests/workspace/script.rs
  33. 1 1
      frontend/rust-lib/flowy-grid/src/event_handler.rs
  34. 2 2
      frontend/rust-lib/flowy-grid/src/event_map.rs
  35. 1 1
      frontend/rust-lib/flowy-grid/src/lib.rs
  36. 16 55
      frontend/rust-lib/flowy-grid/src/manager.rs
  37. 7 7
      frontend/rust-lib/flowy-grid/src/protobuf/model/event_map.rs
  38. 1 1
      frontend/rust-lib/flowy-grid/src/protobuf/proto/event_map.proto
  39. 2 2
      frontend/rust-lib/flowy-grid/src/services/cell_data.rs
  40. 106 0
      frontend/rust-lib/flowy-grid/src/services/grid_builder.rs
  41. 1 0
      frontend/rust-lib/flowy-grid/src/services/mod.rs
  42. 1 1
      frontend/rust-lib/flowy-grid/src/services/util.rs
  43. 4 3
      frontend/rust-lib/flowy-sdk/src/deps_resolve/folder_deps.rs
  44. 1 1
      frontend/rust-lib/flowy-test/src/helper.rs
  45. 13 4
      shared-lib/flowy-collaboration/src/entities/document_info.rs
  46. 6 8
      shared-lib/flowy-folder-data-model/src/entities/view.rs
  47. 20 24
      shared-lib/flowy-folder-data-model/src/protobuf/model/view.rs
  48. 2 3
      shared-lib/flowy-folder-data-model/src/protobuf/proto/view.proto
  49. 1 1
      shared-lib/flowy-folder-data-model/src/user_default.rs

+ 1 - 1
frontend/app_flowy/lib/plugin/plugin.dart

@@ -52,7 +52,7 @@ abstract class PluginBuilder {
 
   PluginType get pluginType;
 
-  ViewDataType get dataType => ViewDataType.PlainText;
+  ViewDataType get dataType => ViewDataType.Block;
 }
 
 abstract class PluginConfig {

+ 1 - 1
frontend/app_flowy/lib/workspace/application/doc/doc_bloc.dart

@@ -85,7 +85,7 @@ class DocumentBloc extends Bloc<DocumentEvent, DocumentState> {
     });
 
     listener.start();
-    final result = await service.openDocument(docId: view.id, dataType: view.dataType);
+    final result = await service.openDocument(docId: view.id);
     result.fold(
       (block) {
         document = _decodeJsonToDocument(block.deltaStr);

+ 7 - 6
frontend/app_flowy/lib/workspace/application/doc/doc_service.dart

@@ -7,17 +7,18 @@ import 'package:flowy_sdk/protobuf/flowy-error/errors.pb.dart';
 class DocumentService {
   Future<Either<BlockDelta, FlowyError>> openDocument({
     required String docId,
-    required ViewDataType dataType,
-  }) {
-    final request = ViewId(value: docId);
-    return FolderEventOpenView(request).send();
+  }) async {
+    await FolderEventSetLatestView(ViewId(value: docId)).send();
+
+    final payload = BlockId(value: docId);
+    return BlockEventGetBlockData(payload).send();
   }
 
   Future<Either<BlockDelta, FlowyError>> composeDelta({required String docId, required String data}) {
-    final request = BlockDelta.create()
+    final payload = BlockDelta.create()
       ..blockId = docId
       ..deltaStr = data;
-    return FolderEventApplyDocDelta(request).send();
+    return FolderEventApplyDocDelta(payload).send();
   }
 
   Future<Either<Unit, FlowyError>> closeDocument({required String docId}) {

+ 5 - 2
frontend/app_flowy/lib/workspace/application/grid/grid_service.dart

@@ -1,12 +1,15 @@
 import 'package:flowy_sdk/dispatch/dispatch.dart';
 import 'package:flowy_sdk/protobuf/flowy-error/errors.pb.dart';
+import 'package:flowy_sdk/protobuf/flowy-folder-data-model/view.pb.dart';
 import 'package:flowy_sdk/protobuf/flowy-grid-data-model/grid.pb.dart';
 import 'package:dartz/dartz.dart';
 
 class GridService {
-  Future<Either<Grid, FlowyError>> openGrid({required String gridId}) {
+  Future<Either<Grid, FlowyError>> openGrid({required String gridId}) async {
+    await FolderEventSetLatestView(ViewId(value: gridId)).send();
+
     final payload = GridId(value: gridId);
-    return GridEventOpenGrid(payload).send();
+    return GridEventGetGridData(payload).send();
   }
 
   Future<Either<void, FlowyError>> createRow({required String gridId}) {

+ 1 - 1
frontend/app_flowy/lib/workspace/presentation/plugins/doc/document.dart

@@ -50,7 +50,7 @@ class DocumentPluginBuilder extends PluginBuilder {
   PluginType get pluginType => DefaultPlugin.quill.type();
 
   @override
-  ViewDataType get dataType => ViewDataType.RichText;
+  ViewDataType get dataType => ViewDataType.Block;
 }
 
 class DocumentPlugin implements Plugin {

+ 1 - 1
frontend/app_flowy/lib/workspace/presentation/plugins/grid/grid.dart

@@ -17,7 +17,7 @@ class GridPluginBuilder implements PluginBuilder {
   }
 
   @override
-  String get menuName => "Table";
+  String get menuName => "Grid";
 
   @override
   PluginType get pluginType => DefaultPlugin.grid.type();

+ 20 - 3
frontend/app_flowy/packages/flowy_sdk/lib/dispatch/dart_event/flowy-block/dart_event.dart

@@ -1,13 +1,30 @@
 
 /// Auto generate. Do not edit
 part of '../../dispatch.dart';
-class BlockEventApplyDocDelta {
+class BlockEventGetBlockData {
+     BlockId request;
+     BlockEventGetBlockData(this.request);
+
+    Future<Either<BlockDelta, FlowyError>> send() {
+    final request = FFIRequest.create()
+          ..event = BlockEvent.GetBlockData.toString()
+          ..payload = requestToBytes(this.request);
+
+    return Dispatch.asyncRequest(request)
+        .then((bytesResult) => bytesResult.fold(
+           (okBytes) => left(BlockDelta.fromBuffer(okBytes)),
+           (errBytes) => right(FlowyError.fromBuffer(errBytes)),
+        ));
+    }
+}
+
+class BlockEventApplyDelta {
      BlockDelta request;
-     BlockEventApplyDocDelta(this.request);
+     BlockEventApplyDelta(this.request);
 
     Future<Either<BlockDelta, FlowyError>> send() {
     final request = FFIRequest.create()
-          ..event = BlockEvent.ApplyDocDelta.toString()
+          ..event = BlockEvent.ApplyDelta.toString()
           ..payload = requestToBytes(this.request);
 
     return Dispatch.asyncRequest(request)

+ 5 - 5
frontend/app_flowy/packages/flowy_sdk/lib/dispatch/dart_event/flowy-folder/dart_event.dart

@@ -267,18 +267,18 @@ class FolderEventCopyLink {
     }
 }
 
-class FolderEventOpenView {
+class FolderEventSetLatestView {
      ViewId request;
-     FolderEventOpenView(this.request);
+     FolderEventSetLatestView(this.request);
 
-    Future<Either<BlockDelta, FlowyError>> send() {
+    Future<Either<Unit, FlowyError>> send() {
     final request = FFIRequest.create()
-          ..event = FolderEvent.OpenView.toString()
+          ..event = FolderEvent.SetLatestView.toString()
           ..payload = requestToBytes(this.request);
 
     return Dispatch.asyncRequest(request)
         .then((bytesResult) => bytesResult.fold(
-           (okBytes) => left(BlockDelta.fromBuffer(okBytes)),
+           (bytes) => left(unit),
            (errBytes) => right(FlowyError.fromBuffer(errBytes)),
         ));
     }

+ 3 - 3
frontend/app_flowy/packages/flowy_sdk/lib/dispatch/dart_event/flowy-grid/dart_event.dart

@@ -1,13 +1,13 @@
 
 /// Auto generate. Do not edit
 part of '../../dispatch.dart';
-class GridEventOpenGrid {
+class GridEventGetGridData {
      GridId request;
-     GridEventOpenGrid(this.request);
+     GridEventGetGridData(this.request);
 
     Future<Either<Grid, FlowyError>> send() {
     final request = FFIRequest.create()
-          ..event = GridEvent.OpenGrid.toString()
+          ..event = GridEvent.GetGridData.toString()
           ..payload = requestToBytes(this.request);
 
     return Dispatch.asyncRequest(request)

+ 5 - 3
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-block/event_map.pbenum.dart

@@ -10,11 +10,13 @@ import 'dart:core' as $core;
 import 'package:protobuf/protobuf.dart' as $pb;
 
 class BlockEvent extends $pb.ProtobufEnum {
-  static const BlockEvent ApplyDocDelta = BlockEvent._(0, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'ApplyDocDelta');
-  static const BlockEvent ExportDocument = BlockEvent._(1, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'ExportDocument');
+  static const BlockEvent GetBlockData = BlockEvent._(0, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'GetBlockData');
+  static const BlockEvent ApplyDelta = BlockEvent._(1, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'ApplyDelta');
+  static const BlockEvent ExportDocument = BlockEvent._(2, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'ExportDocument');
 
   static const $core.List<BlockEvent> values = <BlockEvent> [
-    ApplyDocDelta,
+    GetBlockData,
+    ApplyDelta,
     ExportDocument,
   ];
 

+ 4 - 3
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-block/event_map.pbjson.dart

@@ -12,10 +12,11 @@ import 'dart:typed_data' as $typed_data;
 const BlockEvent$json = const {
   '1': 'BlockEvent',
   '2': const [
-    const {'1': 'ApplyDocDelta', '2': 0},
-    const {'1': 'ExportDocument', '2': 1},
+    const {'1': 'GetBlockData', '2': 0},
+    const {'1': 'ApplyDelta', '2': 1},
+    const {'1': 'ExportDocument', '2': 2},
   ],
 };
 
 /// Descriptor for `BlockEvent`. Decode as a `google.protobuf.EnumDescriptorProto`.
-final $typed_data.Uint8List blockEventDescriptor = $convert.base64Decode('CgpCbG9ja0V2ZW50EhEKDUFwcGx5RG9jRGVsdGEQABISCg5FeHBvcnREb2N1bWVudBAB');
+final $typed_data.Uint8List blockEventDescriptor = $convert.base64Decode('CgpCbG9ja0V2ZW50EhAKDEdldEJsb2NrRGF0YRAAEg4KCkFwcGx5RGVsdGEQARISCg5FeHBvcnREb2N1bWVudBAC');

+ 3 - 3
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder-data-model/view.pb.dart

@@ -20,7 +20,7 @@ class View extends $pb.GeneratedMessage {
     ..aOS(2, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'belongToId')
     ..aOS(3, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'name')
     ..aOS(4, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'desc')
-    ..e<ViewDataType>(5, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'dataType', $pb.PbFieldType.OE, defaultOrMaker: ViewDataType.RichText, valueOf: ViewDataType.valueOf, enumValues: ViewDataType.values)
+    ..e<ViewDataType>(5, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'dataType', $pb.PbFieldType.OE, defaultOrMaker: ViewDataType.Block, valueOf: ViewDataType.valueOf, enumValues: ViewDataType.values)
     ..aInt64(6, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'version')
     ..aOM<RepeatedView>(7, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'belongings', subBuilder: RepeatedView.create)
     ..aInt64(8, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'modifiedTime')
@@ -274,7 +274,7 @@ class CreateViewPayload extends $pb.GeneratedMessage {
     ..aOS(2, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'name')
     ..aOS(3, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'desc')
     ..aOS(4, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'thumbnail')
-    ..e<ViewDataType>(5, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'dataType', $pb.PbFieldType.OE, defaultOrMaker: ViewDataType.RichText, valueOf: ViewDataType.valueOf, enumValues: ViewDataType.values)
+    ..e<ViewDataType>(5, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'dataType', $pb.PbFieldType.OE, defaultOrMaker: ViewDataType.Block, valueOf: ViewDataType.valueOf, enumValues: ViewDataType.values)
     ..aOS(6, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'extData')
     ..a<$core.int>(7, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'pluginType', $pb.PbFieldType.O3)
     ..hasRequiredFields = false
@@ -408,7 +408,7 @@ class CreateViewParams extends $pb.GeneratedMessage {
     ..aOS(2, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'name')
     ..aOS(3, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'desc')
     ..aOS(4, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'thumbnail')
-    ..e<ViewDataType>(5, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'dataType', $pb.PbFieldType.OE, defaultOrMaker: ViewDataType.RichText, valueOf: ViewDataType.valueOf, enumValues: ViewDataType.values)
+    ..e<ViewDataType>(5, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'dataType', $pb.PbFieldType.OE, defaultOrMaker: ViewDataType.Block, valueOf: ViewDataType.valueOf, enumValues: ViewDataType.values)
     ..aOS(6, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'extData')
     ..aOS(7, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'viewId')
     ..aOS(8, const $core.bool.fromEnvironment('protobuf.omit_field_names') ? '' : 'data')

+ 3 - 5
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder-data-model/view.pbenum.dart

@@ -10,13 +10,11 @@ import 'dart:core' as $core;
 import 'package:protobuf/protobuf.dart' as $pb;
 
 class ViewDataType extends $pb.ProtobufEnum {
-  static const ViewDataType RichText = ViewDataType._(0, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'RichText');
-  static const ViewDataType PlainText = ViewDataType._(1, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'PlainText');
-  static const ViewDataType Grid = ViewDataType._(2, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'Grid');
+  static const ViewDataType Block = ViewDataType._(0, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'Block');
+  static const ViewDataType Grid = ViewDataType._(1, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'Grid');
 
   static const $core.List<ViewDataType> values = <ViewDataType> [
-    RichText,
-    PlainText,
+    Block,
     Grid,
   ];
 

+ 3 - 4
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder-data-model/view.pbjson.dart

@@ -12,14 +12,13 @@ import 'dart:typed_data' as $typed_data;
 const ViewDataType$json = const {
   '1': 'ViewDataType',
   '2': const [
-    const {'1': 'RichText', '2': 0},
-    const {'1': 'PlainText', '2': 1},
-    const {'1': 'Grid', '2': 2},
+    const {'1': 'Block', '2': 0},
+    const {'1': 'Grid', '2': 1},
   ],
 };
 
 /// Descriptor for `ViewDataType`. Decode as a `google.protobuf.EnumDescriptorProto`.
-final $typed_data.Uint8List viewDataTypeDescriptor = $convert.base64Decode('CgxWaWV3RGF0YVR5cGUSDAoIUmljaFRleHQQABINCglQbGFpblRleHQQARIICgRHcmlkEAI=');
+final $typed_data.Uint8List viewDataTypeDescriptor = $convert.base64Decode('CgxWaWV3RGF0YVR5cGUSCQoFQmxvY2sQABIICgRHcmlkEAE=');
 @$core.Deprecated('Use viewDescriptor instead')
 const View$json = const {
   '1': 'View',

+ 2 - 2
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder/event_map.pbenum.dart

@@ -26,7 +26,7 @@ class FolderEvent extends $pb.ProtobufEnum {
   static const FolderEvent DeleteView = FolderEvent._(204, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'DeleteView');
   static const FolderEvent DuplicateView = FolderEvent._(205, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'DuplicateView');
   static const FolderEvent CopyLink = FolderEvent._(206, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'CopyLink');
-  static const FolderEvent OpenView = FolderEvent._(207, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'OpenView');
+  static const FolderEvent SetLatestView = FolderEvent._(207, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'SetLatestView');
   static const FolderEvent CloseView = FolderEvent._(208, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'CloseView');
   static const FolderEvent ReadTrash = FolderEvent._(300, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'ReadTrash');
   static const FolderEvent PutbackTrash = FolderEvent._(301, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'PutbackTrash');
@@ -53,7 +53,7 @@ class FolderEvent extends $pb.ProtobufEnum {
     DeleteView,
     DuplicateView,
     CopyLink,
-    OpenView,
+    SetLatestView,
     CloseView,
     ReadTrash,
     PutbackTrash,

+ 2 - 2
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-folder/event_map.pbjson.dart

@@ -28,7 +28,7 @@ const FolderEvent$json = const {
     const {'1': 'DeleteView', '2': 204},
     const {'1': 'DuplicateView', '2': 205},
     const {'1': 'CopyLink', '2': 206},
-    const {'1': 'OpenView', '2': 207},
+    const {'1': 'SetLatestView', '2': 207},
     const {'1': 'CloseView', '2': 208},
     const {'1': 'ReadTrash', '2': 300},
     const {'1': 'PutbackTrash', '2': 301},
@@ -41,4 +41,4 @@ const FolderEvent$json = const {
 };
 
 /// Descriptor for `FolderEvent`. Decode as a `google.protobuf.EnumDescriptorProto`.
-final $typed_data.Uint8List folderEventDescriptor = $convert.base64Decode('CgtGb2xkZXJFdmVudBITCg9DcmVhdGVXb3Jrc3BhY2UQABIUChBSZWFkQ3VyV29ya3NwYWNlEAESEgoOUmVhZFdvcmtzcGFjZXMQAhITCg9EZWxldGVXb3Jrc3BhY2UQAxIRCg1PcGVuV29ya3NwYWNlEAQSFQoRUmVhZFdvcmtzcGFjZUFwcHMQBRINCglDcmVhdGVBcHAQZRINCglEZWxldGVBcHAQZhILCgdSZWFkQXBwEGcSDQoJVXBkYXRlQXBwEGgSDwoKQ3JlYXRlVmlldxDJARINCghSZWFkVmlldxDKARIPCgpVcGRhdGVWaWV3EMsBEg8KCkRlbGV0ZVZpZXcQzAESEgoNRHVwbGljYXRlVmlldxDNARINCghDb3B5TGluaxDOARINCghPcGVuVmlldxDPARIOCglDbG9zZVZpZXcQ0AESDgoJUmVhZFRyYXNoEKwCEhEKDFB1dGJhY2tUcmFzaBCtAhIQCgtEZWxldGVUcmFzaBCuAhIUCg9SZXN0b3JlQWxsVHJhc2gQrwISEwoORGVsZXRlQWxsVHJhc2gQsAISEgoNQXBwbHlEb2NEZWx0YRCQAxITCg5FeHBvcnREb2N1bWVudBD0Aw==');
+final $typed_data.Uint8List folderEventDescriptor = $convert.base64Decode('CgtGb2xkZXJFdmVudBITCg9DcmVhdGVXb3Jrc3BhY2UQABIUChBSZWFkQ3VyV29ya3NwYWNlEAESEgoOUmVhZFdvcmtzcGFjZXMQAhITCg9EZWxldGVXb3Jrc3BhY2UQAxIRCg1PcGVuV29ya3NwYWNlEAQSFQoRUmVhZFdvcmtzcGFjZUFwcHMQBRINCglDcmVhdGVBcHAQZRINCglEZWxldGVBcHAQZhILCgdSZWFkQXBwEGcSDQoJVXBkYXRlQXBwEGgSDwoKQ3JlYXRlVmlldxDJARINCghSZWFkVmlldxDKARIPCgpVcGRhdGVWaWV3EMsBEg8KCkRlbGV0ZVZpZXcQzAESEgoNRHVwbGljYXRlVmlldxDNARINCghDb3B5TGluaxDOARISCg1TZXRMYXRlc3RWaWV3EM8BEg4KCUNsb3NlVmlldxDQARIOCglSZWFkVHJhc2gQrAISEQoMUHV0YmFja1RyYXNoEK0CEhAKC0RlbGV0ZVRyYXNoEK4CEhQKD1Jlc3RvcmVBbGxUcmFzaBCvAhITCg5EZWxldGVBbGxUcmFzaBCwAhISCg1BcHBseURvY0RlbHRhEJADEhMKDkV4cG9ydERvY3VtZW50EPQD');

+ 2 - 2
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-grid/event_map.pbenum.dart

@@ -10,13 +10,13 @@ import 'dart:core' as $core;
 import 'package:protobuf/protobuf.dart' as $pb;
 
 class GridEvent extends $pb.ProtobufEnum {
-  static const GridEvent OpenGrid = GridEvent._(0, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'OpenGrid');
+  static const GridEvent GetGridData = GridEvent._(0, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'GetGridData');
   static const GridEvent GetRows = GridEvent._(1, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'GetRows');
   static const GridEvent GetFields = GridEvent._(2, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'GetFields');
   static const GridEvent CreateRow = GridEvent._(3, const $core.bool.fromEnvironment('protobuf.omit_enum_names') ? '' : 'CreateRow');
 
   static const $core.List<GridEvent> values = <GridEvent> [
-    OpenGrid,
+    GetGridData,
     GetRows,
     GetFields,
     CreateRow,

+ 2 - 2
frontend/app_flowy/packages/flowy_sdk/lib/protobuf/flowy-grid/event_map.pbjson.dart

@@ -12,7 +12,7 @@ import 'dart:typed_data' as $typed_data;
 const GridEvent$json = const {
   '1': 'GridEvent',
   '2': const [
-    const {'1': 'OpenGrid', '2': 0},
+    const {'1': 'GetGridData', '2': 0},
     const {'1': 'GetRows', '2': 1},
     const {'1': 'GetFields', '2': 2},
     const {'1': 'CreateRow', '2': 3},
@@ -20,4 +20,4 @@ const GridEvent$json = const {
 };
 
 /// Descriptor for `GridEvent`. Decode as a `google.protobuf.EnumDescriptorProto`.
-final $typed_data.Uint8List gridEventDescriptor = $convert.base64Decode('CglHcmlkRXZlbnQSDAoIT3BlbkdyaWQQABILCgdHZXRSb3dzEAESDQoJR2V0RmllbGRzEAISDQoJQ3JlYXRlUm93EAM=');
+final $typed_data.Uint8List gridEventDescriptor = $convert.base64Decode('CglHcmlkRXZlbnQSDwoLR2V0R3JpZERhdGEQABILCgdHZXRSb3dzEAESDQoJR2V0RmllbGRzEAISDQoJQ3JlYXRlUm93EAM=');

+ 2 - 2
frontend/rust-lib/dart-ffi/Cargo.toml

@@ -7,8 +7,8 @@ edition = "2018"
 [lib]
 name = "dart_ffi"
 # this value will change depending on the target os
-# default staticlib
-crate-type = ["staticlib"]
+# default cdylib
+crate-type = ["cdylib"]
 
 
 [dependencies]

+ 14 - 1
frontend/rust-lib/flowy-block/src/event_handler.rs

@@ -1,11 +1,24 @@
 use crate::entities::{ExportData, ExportParams, ExportPayload};
 use crate::BlockManager;
-use flowy_collaboration::entities::document_info::BlockDelta;
+use flowy_collaboration::entities::document_info::{BlockDelta, BlockId};
 use flowy_error::FlowyError;
 use lib_dispatch::prelude::{data_result, AppData, Data, DataResult};
 use std::convert::TryInto;
 use std::sync::Arc;
 
+pub(crate) async fn get_block_data_handler(
+    data: Data<BlockId>,
+    manager: AppData<Arc<BlockManager>>,
+) -> DataResult<BlockDelta, FlowyError> {
+    let block_id: BlockId = data.into_inner();
+    let editor = manager.open_block(&block_id).await?;
+    let delta_str = editor.delta_str().await?;
+    data_result(BlockDelta {
+        block_id: block_id.into(),
+        delta_str,
+    })
+}
+
 pub(crate) async fn apply_delta_handler(
     data: Data<BlockDelta>,
     manager: AppData<Arc<BlockManager>>,

+ 7 - 3
frontend/rust-lib/flowy-block/src/event_map.rs

@@ -9,7 +9,8 @@ pub fn create(block_manager: Arc<BlockManager>) -> Module {
     let mut module = Module::new().name(env!("CARGO_PKG_NAME")).data(block_manager);
 
     module = module
-        .event(BlockEvent::ApplyDocDelta, apply_delta_handler)
+        .event(BlockEvent::GetBlockData, get_block_data_handler)
+        .event(BlockEvent::ApplyDelta, apply_delta_handler)
         .event(BlockEvent::ExportDocument, export_handler);
 
     module
@@ -18,9 +19,12 @@ pub fn create(block_manager: Arc<BlockManager>) -> Module {
 #[derive(Clone, Copy, PartialEq, Eq, Debug, Display, Hash, ProtoBuf_Enum, Flowy_Event)]
 #[event_err = "FlowyError"]
 pub enum BlockEvent {
+    #[event(input = "BlockId", output = "BlockDelta")]
+    GetBlockData = 0,
+
     #[event(input = "BlockDelta", output = "BlockDelta")]
-    ApplyDocDelta = 0,
+    ApplyDelta = 1,
 
     #[event(input = "ExportPayload", output = "ExportData")]
-    ExportDocument = 1,
+    ExportDocument = 2,
 }

+ 12 - 8
frontend/rust-lib/flowy-block/src/protobuf/model/event_map.rs

@@ -25,8 +25,9 @@
 
 #[derive(Clone,PartialEq,Eq,Debug,Hash)]
 pub enum BlockEvent {
-    ApplyDocDelta = 0,
-    ExportDocument = 1,
+    GetBlockData = 0,
+    ApplyDelta = 1,
+    ExportDocument = 2,
 }
 
 impl ::protobuf::ProtobufEnum for BlockEvent {
@@ -36,15 +37,17 @@ impl ::protobuf::ProtobufEnum for BlockEvent {
 
     fn from_i32(value: i32) -> ::std::option::Option<BlockEvent> {
         match value {
-            0 => ::std::option::Option::Some(BlockEvent::ApplyDocDelta),
-            1 => ::std::option::Option::Some(BlockEvent::ExportDocument),
+            0 => ::std::option::Option::Some(BlockEvent::GetBlockData),
+            1 => ::std::option::Option::Some(BlockEvent::ApplyDelta),
+            2 => ::std::option::Option::Some(BlockEvent::ExportDocument),
             _ => ::std::option::Option::None
         }
     }
 
     fn values() -> &'static [Self] {
         static values: &'static [BlockEvent] = &[
-            BlockEvent::ApplyDocDelta,
+            BlockEvent::GetBlockData,
+            BlockEvent::ApplyDelta,
             BlockEvent::ExportDocument,
         ];
         values
@@ -63,7 +66,7 @@ impl ::std::marker::Copy for BlockEvent {
 
 impl ::std::default::Default for BlockEvent {
     fn default() -> Self {
-        BlockEvent::ApplyDocDelta
+        BlockEvent::GetBlockData
     }
 }
 
@@ -74,8 +77,9 @@ impl ::protobuf::reflect::ProtobufValue for BlockEvent {
 }
 
 static file_descriptor_proto_data: &'static [u8] = b"\
-    \n\x0fevent_map.proto*3\n\nBlockEvent\x12\x11\n\rApplyDocDelta\x10\0\x12\
-    \x12\n\x0eExportDocument\x10\x01b\x06proto3\
+    \n\x0fevent_map.proto*B\n\nBlockEvent\x12\x10\n\x0cGetBlockData\x10\0\
+    \x12\x0e\n\nApplyDelta\x10\x01\x12\x12\n\x0eExportDocument\x10\x02b\x06p\
+    roto3\
 ";
 
 static file_descriptor_proto_lazy: ::protobuf::rt::LazyV2<::protobuf::descriptor::FileDescriptorProto> = ::protobuf::rt::LazyV2::INIT;

+ 3 - 2
frontend/rust-lib/flowy-block/src/protobuf/proto/event_map.proto

@@ -1,6 +1,7 @@
 syntax = "proto3";
 
 enum BlockEvent {
-    ApplyDocDelta = 0;
-    ExportDocument = 1;
+    GetBlockData = 0;
+    ApplyDelta = 1;
+    ExportDocument = 2;
 }

+ 3 - 3
frontend/rust-lib/flowy-folder/src/event_map.rs

@@ -63,7 +63,7 @@ pub fn create(folder: Arc<FolderManager>) -> Module {
         .event(FolderEvent::UpdateView, update_view_handler)
         .event(FolderEvent::DeleteView, delete_view_handler)
         .event(FolderEvent::DuplicateView, duplicate_view_handler)
-        .event(FolderEvent::OpenView, open_view_handler)
+        .event(FolderEvent::SetLatestView, set_latest_view_handler)
         .event(FolderEvent::CloseView, close_view_handler);
 
     module = module
@@ -127,8 +127,8 @@ pub enum FolderEvent {
     #[event()]
     CopyLink = 206,
 
-    #[event(input = "ViewId", output = "BlockDelta")]
-    OpenView = 207,
+    #[event(input = "ViewId")]
+    SetLatestView = 207,
 
     #[event(input = "ViewId")]
     CloseView = 208,

+ 2 - 2
frontend/rust-lib/flowy-folder/src/manager.rs

@@ -206,9 +206,9 @@ impl DefaultFolderBuilder {
                 } else {
                     initial_quill_delta_string()
                 };
-                view_controller.set_latest_view(view);
+                let _ = view_controller.set_latest_view(&view.id);
                 let _ = view_controller
-                    .create_view(&view.id, ViewDataType::RichText, Bytes::from(view_data))
+                    .create_view(&view.id, ViewDataType::Block, Bytes::from(view_data))
                     .await?;
             }
         }

+ 10 - 10
frontend/rust-lib/flowy-folder/src/protobuf/model/event_map.rs

@@ -41,7 +41,7 @@ pub enum FolderEvent {
     DeleteView = 204,
     DuplicateView = 205,
     CopyLink = 206,
-    OpenView = 207,
+    SetLatestView = 207,
     CloseView = 208,
     ReadTrash = 300,
     PutbackTrash = 301,
@@ -75,7 +75,7 @@ impl ::protobuf::ProtobufEnum for FolderEvent {
             204 => ::std::option::Option::Some(FolderEvent::DeleteView),
             205 => ::std::option::Option::Some(FolderEvent::DuplicateView),
             206 => ::std::option::Option::Some(FolderEvent::CopyLink),
-            207 => ::std::option::Option::Some(FolderEvent::OpenView),
+            207 => ::std::option::Option::Some(FolderEvent::SetLatestView),
             208 => ::std::option::Option::Some(FolderEvent::CloseView),
             300 => ::std::option::Option::Some(FolderEvent::ReadTrash),
             301 => ::std::option::Option::Some(FolderEvent::PutbackTrash),
@@ -106,7 +106,7 @@ impl ::protobuf::ProtobufEnum for FolderEvent {
             FolderEvent::DeleteView,
             FolderEvent::DuplicateView,
             FolderEvent::CopyLink,
-            FolderEvent::OpenView,
+            FolderEvent::SetLatestView,
             FolderEvent::CloseView,
             FolderEvent::ReadTrash,
             FolderEvent::PutbackTrash,
@@ -143,19 +143,19 @@ impl ::protobuf::reflect::ProtobufValue for FolderEvent {
 }
 
 static file_descriptor_proto_data: &'static [u8] = b"\
-    \n\x0fevent_map.proto*\xd2\x03\n\x0bFolderEvent\x12\x13\n\x0fCreateWorks\
+    \n\x0fevent_map.proto*\xd7\x03\n\x0bFolderEvent\x12\x13\n\x0fCreateWorks\
     pace\x10\0\x12\x14\n\x10ReadCurWorkspace\x10\x01\x12\x12\n\x0eReadWorksp\
     aces\x10\x02\x12\x13\n\x0fDeleteWorkspace\x10\x03\x12\x11\n\rOpenWorkspa\
     ce\x10\x04\x12\x15\n\x11ReadWorkspaceApps\x10\x05\x12\r\n\tCreateApp\x10\
     e\x12\r\n\tDeleteApp\x10f\x12\x0b\n\x07ReadApp\x10g\x12\r\n\tUpdateApp\
     \x10h\x12\x0f\n\nCreateView\x10\xc9\x01\x12\r\n\x08ReadView\x10\xca\x01\
     \x12\x0f\n\nUpdateView\x10\xcb\x01\x12\x0f\n\nDeleteView\x10\xcc\x01\x12\
-    \x12\n\rDuplicateView\x10\xcd\x01\x12\r\n\x08CopyLink\x10\xce\x01\x12\r\
-    \n\x08OpenView\x10\xcf\x01\x12\x0e\n\tCloseView\x10\xd0\x01\x12\x0e\n\tR\
-    eadTrash\x10\xac\x02\x12\x11\n\x0cPutbackTrash\x10\xad\x02\x12\x10\n\x0b\
-    DeleteTrash\x10\xae\x02\x12\x14\n\x0fRestoreAllTrash\x10\xaf\x02\x12\x13\
-    \n\x0eDeleteAllTrash\x10\xb0\x02\x12\x12\n\rApplyDocDelta\x10\x90\x03\
-    \x12\x13\n\x0eExportDocument\x10\xf4\x03b\x06proto3\
+    \x12\n\rDuplicateView\x10\xcd\x01\x12\r\n\x08CopyLink\x10\xce\x01\x12\
+    \x12\n\rSetLatestView\x10\xcf\x01\x12\x0e\n\tCloseView\x10\xd0\x01\x12\
+    \x0e\n\tReadTrash\x10\xac\x02\x12\x11\n\x0cPutbackTrash\x10\xad\x02\x12\
+    \x10\n\x0bDeleteTrash\x10\xae\x02\x12\x14\n\x0fRestoreAllTrash\x10\xaf\
+    \x02\x12\x13\n\x0eDeleteAllTrash\x10\xb0\x02\x12\x12\n\rApplyDocDelta\
+    \x10\x90\x03\x12\x13\n\x0eExportDocument\x10\xf4\x03b\x06proto3\
 ";
 
 static file_descriptor_proto_lazy: ::protobuf::rt::LazyV2<::protobuf::descriptor::FileDescriptorProto> = ::protobuf::rt::LazyV2::INIT;

+ 1 - 1
frontend/rust-lib/flowy-folder/src/protobuf/proto/event_map.proto

@@ -17,7 +17,7 @@ enum FolderEvent {
     DeleteView = 204;
     DuplicateView = 205;
     CopyLink = 206;
-    OpenView = 207;
+    SetLatestView = 207;
     CloseView = 208;
     ReadTrash = 300;
     PutbackTrash = 301;

+ 9 - 13
frontend/rust-lib/flowy-folder/src/services/persistence/version_1/view_sql.rs

@@ -84,8 +84,7 @@ pub(crate) struct ViewTable {
 impl ViewTable {
     pub fn new(view: View) -> Self {
         let data_type = match view.data_type {
-            ViewDataType::RichText => SqlViewDataType::RichText,
-            ViewDataType::PlainText => SqlViewDataType::PlainText,
+            ViewDataType::Block => SqlViewDataType::Block,
             ViewDataType::Grid => SqlViewDataType::Grid,
         };
 
@@ -107,8 +106,7 @@ impl ViewTable {
 impl std::convert::From<ViewTable> for View {
     fn from(table: ViewTable) -> Self {
         let data_type = match table.view_type {
-            SqlViewDataType::RichText => ViewDataType::RichText,
-            SqlViewDataType::PlainText => ViewDataType::PlainText,
+            SqlViewDataType::Block => ViewDataType::Block,
             SqlViewDataType::Grid => ViewDataType::Grid,
         };
 
@@ -179,26 +177,24 @@ impl ViewChangeset {
 #[repr(i32)]
 #[sql_type = "Integer"]
 pub enum SqlViewDataType {
-    RichText = 0,
-    PlainText = 1,
-    Grid = 2,
+    Block = 0,
+    Grid = 1,
 }
 
 impl std::default::Default for SqlViewDataType {
     fn default() -> Self {
-        SqlViewDataType::RichText
+        SqlViewDataType::Block
     }
 }
 
 impl std::convert::From<i32> for SqlViewDataType {
     fn from(value: i32) -> Self {
         match value {
-            0 => SqlViewDataType::RichText,
-            1 => SqlViewDataType::PlainText,
-            2 => SqlViewDataType::Grid,
+            0 => SqlViewDataType::Block,
+            1 => SqlViewDataType::Grid,
             o => {
-                log::error!("Unsupported view type {}, fallback to ViewType::Docs", o);
-                SqlViewDataType::PlainText
+                log::error!("Unsupported view type {}, fallback to ViewType::Block", o);
+                SqlViewDataType::Block
             }
         }
     }

+ 3 - 12
frontend/rust-lib/flowy-folder/src/services/view/controller.rs

@@ -14,7 +14,7 @@ use crate::{
 };
 use bytes::Bytes;
 use flowy_collaboration::entities::{
-    document_info::{BlockDelta, BlockId},
+    document_info::BlockId,
     revision::{RepeatedRevision, Revision},
 };
 use flowy_database::kv::KV;
@@ -134,14 +134,9 @@ impl ViewController {
     }
 
     #[tracing::instrument(level = "debug", skip(self), err)]
-    pub(crate) async fn open_view(&self, view_id: &str) -> Result<BlockDelta, FlowyError> {
-        let processor = self.get_data_processor_from_view_id(view_id).await?;
-        let delta_str = processor.delta_str(view_id).await?;
+    pub(crate) fn set_latest_view(&self, view_id: &str) -> Result<(), FlowyError> {
         KV::set_str(LATEST_VIEW_ID, view_id.to_owned());
-        Ok(BlockDelta {
-            block_id: view_id.to_string(),
-            delta_str,
-        })
+        Ok(())
     }
 
     #[tracing::instrument(level = "debug", skip(self), err)]
@@ -231,10 +226,6 @@ impl ViewController {
             }
         }
     }
-
-    pub(crate) fn set_latest_view(&self, view: &View) {
-        KV::set_str(LATEST_VIEW_ID, view.id.clone());
-    }
 }
 
 impl ViewController {

+ 4 - 5
frontend/rust-lib/flowy-folder/src/services/view/event_handler.rs

@@ -8,7 +8,6 @@ use crate::{
     errors::FlowyError,
     services::{TrashController, ViewController},
 };
-use flowy_collaboration::entities::document_info::BlockDelta;
 use lib_dispatch::prelude::{data_result, AppData, Data, DataResult};
 use std::{convert::TryInto, sync::Arc};
 
@@ -66,13 +65,13 @@ pub(crate) async fn delete_view_handler(
     Ok(())
 }
 
-pub(crate) async fn open_view_handler(
+pub(crate) async fn set_latest_view_handler(
     data: Data<ViewId>,
     controller: AppData<Arc<ViewController>>,
-) -> DataResult<BlockDelta, FlowyError> {
+) -> Result<(), FlowyError> {
     let view_id: ViewId = data.into_inner();
-    let doc = controller.open_view(&view_id.value).await?;
-    data_result(doc)
+    let _ = controller.set_latest_view(&view_id.value)?;
+    Ok(())
 }
 
 pub(crate) async fn close_view_handler(

+ 1 - 1
frontend/rust-lib/flowy-folder/tests/workspace/helper.rs

@@ -164,7 +164,7 @@ pub async fn delete_view(sdk: &FlowySDKTest, view_ids: Vec<String>) {
 pub async fn open_document(sdk: &FlowySDKTest, view_id: &str) -> BlockInfo {
     let view_id: ViewId = view_id.into();
     FolderEventBuilder::new(sdk.clone())
-        .event(OpenView)
+        .event(SetLatestView)
         .payload(view_id)
         .async_send()
         .await

+ 2 - 2
frontend/rust-lib/flowy-folder/tests/workspace/script.rs

@@ -68,7 +68,7 @@ impl FolderTest {
         let _ = sdk.init_user().await;
         let mut workspace = create_workspace(&sdk, "FolderWorkspace", "Folder test workspace").await;
         let mut app = create_app(&sdk, &workspace.id, "Folder App", "Folder test app").await;
-        let view = create_view(&sdk, &app.id, "Folder View", "Folder test view", ViewDataType::RichText).await;
+        let view = create_view(&sdk, &app.id, "Folder View", "Folder test view", ViewDataType::Block).await;
         app.belongings = RepeatedView {
             items: vec![view.clone()],
         };
@@ -146,7 +146,7 @@ impl FolderTest {
             }
 
             FolderScript::CreateView { name, desc } => {
-                let view = create_view(sdk, &self.app.id, &name, &desc, ViewDataType::RichText).await;
+                let view = create_view(sdk, &self.app.id, &name, &desc, ViewDataType::Block).await;
                 self.view = view;
             }
             FolderScript::AssertView(view) => {

+ 1 - 1
frontend/rust-lib/flowy-grid/src/event_handler.rs

@@ -5,7 +5,7 @@ use lib_dispatch::prelude::{data_result, AppData, Data, DataResult};
 use std::sync::Arc;
 
 #[tracing::instrument(level = "debug", skip(data, manager), err)]
-pub(crate) async fn open_grid_handler(
+pub(crate) async fn get_grid_data_handler(
     data: Data<GridId>,
     manager: AppData<Arc<GridManager>>,
 ) -> DataResult<Grid, FlowyError> {

+ 2 - 2
frontend/rust-lib/flowy-grid/src/event_map.rs

@@ -8,7 +8,7 @@ use strum_macros::Display;
 pub fn create(grid_manager: Arc<GridManager>) -> Module {
     let mut module = Module::new().name(env!("CARGO_PKG_NAME")).data(grid_manager);
     module = module
-        .event(GridEvent::OpenGrid, open_grid_handler)
+        .event(GridEvent::GetGridData, get_grid_data_handler)
         .event(GridEvent::GetRows, get_rows_handler)
         .event(GridEvent::GetFields, get_fields_handler)
         .event(GridEvent::CreateRow, create_row_handler);
@@ -20,7 +20,7 @@ pub fn create(grid_manager: Arc<GridManager>) -> Module {
 #[event_err = "FlowyError"]
 pub enum GridEvent {
     #[event(input = "GridId", output = "Grid")]
-    OpenGrid = 0,
+    GetGridData = 0,
 
     #[event(input = "QueryRowPayload", output = "RepeatedRow")]
     GetRows = 1,

+ 1 - 1
frontend/rust-lib/flowy-grid/src/lib.rs

@@ -6,4 +6,4 @@ pub mod event_map;
 pub mod manager;
 
 mod protobuf;
-mod services;
+pub mod services;

+ 16 - 55
frontend/rust-lib/flowy-grid/src/manager.rs

@@ -1,11 +1,12 @@
 use crate::services::grid_editor::ClientGridEditor;
-use crate::services::kv_persistence::GridKVPersistence;
+use crate::services::kv_persistence::{GridKVPersistence, KVTransaction};
 use dashmap::DashMap;
-use flowy_collaboration::client_grid::make_grid_delta;
+
 use flowy_collaboration::entities::revision::RepeatedRevision;
 use flowy_error::{FlowyError, FlowyResult};
-use flowy_grid_data_model::entities::{Field, FieldOrder, FieldType, Grid, RawRow, RowOrder};
+use flowy_grid_data_model::entities::{Field, RawRow};
 use flowy_sync::{RevisionManager, RevisionPersistence, RevisionWebSocket};
+
 use lib_sqlite::ConnectionPool;
 use parking_lot::RwLock;
 use std::sync::Arc;
@@ -76,6 +77,18 @@ impl GridManager {
         }
     }
 
+    pub fn save_rows(&self, rows: Vec<RawRow>) -> FlowyResult<()> {
+        let kv_persistence = self.get_kv_persistence()?;
+        let _ = kv_persistence.batch_set(rows)?;
+        Ok(())
+    }
+
+    pub fn save_fields(&self, fields: Vec<Field>) -> FlowyResult<()> {
+        let kv_persistence = self.get_kv_persistence()?;
+        let _ = kv_persistence.batch_set(fields)?;
+        Ok(())
+    }
+
     async fn get_or_create_grid_editor(&self, grid_id: &str) -> FlowyResult<Arc<ClientGridEditor>> {
         match self.editor_map.get(grid_id) {
             None => {
@@ -122,58 +135,6 @@ impl GridManager {
     }
 }
 
-use lib_infra::uuid;
-pub fn default_grid(grid_id: &str) -> String {
-    let fields = vec![
-        Field {
-            id: uuid(),
-            name: "".to_string(),
-            desc: "".to_string(),
-            field_type: FieldType::RichText,
-            frozen: false,
-            width: 100,
-            type_options: Default::default(),
-        },
-        Field {
-            id: uuid(),
-            name: "".to_string(),
-            desc: "".to_string(),
-            field_type: FieldType::RichText,
-            frozen: false,
-            width: 100,
-            type_options: Default::default(),
-        },
-    ];
-
-    let rows = vec![
-        RawRow {
-            id: uuid(),
-            grid_id: grid_id.to_string(),
-            cell_by_field_id: Default::default(),
-        },
-        RawRow {
-            id: uuid(),
-            grid_id: grid_id.to_string(),
-            cell_by_field_id: Default::default(),
-        },
-    ];
-
-    make_grid(&grid_id, fields, rows)
-}
-
-pub fn make_grid(grid_id: &str, fields: Vec<Field>, rows: Vec<RawRow>) -> String {
-    let field_orders = fields.iter().map(FieldOrder::from).collect::<Vec<_>>();
-    let row_orders = rows.iter().map(RowOrder::from).collect::<Vec<_>>();
-
-    let grid = Grid {
-        id: grid_id.to_owned(),
-        field_orders: field_orders.into(),
-        row_orders: row_orders.into(),
-    };
-    let delta = make_grid_delta(&grid);
-    delta.to_delta_str()
-}
-
 pub struct GridEditorMap {
     inner: DashMap<String, Arc<ClientGridEditor>>,
 }

+ 7 - 7
frontend/rust-lib/flowy-grid/src/protobuf/model/event_map.rs

@@ -25,7 +25,7 @@
 
 #[derive(Clone,PartialEq,Eq,Debug,Hash)]
 pub enum GridEvent {
-    OpenGrid = 0,
+    GetGridData = 0,
     GetRows = 1,
     GetFields = 2,
     CreateRow = 3,
@@ -38,7 +38,7 @@ impl ::protobuf::ProtobufEnum for GridEvent {
 
     fn from_i32(value: i32) -> ::std::option::Option<GridEvent> {
         match value {
-            0 => ::std::option::Option::Some(GridEvent::OpenGrid),
+            0 => ::std::option::Option::Some(GridEvent::GetGridData),
             1 => ::std::option::Option::Some(GridEvent::GetRows),
             2 => ::std::option::Option::Some(GridEvent::GetFields),
             3 => ::std::option::Option::Some(GridEvent::CreateRow),
@@ -48,7 +48,7 @@ impl ::protobuf::ProtobufEnum for GridEvent {
 
     fn values() -> &'static [Self] {
         static values: &'static [GridEvent] = &[
-            GridEvent::OpenGrid,
+            GridEvent::GetGridData,
             GridEvent::GetRows,
             GridEvent::GetFields,
             GridEvent::CreateRow,
@@ -69,7 +69,7 @@ impl ::std::marker::Copy for GridEvent {
 
 impl ::std::default::Default for GridEvent {
     fn default() -> Self {
-        GridEvent::OpenGrid
+        GridEvent::GetGridData
     }
 }
 
@@ -80,9 +80,9 @@ impl ::protobuf::reflect::ProtobufValue for GridEvent {
 }
 
 static file_descriptor_proto_data: &'static [u8] = b"\
-    \n\x0fevent_map.proto*D\n\tGridEvent\x12\x0c\n\x08OpenGrid\x10\0\x12\x0b\
-    \n\x07GetRows\x10\x01\x12\r\n\tGetFields\x10\x02\x12\r\n\tCreateRow\x10\
-    \x03b\x06proto3\
+    \n\x0fevent_map.proto*G\n\tGridEvent\x12\x0f\n\x0bGetGridData\x10\0\x12\
+    \x0b\n\x07GetRows\x10\x01\x12\r\n\tGetFields\x10\x02\x12\r\n\tCreateRow\
+    \x10\x03b\x06proto3\
 ";
 
 static file_descriptor_proto_lazy: ::protobuf::rt::LazyV2<::protobuf::descriptor::FileDescriptorProto> = ::protobuf::rt::LazyV2::INIT;

+ 1 - 1
frontend/rust-lib/flowy-grid/src/protobuf/proto/event_map.proto

@@ -1,7 +1,7 @@
 syntax = "proto3";
 
 enum GridEvent {
-    OpenGrid = 0;
+    GetGridData = 0;
     GetRows = 1;
     GetFields = 2;
     CreateRow = 3;

+ 2 - 2
frontend/rust-lib/flowy-grid/src/services/cell_data.rs

@@ -414,7 +414,7 @@ impl std::default::Default for FlowyMoney {
 
 impl FlowyMoney {
     // Currency list https://docs.rs/rusty-money/0.4.0/rusty_money/iso/index.html
-    pub fn from_str(s: &str) -> FlowyMoney {
+    pub fn from_symbol_str(s: &str) -> FlowyMoney {
         match s {
             "CNY" => FlowyMoney::CNY,
             "EUR" => FlowyMoney::EUR,
@@ -424,7 +424,7 @@ impl FlowyMoney {
     }
 
     pub fn from_money(money: &rusty_money::Money<Currency>) -> FlowyMoney {
-        FlowyMoney::from_str(&money.currency().symbol.to_string())
+        FlowyMoney::from_symbol_str(&money.currency().symbol.to_string())
     }
 
     pub fn currency(&self) -> &'static Currency {

+ 106 - 0
frontend/rust-lib/flowy-grid/src/services/grid_builder.rs

@@ -0,0 +1,106 @@
+use crate::manager::GridManager;
+use flowy_collaboration::client_grid::make_grid_delta;
+use flowy_error::{FlowyError, FlowyResult};
+use flowy_grid_data_model::entities::{Field, FieldOrder, FieldType, Grid, RawCell, RawRow, RowOrder};
+use lib_infra::uuid;
+use std::collections::HashMap;
+use std::sync::Arc;
+
+pub struct GridBuilder {
+    grid_manager: Arc<GridManager>,
+    grid_id: String,
+    fields: Vec<Field>,
+    rows: Vec<RawRow>,
+}
+
+impl GridBuilder {
+    pub fn new(grid_id: &str, grid_manager: Arc<GridManager>) -> Self {
+        Self {
+            grid_manager,
+            grid_id: grid_id.to_owned(),
+            fields: vec![],
+            rows: vec![],
+        }
+    }
+
+    pub fn add_field(mut self, name: &str, desc: &str, field_type: FieldType) -> Self {
+        let field = Field {
+            id: uuid(),
+            name: name.to_string(),
+            desc: desc.to_string(),
+            field_type,
+            frozen: false,
+            width: 100,
+            type_options: Default::default(),
+        };
+        self.fields.push(field);
+        self
+    }
+
+    pub fn add_empty_row(mut self) -> Self {
+        let row = RawRow {
+            id: uuid(),
+            grid_id: self.grid_id.clone(),
+            cell_by_field_id: Default::default(),
+        };
+        self.rows.push(row);
+        self
+    }
+
+    pub fn add_row(mut self, cells: Vec<RawCell>) -> Self {
+        let cell_by_field_id = cells
+            .into_iter()
+            .map(|cell| (cell.id.clone(), cell))
+            .collect::<HashMap<String, RawCell>>();
+
+        let row = RawRow {
+            id: uuid(),
+            grid_id: self.grid_id.clone(),
+            cell_by_field_id,
+        };
+        self.rows.push(row);
+        self
+    }
+
+    pub fn build(self) -> FlowyResult<String> {
+        let field_orders = self.fields.iter().map(FieldOrder::from).collect::<Vec<FieldOrder>>();
+
+        let row_orders = self.rows.iter().map(RowOrder::from).collect::<Vec<RowOrder>>();
+
+        let grid = Grid {
+            id: self.grid_id,
+            field_orders: field_orders.into(),
+            row_orders: row_orders.into(),
+        };
+
+        // let _ = check_rows(&self.fields, &self.rows)?;
+        let _ = self.grid_manager.save_rows(self.rows)?;
+        let _ = self.grid_manager.save_fields(self.fields)?;
+
+        let delta = make_grid_delta(&grid);
+        Ok(delta.to_delta_str())
+    }
+}
+
+#[allow(dead_code)]
+fn check_rows(fields: &[Field], rows: &[RawRow]) -> FlowyResult<()> {
+    let field_ids = fields.iter().map(|field| &field.id).collect::<Vec<&String>>();
+    for row in rows {
+        let cell_field_ids = row.cell_by_field_id.keys().into_iter().collect::<Vec<&String>>();
+        if cell_field_ids != field_ids {
+            let msg = format!("{:?} contains invalid cells", row);
+            return Err(FlowyError::internal().context(msg));
+        }
+    }
+    Ok(())
+}
+
+pub fn make_default_grid(grid_id: &str, grid_manager: Arc<GridManager>) -> String {
+    GridBuilder::new(grid_id, grid_manager)
+        .add_field("Name", "", FieldType::RichText)
+        .add_field("Tags", "", FieldType::SingleSelect)
+        .add_empty_row()
+        .add_empty_row()
+        .build()
+        .unwrap()
+}

+ 1 - 0
frontend/rust-lib/flowy-grid/src/services/mod.rs

@@ -1,6 +1,7 @@
 mod util;
 
 pub mod cell_data;
+pub mod grid_builder;
 pub mod grid_editor;
 pub mod kv_persistence;
 pub mod stringify;

+ 1 - 1
frontend/rust-lib/flowy-grid/src/services/util.rs

@@ -25,7 +25,7 @@ fn generate_currency_by_symbol() -> HashMap<String, &'static Currency> {
 #[allow(dead_code)]
 pub fn string_to_money(money_str: &str) -> Option<Money<Currency>> {
     let mut process_money_str = String::from(money_str);
-    let default_currency = FlowyMoney::from_str("CNY").currency();
+    let default_currency = FlowyMoney::from_symbol_str("CNY").currency();
 
     if process_money_str.is_empty() {
         return None;

+ 4 - 3
frontend/rust-lib/flowy-sdk/src/deps_resolve/folder_deps.rs

@@ -11,7 +11,8 @@ use flowy_folder::{
     event_map::{FolderCouldServiceV1, WorkspaceDatabase, WorkspaceUser},
     manager::FolderManager,
 };
-use flowy_grid::manager::{default_grid, GridManager};
+use flowy_grid::manager::GridManager;
+use flowy_grid::services::grid_builder::make_default_grid;
 use flowy_net::ClientServerConfiguration;
 use flowy_net::{
     http_server::folder::FolderHttpCloudService, local_server::LocalServer, ws::connection::FlowyWebSocketConnect,
@@ -178,7 +179,7 @@ impl ViewDataProcessor for BlockManagerViewDataImpl {
     }
 
     fn data_type(&self) -> ViewDataType {
-        ViewDataType::RichText
+        ViewDataType::Block
     }
 }
 
@@ -226,7 +227,7 @@ impl ViewDataProcessor for GridManagerViewDataImpl {
     }
 
     fn default_view_data(&self, view_id: &str) -> String {
-        default_grid(view_id)
+        make_default_grid(view_id, self.0.clone())
     }
 
     fn data_type(&self) -> ViewDataType {

+ 1 - 1
frontend/rust-lib/flowy-test/src/helper.rs

@@ -88,7 +88,7 @@ async fn create_view(sdk: &FlowySDKTest, app_id: &str) -> View {
         name: "View A".to_string(),
         desc: "".to_string(),
         thumbnail: Some("http://1.png".to_string()),
-        data_type: ViewDataType::RichText,
+        data_type: ViewDataType::Block,
         ext_data: "".to_string(),
         plugin_type: 0,
     };

+ 13 - 4
shared-lib/flowy-collaboration/src/entities/document_info.rs

@@ -92,6 +92,11 @@ pub struct BlockId {
     #[pb(index = 1)]
     pub value: String,
 }
+impl AsRef<str> for BlockId {
+    fn as_ref(&self) -> &str {
+        &self.value
+    }
+}
 
 impl std::convert::From<String> for BlockId {
     fn from(value: String) -> Self {
@@ -99,10 +104,14 @@ impl std::convert::From<String> for BlockId {
     }
 }
 
+impl std::convert::From<BlockId> for String {
+    fn from(block_id: BlockId) -> Self {
+        block_id.value
+    }
+}
+
 impl std::convert::From<&String> for BlockId {
-    fn from(doc_id: &String) -> Self {
-        BlockId {
-            value: doc_id.to_owned(),
-        }
+    fn from(s: &String) -> Self {
+        BlockId { value: s.to_owned() }
     }
 }

+ 6 - 8
shared-lib/flowy-folder-data-model/src/entities/view.rs

@@ -83,26 +83,24 @@ impl std::convert::From<View> for Trash {
 #[derive(Eq, PartialEq, Hash, Debug, ProtoBuf_Enum, Clone, Serialize_repr, Deserialize_repr)]
 #[repr(u8)]
 pub enum ViewDataType {
-    RichText = 0,
-    PlainText = 1,
-    Grid = 2,
+    Block = 0,
+    Grid = 1,
 }
 
 impl std::default::Default for ViewDataType {
     fn default() -> Self {
-        ViewDataType::RichText
+        ViewDataType::Block
     }
 }
 
 impl std::convert::From<i32> for ViewDataType {
     fn from(val: i32) -> Self {
         match val {
-            0 => ViewDataType::RichText,
-            1 => ViewDataType::PlainText,
-            2 => ViewDataType::Grid,
+            0 => ViewDataType::Block,
+            1 => ViewDataType::Grid,
             _ => {
                 log::error!("Invalid view type: {}", val);
-                ViewDataType::PlainText
+                ViewDataType::Block
             }
         }
     }

+ 20 - 24
shared-lib/flowy-folder-data-model/src/protobuf/model/view.rs

@@ -165,7 +165,7 @@ impl View {
         self.data_type
     }
     pub fn clear_data_type(&mut self) {
-        self.data_type = ViewDataType::RichText;
+        self.data_type = ViewDataType::Block;
     }
 
     // Param is passed by value, moved
@@ -409,7 +409,7 @@ impl ::protobuf::Message for View {
         if !self.desc.is_empty() {
             my_size += ::protobuf::rt::string_size(4, &self.desc);
         }
-        if self.data_type != ViewDataType::RichText {
+        if self.data_type != ViewDataType::Block {
             my_size += ::protobuf::rt::enum_size(5, self.data_type);
         }
         if self.version != 0 {
@@ -452,7 +452,7 @@ impl ::protobuf::Message for View {
         if !self.desc.is_empty() {
             os.write_string(4, &self.desc)?;
         }
-        if self.data_type != ViewDataType::RichText {
+        if self.data_type != ViewDataType::Block {
             os.write_enum(5, ::protobuf::ProtobufEnum::value(&self.data_type))?;
         }
         if self.version != 0 {
@@ -596,7 +596,7 @@ impl ::protobuf::Clear for View {
         self.belong_to_id.clear();
         self.name.clear();
         self.desc.clear();
-        self.data_type = ViewDataType::RichText;
+        self.data_type = ViewDataType::Block;
         self.version = 0;
         self.belongings.clear();
         self.modified_time = 0;
@@ -952,7 +952,7 @@ impl CreateViewPayload {
         self.data_type
     }
     pub fn clear_data_type(&mut self) {
-        self.data_type = ViewDataType::RichText;
+        self.data_type = ViewDataType::Block;
     }
 
     // Param is passed by value, moved
@@ -1060,7 +1060,7 @@ impl ::protobuf::Message for CreateViewPayload {
         if !self.desc.is_empty() {
             my_size += ::protobuf::rt::string_size(3, &self.desc);
         }
-        if self.data_type != ViewDataType::RichText {
+        if self.data_type != ViewDataType::Block {
             my_size += ::protobuf::rt::enum_size(5, self.data_type);
         }
         if !self.ext_data.is_empty() {
@@ -1091,7 +1091,7 @@ impl ::protobuf::Message for CreateViewPayload {
         if !self.desc.is_empty() {
             os.write_string(3, &self.desc)?;
         }
-        if self.data_type != ViewDataType::RichText {
+        if self.data_type != ViewDataType::Block {
             os.write_enum(5, ::protobuf::ProtobufEnum::value(&self.data_type))?;
         }
         if !self.ext_data.is_empty() {
@@ -1200,7 +1200,7 @@ impl ::protobuf::Clear for CreateViewPayload {
         self.name.clear();
         self.desc.clear();
         self.one_of_thumbnail = ::std::option::Option::None;
-        self.data_type = ViewDataType::RichText;
+        self.data_type = ViewDataType::Block;
         self.ext_data.clear();
         self.plugin_type = 0;
         self.unknown_fields.clear();
@@ -1358,7 +1358,7 @@ impl CreateViewParams {
         self.data_type
     }
     pub fn clear_data_type(&mut self) {
-        self.data_type = ViewDataType::RichText;
+        self.data_type = ViewDataType::Block;
     }
 
     // Param is passed by value, moved
@@ -1524,7 +1524,7 @@ impl ::protobuf::Message for CreateViewParams {
         if !self.thumbnail.is_empty() {
             my_size += ::protobuf::rt::string_size(4, &self.thumbnail);
         }
-        if self.data_type != ViewDataType::RichText {
+        if self.data_type != ViewDataType::Block {
             my_size += ::protobuf::rt::enum_size(5, self.data_type);
         }
         if !self.ext_data.is_empty() {
@@ -1557,7 +1557,7 @@ impl ::protobuf::Message for CreateViewParams {
         if !self.thumbnail.is_empty() {
             os.write_string(4, &self.thumbnail)?;
         }
-        if self.data_type != ViewDataType::RichText {
+        if self.data_type != ViewDataType::Block {
             os.write_enum(5, ::protobuf::ProtobufEnum::value(&self.data_type))?;
         }
         if !self.ext_data.is_empty() {
@@ -1675,7 +1675,7 @@ impl ::protobuf::Clear for CreateViewParams {
         self.name.clear();
         self.desc.clear();
         self.thumbnail.clear();
-        self.data_type = ViewDataType::RichText;
+        self.data_type = ViewDataType::Block;
         self.ext_data.clear();
         self.view_id.clear();
         self.data.clear();
@@ -2821,9 +2821,8 @@ impl ::protobuf::reflect::ProtobufValue for UpdateViewParams {
 
 #[derive(Clone,PartialEq,Eq,Debug,Hash)]
 pub enum ViewDataType {
-    RichText = 0,
-    PlainText = 1,
-    Grid = 2,
+    Block = 0,
+    Grid = 1,
 }
 
 impl ::protobuf::ProtobufEnum for ViewDataType {
@@ -2833,17 +2832,15 @@ impl ::protobuf::ProtobufEnum for ViewDataType {
 
     fn from_i32(value: i32) -> ::std::option::Option<ViewDataType> {
         match value {
-            0 => ::std::option::Option::Some(ViewDataType::RichText),
-            1 => ::std::option::Option::Some(ViewDataType::PlainText),
-            2 => ::std::option::Option::Some(ViewDataType::Grid),
+            0 => ::std::option::Option::Some(ViewDataType::Block),
+            1 => ::std::option::Option::Some(ViewDataType::Grid),
             _ => ::std::option::Option::None
         }
     }
 
     fn values() -> &'static [Self] {
         static values: &'static [ViewDataType] = &[
-            ViewDataType::RichText,
-            ViewDataType::PlainText,
+            ViewDataType::Block,
             ViewDataType::Grid,
         ];
         values
@@ -2862,7 +2859,7 @@ impl ::std::marker::Copy for ViewDataType {
 
 impl ::std::default::Default for ViewDataType {
     fn default() -> Self {
-        ViewDataType::RichText
+        ViewDataType::Block
     }
 }
 
@@ -2907,9 +2904,8 @@ static file_descriptor_proto_data: &'static [u8] = b"\
     \x17\n\x07view_id\x18\x01\x20\x01(\tR\x06viewId\x12\x14\n\x04name\x18\
     \x02\x20\x01(\tH\0R\x04name\x12\x14\n\x04desc\x18\x03\x20\x01(\tH\x01R\
     \x04desc\x12\x1e\n\tthumbnail\x18\x04\x20\x01(\tH\x02R\tthumbnailB\r\n\
-    \x0bone_of_nameB\r\n\x0bone_of_descB\x12\n\x10one_of_thumbnail*5\n\x0cVi\
-    ewDataType\x12\x0c\n\x08RichText\x10\0\x12\r\n\tPlainText\x10\x01\x12\
-    \x08\n\x04Grid\x10\x02b\x06proto3\
+    \x0bone_of_nameB\r\n\x0bone_of_descB\x12\n\x10one_of_thumbnail*#\n\x0cVi\
+    ewDataType\x12\t\n\x05Block\x10\0\x12\x08\n\x04Grid\x10\x01b\x06proto3\
 ";
 
 static file_descriptor_proto_lazy: ::protobuf::rt::LazyV2<::protobuf::descriptor::FileDescriptorProto> = ::protobuf::rt::LazyV2::INIT;

+ 2 - 3
shared-lib/flowy-folder-data-model/src/protobuf/proto/view.proto

@@ -56,7 +56,6 @@ message UpdateViewParams {
     oneof one_of_thumbnail { string thumbnail = 4; };
 }
 enum ViewDataType {
-    RichText = 0;
-    PlainText = 1;
-    Grid = 2;
+    Block = 0;
+    Grid = 1;
 }

+ 1 - 1
shared-lib/flowy-folder-data-model/src/user_default.rs

@@ -49,7 +49,7 @@ fn create_default_view(app_id: String, time: chrono::DateTime<Utc>) -> View {
     let view_id = uuid::Uuid::new_v4();
     let name = "Read me".to_string();
     let desc = "".to_string();
-    let data_type = ViewDataType::RichText;
+    let data_type = ViewDataType::Block;
 
     View {
         id: view_id.to_string(),