views.rs 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127
  1. use std::collections::HashMap;
  2. use std::sync::Arc;
  3. use collab_database::fields::Field;
  4. use collab_database::rows::{Row, RowId};
  5. use nanoid::nanoid;
  6. use tokio::sync::{broadcast, RwLock};
  7. use flowy_error::FlowyResult;
  8. use lib_infra::future::Fut;
  9. use crate::services::cell::CellCache;
  10. use crate::services::database::{DatabaseRowEvent, MutexDatabase};
  11. use crate::services::database_view::{DatabaseViewData, DatabaseViewEditor};
  12. use crate::services::group::RowChangeset;
  13. pub type RowEventSender = broadcast::Sender<DatabaseRowEvent>;
  14. pub type RowEventReceiver = broadcast::Receiver<DatabaseRowEvent>;
  15. pub struct DatabaseViews {
  16. #[allow(dead_code)]
  17. database: MutexDatabase,
  18. cell_cache: CellCache,
  19. database_view_data: Arc<dyn DatabaseViewData>,
  20. editor_map: Arc<RwLock<HashMap<String, Arc<DatabaseViewEditor>>>>,
  21. }
  22. impl DatabaseViews {
  23. pub async fn new(
  24. database: MutexDatabase,
  25. cell_cache: CellCache,
  26. database_view_data: Arc<dyn DatabaseViewData>,
  27. ) -> FlowyResult<Self> {
  28. let editor_map = Arc::new(RwLock::new(HashMap::default()));
  29. Ok(Self {
  30. database,
  31. database_view_data,
  32. cell_cache,
  33. editor_map,
  34. })
  35. }
  36. pub async fn close_view(&self, view_id: &str) -> bool {
  37. let mut editor_map = self.editor_map.write().await;
  38. if let Some(view) = editor_map.remove(view_id) {
  39. view.close().await;
  40. }
  41. editor_map.is_empty()
  42. }
  43. pub async fn editors(&self) -> Vec<Arc<DatabaseViewEditor>> {
  44. self.editor_map.read().await.values().cloned().collect()
  45. }
  46. /// It may generate a RowChangeset when the Row was moved from one group to another.
  47. /// The return value, [RowChangeset], contains the changes made by the groups.
  48. ///
  49. pub async fn move_group_row(
  50. &self,
  51. view_id: &str,
  52. row: Arc<Row>,
  53. to_group_id: String,
  54. to_row_id: Option<RowId>,
  55. recv_row_changeset: impl FnOnce(RowChangeset) -> Fut<()>,
  56. ) -> FlowyResult<()> {
  57. let view_editor = self.get_view_editor(view_id).await?;
  58. let mut row_changeset = RowChangeset::new(row.id.clone());
  59. view_editor
  60. .v_move_group_row(&row, &mut row_changeset, &to_group_id, to_row_id)
  61. .await;
  62. if !row_changeset.is_empty() {
  63. recv_row_changeset(row_changeset).await;
  64. }
  65. Ok(())
  66. }
  67. /// Notifies the view's field type-option data is changed
  68. /// For the moment, only the groups will be generated after the type-option data changed. A
  69. /// [Field] has a property named type_options contains a list of type-option data.
  70. /// # Arguments
  71. ///
  72. /// * `field_id`: the id of the field in current view
  73. ///
  74. #[tracing::instrument(level = "debug", skip(self, old_field), err)]
  75. pub async fn did_update_field_type_option(
  76. &self,
  77. view_id: &str,
  78. field_id: &str,
  79. old_field: &Field,
  80. ) -> FlowyResult<()> {
  81. let view_editor = self.get_view_editor(view_id).await?;
  82. // If the id of the grouping field is equal to the updated field's id, then we need to
  83. // update the group setting
  84. if view_editor.is_grouping_field(field_id).await {
  85. view_editor.v_update_grouping_field(field_id).await?;
  86. }
  87. view_editor
  88. .v_did_update_field_type_option(field_id, old_field)
  89. .await?;
  90. Ok(())
  91. }
  92. pub async fn get_view_editor(&self, view_id: &str) -> FlowyResult<Arc<DatabaseViewEditor>> {
  93. debug_assert!(!view_id.is_empty());
  94. if let Some(editor) = self.editor_map.read().await.get(view_id) {
  95. return Ok(editor.clone());
  96. }
  97. let mut editor_map = self.editor_map.write().await;
  98. let editor = Arc::new(
  99. DatabaseViewEditor::new(
  100. view_id.to_owned(),
  101. self.database_view_data.clone(),
  102. self.cell_cache.clone(),
  103. )
  104. .await?,
  105. );
  106. editor_map.insert(view_id.to_owned(), editor.clone());
  107. Ok(editor)
  108. }
  109. }
  110. pub fn gen_handler_id() -> String {
  111. nanoid!(10)
  112. }