From 1ec4e45a7f86b8cd875ab9c71fcb9c47e33c455e Mon Sep 17 00:00:00 2001 From: XFFXFF <1247714429@qq.com> Date: Sun, 7 Aug 2022 12:34:23 +0800 Subject: [PATCH] test: expect reuse field X changes but fn depends on field Y --- ...truct_changes_but_fn_deponds_on_field_y.rs | 109 ++++++++++++++++++ ...input_changes_but_fn_deponds_on_field_y.rs | 85 ++++++++++++++ 2 files changed, 194 insertions(+) create mode 100644 salsa-2022-tests/tests/expect_reuse_field_x_of_a_tracked_struct_changes_but_fn_deponds_on_field_y.rs create mode 100644 salsa-2022-tests/tests/expect_reuse_field_x_of_an_input_changes_but_fn_deponds_on_field_y.rs diff --git a/salsa-2022-tests/tests/expect_reuse_field_x_of_a_tracked_struct_changes_but_fn_deponds_on_field_y.rs b/salsa-2022-tests/tests/expect_reuse_field_x_of_a_tracked_struct_changes_but_fn_deponds_on_field_y.rs new file mode 100644 index 0000000..2a9633d --- /dev/null +++ b/salsa-2022-tests/tests/expect_reuse_field_x_of_a_tracked_struct_changes_but_fn_deponds_on_field_y.rs @@ -0,0 +1,109 @@ +//! Test that if field X of a tracked struct changes but not field Y, +//! functions that depend on X re-execute, but those depending only on Y do not +//! compiles and executes successfully. +#![allow(dead_code)] + +use salsa_2022_tests::{HasLogger, Logger}; + +use expect_test::expect; + +#[salsa::jar(db = Db)] +struct Jar( + MyInput, + MyTracked, + final_result_deponds_on_x, + final_result_deponds_on_y, + intermediate_result, +); + +trait Db: salsa::DbWithJar + HasLogger {} + +#[salsa::input(jar = Jar)] +struct MyInput { + field: u32, +} + +#[salsa::tracked(jar = Jar)] +fn final_result_deponds_on_x(db: &dyn Db, input: MyInput) -> u32 { + db.push_log(format!("final_result_deponds_on_x({:?})", input)); + intermediate_result(db, input).x(db) * 2 +} + +#[salsa::tracked(jar = Jar)] +fn final_result_deponds_on_y(db: &dyn Db, input: MyInput) -> u32 { + db.push_log(format!("final_result_deponds_on_y({:?})", input)); + intermediate_result(db, input).y(db) * 2 +} + +#[salsa::tracked(jar = Jar)] +struct MyTracked { + x: u32, + y: u32, +} + +#[salsa::tracked(jar = Jar)] +fn intermediate_result(db: &dyn Db, input: MyInput) -> MyTracked { + MyTracked::new(db, (input.field(db) + 1) / 2, input.field(db) / 2) +} + +#[salsa::db(Jar)] +#[derive(Default)] +struct Database { + storage: salsa::Storage, + logger: Logger, +} + +impl salsa::Database for Database { + fn salsa_runtime(&self) -> &salsa::Runtime { + self.storage.runtime() + } +} + +impl Db for Database {} + +impl HasLogger for Database { + fn logger(&self) -> &Logger { + &self.logger + } +} + +#[test] +fn execute() { + // x = (input.field + 1) / 2 + // y = input.field / 2 + // final_result_deponds_on_x = x * 2 = (input.field + 1) / 2 * 2 + // final_result_deponds_on_y = y * 2 = input.field / 2 * 2 + let mut db = Database::default(); + + // intermediate results: + // x = (22 + 1) / 2 = 11 + // y = 22 / 2 = 11 + let input = MyInput::new(&mut db, 22); + assert_eq!(final_result_deponds_on_x(&db, input), 22); + db.assert_logs(expect![[r#" + [ + "final_result_deponds_on_x(MyInput(Id { value: 1 }))", + ]"#]]); + + assert_eq!(final_result_deponds_on_y(&db, input), 22); + db.assert_logs(expect![[r#" + [ + "final_result_deponds_on_y(MyInput(Id { value: 1 }))", + ]"#]]); + + input.set_field(&mut db, 23); + // x = (23 + 1) / 2 = 12 + // Intermediate result x changes, so final result depends on x + // needs to be recomputed; + assert_eq!(final_result_deponds_on_x(&db, input), 24); + db.assert_logs(expect![[r#" + [ + "final_result_deponds_on_x(MyInput(Id { value: 1 }))", + ]"#]]); + + // y = 23 / 2 = 11 + // Intermediate result y is the same, so final result depends on y + // does not need to be recomputed; + assert_eq!(final_result_deponds_on_y(&db, input), 22); + db.assert_logs(expect!["[]"]); +} diff --git a/salsa-2022-tests/tests/expect_reuse_field_x_of_an_input_changes_but_fn_deponds_on_field_y.rs b/salsa-2022-tests/tests/expect_reuse_field_x_of_an_input_changes_but_fn_deponds_on_field_y.rs new file mode 100644 index 0000000..5efd337 --- /dev/null +++ b/salsa-2022-tests/tests/expect_reuse_field_x_of_an_input_changes_but_fn_deponds_on_field_y.rs @@ -0,0 +1,85 @@ +//! Test that if field X of an input changes but not field Y, +//! functions that depend on X re-execute, but those depending only on Y do not +//! compiles and executes successfully. +#![allow(dead_code)] + +use salsa_2022_tests::{HasLogger, Logger}; + +use expect_test::expect; + +#[salsa::jar(db = Db)] +struct Jar(MyInput, result_deponds_on_x, result_deponds_on_y); + +trait Db: salsa::DbWithJar + HasLogger {} + +#[salsa::input(jar = Jar)] +struct MyInput { + x: u32, + y: u32, +} + +#[salsa::tracked(jar = Jar)] +fn result_deponds_on_x(db: &dyn Db, input: MyInput) -> u32 { + db.push_log(format!("result_deponds_on_x({:?})", input)); + input.x(db) + 1 +} + +#[salsa::tracked(jar = Jar)] +fn result_deponds_on_y(db: &dyn Db, input: MyInput) -> u32 { + db.push_log(format!("result_deponds_on_y({:?})", input)); + input.y(db) - 1 +} + +#[salsa::db(Jar)] +#[derive(Default)] +struct Database { + storage: salsa::Storage, + logger: Logger, +} + +impl salsa::Database for Database { + fn salsa_runtime(&self) -> &salsa::Runtime { + self.storage.runtime() + } +} + +impl Db for Database {} + +impl HasLogger for Database { + fn logger(&self) -> &Logger { + &self.logger + } +} + +#[test] +fn execute() { + // result_deponds_on_x = x + 1 + // result_deponds_on_y = y - 1 + let mut db = Database::default(); + + let input = MyInput::new(&mut db, 22, 33); + assert_eq!(result_deponds_on_x(&db, input), 23); + db.assert_logs(expect![[r#" + [ + "result_deponds_on_x(MyInput(Id { value: 1 }))", + ]"#]]); + + assert_eq!(result_deponds_on_y(&db, input), 32); + db.assert_logs(expect![[r#" + [ + "result_deponds_on_y(MyInput(Id { value: 1 }))", + ]"#]]); + + input.set_x(&mut db, 23); + // input x changes, so result depends on x needs to be recomputed; + assert_eq!(result_deponds_on_x(&db, input), 24); + db.assert_logs(expect![[r#" + [ + "result_deponds_on_x(MyInput(Id { value: 1 }))", + ]"#]]); + + // input y is the same, so result depends on y + // does not need to be recomputed; + assert_eq!(result_deponds_on_y(&db, input), 32); + db.assert_logs(expect!["[]"]); +}