| 
									
										
										
										
											2023-06-03 23:35:55 +08:00
										 |  |  | use std::time::Duration;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  | use flowy_database2::entities::FieldType;
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  | use flowy_database2::services::field::{
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |   ChecklistCellChangeset, DateCellChangeset, DateCellData, MultiSelectTypeOption,
 | 
					
						
							| 
									
										
										
										
											2024-05-05 22:04:34 +08:00
										 |  |  |   RelationCellChangeset, SelectOptionCellChangeset, SingleSelectTypeOption, StringCellData,
 | 
					
						
							| 
									
										
										
										
											2024-06-13 10:22:13 +03:30
										 |  |  |   TimeCellData, URLCellData,
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  | };
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  | use lib_infra::box_any::BoxAny;
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  | use crate::database::cell_test::script::CellScript::UpdateCell;
 | 
					
						
							|  |  |  | use crate::database::cell_test::script::DatabaseCellTest;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #[tokio::test]
 | 
					
						
							|  |  |  | async fn grid_cell_update() {
 | 
					
						
							|  |  |  |   let mut test = DatabaseCellTest::new().await;
 | 
					
						
							| 
									
										
										
										
											2024-08-18 05:16:42 +02:00
										 |  |  |   let fields = test.get_fields().await;
 | 
					
						
							| 
									
										
										
										
											2024-08-26 09:46:16 +08:00
										 |  |  |   let rows = &test.rows;
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   let mut scripts = vec![];
 | 
					
						
							| 
									
										
										
										
											2024-08-26 09:46:16 +08:00
										 |  |  |   for row in rows.iter() {
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |     for field in &fields {
 | 
					
						
							|  |  |  |       let field_type = FieldType::from(field.field_type);
 | 
					
						
							| 
									
										
										
										
											2023-09-08 10:07:24 +08:00
										 |  |  |       if field_type == FieldType::LastEditedTime || field_type == FieldType::CreatedTime {
 | 
					
						
							|  |  |  |         continue;
 | 
					
						
							|  |  |  |       }
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |       let cell_changeset = match field_type {
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |         FieldType::RichText => BoxAny::new("".to_string()),
 | 
					
						
							|  |  |  |         FieldType::Number => BoxAny::new("123".to_string()),
 | 
					
						
							|  |  |  |         FieldType::DateTime => BoxAny::new(DateCellChangeset {
 | 
					
						
							|  |  |  |           date: Some(123),
 | 
					
						
							|  |  |  |           ..Default::default()
 | 
					
						
							|  |  |  |         }),
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |         FieldType::SingleSelect => {
 | 
					
						
							|  |  |  |           let type_option = field
 | 
					
						
							|  |  |  |             .get_type_option::<SingleSelectTypeOption>(field.field_type)
 | 
					
						
							|  |  |  |             .unwrap();
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |           BoxAny::new(SelectOptionCellChangeset::from_insert_option_id(
 | 
					
						
							|  |  |  |             &type_option.options.first().unwrap().id,
 | 
					
						
							|  |  |  |           ))
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |         },
 | 
					
						
							|  |  |  |         FieldType::MultiSelect => {
 | 
					
						
							|  |  |  |           let type_option = field
 | 
					
						
							|  |  |  |             .get_type_option::<MultiSelectTypeOption>(field.field_type)
 | 
					
						
							|  |  |  |             .unwrap();
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |           BoxAny::new(SelectOptionCellChangeset::from_insert_option_id(
 | 
					
						
							|  |  |  |             &type_option.options.first().unwrap().id,
 | 
					
						
							|  |  |  |           ))
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |         },
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |         FieldType::Checklist => BoxAny::new(ChecklistCellChangeset {
 | 
					
						
							| 
									
										
										
										
											2024-02-22 08:00:59 +08:00
										 |  |  |           insert_options: vec![("new option".to_string(), false)],
 | 
					
						
							| 
									
										
										
										
											2023-05-30 09:41:33 +08:00
										 |  |  |           ..Default::default()
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |         }),
 | 
					
						
							|  |  |  |         FieldType::Checkbox => BoxAny::new("1".to_string()),
 | 
					
						
							|  |  |  |         FieldType::URL => BoxAny::new("1".to_string()),
 | 
					
						
							| 
									
										
										
										
											2024-02-29 14:38:18 +08:00
										 |  |  |         FieldType::Relation => BoxAny::new(RelationCellChangeset {
 | 
					
						
							|  |  |  |           inserted_row_ids: vec!["abcdefabcdef".to_string().into()],
 | 
					
						
							|  |  |  |           ..Default::default()
 | 
					
						
							|  |  |  |         }),
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |         _ => BoxAny::new("".to_string()),
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |       };
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       scripts.push(UpdateCell {
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |         view_id: test.view_id.clone(),
 | 
					
						
							|  |  |  |         field_id: field.id.clone(),
 | 
					
						
							| 
									
										
										
										
											2024-08-26 09:46:16 +08:00
										 |  |  |         row_id: row.id.clone(),
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |         changeset: cell_changeset,
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |         is_err: false,
 | 
					
						
							|  |  |  |       });
 | 
					
						
							|  |  |  |     }
 | 
					
						
							|  |  |  |   }
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   test.run_scripts(scripts).await;
 | 
					
						
							|  |  |  | }
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #[tokio::test]
 | 
					
						
							| 
									
										
										
										
											2023-05-26 14:04:17 +03:30
										 |  |  | async fn text_cell_data_test() {
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |   let test = DatabaseCellTest::new().await;
 | 
					
						
							| 
									
										
										
										
											2024-08-18 05:16:42 +02:00
										 |  |  |   let text_field = test.get_first_field(FieldType::RichText).await;
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   let cells = test
 | 
					
						
							|  |  |  |     .editor
 | 
					
						
							|  |  |  |     .get_cells_for_field(&test.view_id, &text_field.id)
 | 
					
						
							|  |  |  |     .await;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-06-01 20:23:27 +08:00
										 |  |  |   for (i, row_cell) in cells.into_iter().enumerate() {
 | 
					
						
							| 
									
										
										
										
											2024-05-05 22:04:34 +08:00
										 |  |  |     let text = StringCellData::from(row_cell.cell.as_ref().unwrap());
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |     match i {
 | 
					
						
							|  |  |  |       0 => assert_eq!(text.as_str(), "A"),
 | 
					
						
							|  |  |  |       1 => assert_eq!(text.as_str(), ""),
 | 
					
						
							|  |  |  |       2 => assert_eq!(text.as_str(), "C"),
 | 
					
						
							|  |  |  |       3 => assert_eq!(text.as_str(), "DA"),
 | 
					
						
							|  |  |  |       4 => assert_eq!(text.as_str(), "AE"),
 | 
					
						
							|  |  |  |       5 => assert_eq!(text.as_str(), "AE"),
 | 
					
						
							|  |  |  |       _ => {},
 | 
					
						
							|  |  |  |     }
 | 
					
						
							|  |  |  |   }
 | 
					
						
							|  |  |  | }
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #[tokio::test]
 | 
					
						
							| 
									
										
										
										
											2023-05-26 14:04:17 +03:30
										 |  |  | async fn url_cell_data_test() {
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |   let test = DatabaseCellTest::new().await;
 | 
					
						
							| 
									
										
										
										
											2024-08-18 05:16:42 +02:00
										 |  |  |   let url_field = test.get_first_field(FieldType::URL).await;
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |   let cells = test
 | 
					
						
							|  |  |  |     .editor
 | 
					
						
							|  |  |  |     .get_cells_for_field(&test.view_id, &url_field.id)
 | 
					
						
							|  |  |  |     .await;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-06-01 20:23:27 +08:00
										 |  |  |   for (i, row_cell) in cells.into_iter().enumerate() {
 | 
					
						
							|  |  |  |     if let Some(cell) = row_cell.cell.as_ref() {
 | 
					
						
							|  |  |  |       let cell = URLCellData::from(cell);
 | 
					
						
							|  |  |  |       if i == 0 {
 | 
					
						
							| 
									
										
										
										
											2024-04-15 11:43:02 +08:00
										 |  |  |         assert_eq!(
 | 
					
						
							|  |  |  |           cell.data.as_str(),
 | 
					
						
							|  |  |  |           "AppFlowy website - https://www.appflowy.io"
 | 
					
						
							|  |  |  |         );
 | 
					
						
							| 
									
										
										
										
											2023-06-01 20:23:27 +08:00
										 |  |  |       }
 | 
					
						
							| 
									
										
										
										
											2023-04-28 14:08:53 +08:00
										 |  |  |     }
 | 
					
						
							|  |  |  |   }
 | 
					
						
							|  |  |  | }
 | 
					
						
							| 
									
										
										
										
											2023-05-26 14:04:17 +03:30
										 |  |  | 
 | 
					
						
							|  |  |  | #[tokio::test]
 | 
					
						
							|  |  |  | async fn update_updated_at_field_on_other_cell_update() {
 | 
					
						
							|  |  |  |   let mut test = DatabaseCellTest::new().await;
 | 
					
						
							| 
									
										
										
										
											2024-08-18 05:16:42 +02:00
										 |  |  |   let updated_at_field = test.get_first_field(FieldType::LastEditedTime).await;
 | 
					
						
							| 
									
										
										
										
											2023-05-26 14:04:17 +03:30
										 |  |  | 
 | 
					
						
							|  |  |  |   let text_field = test
 | 
					
						
							|  |  |  |     .fields
 | 
					
						
							|  |  |  |     .iter()
 | 
					
						
							|  |  |  |     .find(|&f| FieldType::from(f.field_type) == FieldType::RichText)
 | 
					
						
							|  |  |  |     .unwrap();
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   let before_update_timestamp = chrono::offset::Utc::now().timestamp();
 | 
					
						
							|  |  |  |   test
 | 
					
						
							|  |  |  |     .run_script(UpdateCell {
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |       view_id: test.view_id.clone(),
 | 
					
						
							| 
									
										
										
										
											2024-08-26 09:46:16 +08:00
										 |  |  |       row_id: test.rows[0].id.clone(),
 | 
					
						
							| 
									
										
										
										
											2024-02-22 07:12:52 +08:00
										 |  |  |       field_id: text_field.id.clone(),
 | 
					
						
							|  |  |  |       changeset: BoxAny::new("change".to_string()),
 | 
					
						
							| 
									
										
										
										
											2023-05-26 14:04:17 +03:30
										 |  |  |       is_err: false,
 | 
					
						
							|  |  |  |     })
 | 
					
						
							|  |  |  |     .await;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   let cells = test
 | 
					
						
							|  |  |  |     .editor
 | 
					
						
							|  |  |  |     .get_cells_for_field(&test.view_id, &updated_at_field.id)
 | 
					
						
							|  |  |  |     .await;
 | 
					
						
							| 
									
										
										
										
											2023-06-03 23:35:55 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   tokio::time::sleep(Duration::from_millis(500)).await;
 | 
					
						
							|  |  |  |   let after_update_timestamp = chrono::offset::Utc::now().timestamp();
 | 
					
						
							| 
									
										
										
										
											2023-05-31 17:42:14 +08:00
										 |  |  |   assert!(!cells.is_empty());
 | 
					
						
							| 
									
										
										
										
											2023-06-01 20:23:27 +08:00
										 |  |  |   for (i, row_cell) in cells.into_iter().enumerate() {
 | 
					
						
							|  |  |  |     let timestamp = DateCellData::from(row_cell.cell.as_ref().unwrap())
 | 
					
						
							|  |  |  |       .timestamp
 | 
					
						
							|  |  |  |       .unwrap();
 | 
					
						
							| 
									
										
										
										
											2023-05-26 14:04:17 +03:30
										 |  |  |     println!(
 | 
					
						
							|  |  |  |       "{}, bf: {}, af: {}",
 | 
					
						
							|  |  |  |       timestamp, before_update_timestamp, after_update_timestamp
 | 
					
						
							|  |  |  |     );
 | 
					
						
							|  |  |  |     match i {
 | 
					
						
							|  |  |  |       0 => assert!(
 | 
					
						
							|  |  |  |         timestamp >= before_update_timestamp && timestamp <= after_update_timestamp,
 | 
					
						
							|  |  |  |         "{} >= {} && {} <= {}",
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         before_update_timestamp,
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         after_update_timestamp
 | 
					
						
							|  |  |  |       ),
 | 
					
						
							|  |  |  |       1 => assert!(
 | 
					
						
							|  |  |  |         timestamp <= before_update_timestamp,
 | 
					
						
							|  |  |  |         "{} <= {}",
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         before_update_timestamp
 | 
					
						
							|  |  |  |       ),
 | 
					
						
							|  |  |  |       2 => assert!(
 | 
					
						
							|  |  |  |         timestamp <= before_update_timestamp,
 | 
					
						
							|  |  |  |         "{} <= {}",
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         before_update_timestamp
 | 
					
						
							|  |  |  |       ),
 | 
					
						
							|  |  |  |       3 => assert!(
 | 
					
						
							|  |  |  |         timestamp <= before_update_timestamp,
 | 
					
						
							|  |  |  |         "{} <= {}",
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         before_update_timestamp
 | 
					
						
							|  |  |  |       ),
 | 
					
						
							|  |  |  |       4 => assert!(
 | 
					
						
							|  |  |  |         timestamp <= before_update_timestamp,
 | 
					
						
							|  |  |  |         "{} <= {}",
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         before_update_timestamp
 | 
					
						
							|  |  |  |       ),
 | 
					
						
							|  |  |  |       5 => assert!(
 | 
					
						
							|  |  |  |         timestamp <= before_update_timestamp,
 | 
					
						
							|  |  |  |         "{} <= {}",
 | 
					
						
							|  |  |  |         timestamp,
 | 
					
						
							|  |  |  |         before_update_timestamp
 | 
					
						
							|  |  |  |       ),
 | 
					
						
							|  |  |  |       _ => {},
 | 
					
						
							|  |  |  |     }
 | 
					
						
							|  |  |  |   }
 | 
					
						
							|  |  |  | }
 | 
					
						
							| 
									
										
										
										
											2024-06-13 10:22:13 +03:30
										 |  |  | 
 | 
					
						
							|  |  |  | #[tokio::test]
 | 
					
						
							|  |  |  | async fn time_cell_data_test() {
 | 
					
						
							|  |  |  |   let test = DatabaseCellTest::new().await;
 | 
					
						
							| 
									
										
										
										
											2024-08-18 05:16:42 +02:00
										 |  |  |   let time_field = test.get_first_field(FieldType::Time).await;
 | 
					
						
							| 
									
										
										
										
											2024-06-13 10:22:13 +03:30
										 |  |  |   let cells = test
 | 
					
						
							|  |  |  |     .editor
 | 
					
						
							|  |  |  |     .get_cells_for_field(&test.view_id, &time_field.id)
 | 
					
						
							|  |  |  |     .await;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   if let Some(cell) = cells[0].cell.as_ref() {
 | 
					
						
							|  |  |  |     let cell = TimeCellData::from(cell);
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     assert!(cell.0.is_some());
 | 
					
						
							|  |  |  |     assert_eq!(cell.0.unwrap_or_default(), 75);
 | 
					
						
							|  |  |  |   }
 | 
					
						
							|  |  |  | }
 |