From c82f4fa0bb4af30fc6b5319bf8cdc12fc105b97b Mon Sep 17 00:00:00 2001 From: pedrocarlo Date: Fri, 6 Jun 2025 15:40:36 -0300 Subject: [PATCH] adjust creation of columns to avoid name collision --- simulator/generation/predicate/binary.rs | 33 ++++++++++++++---------- simulator/generation/property.rs | 9 ++----- simulator/generation/table.rs | 19 +++++++++++--- simulator/model/table.rs | 17 +++++++++++- 4 files changed, 53 insertions(+), 25 deletions(-) diff --git a/simulator/generation/predicate/binary.rs b/simulator/generation/predicate/binary.rs index 2fef7cbb3..704d7f14d 100644 --- a/simulator/generation/predicate/binary.rs +++ b/simulator/generation/predicate/binary.rs @@ -422,17 +422,17 @@ mod tests { }, }; - fn get_rng() -> rand_chacha::ChaCha8Rng { - let seed = std::time::SystemTime::now() + fn get_seed() -> u64 { + std::time::SystemTime::now() .duration_since(std::time::UNIX_EPOCH) .unwrap() - .as_secs(); - ChaCha8Rng::seed_from_u64(seed) + .as_secs() } #[test] fn fuzz_true_binary_predicate() { - let mut rng = get_rng(); + let seed = get_seed(); + let mut rng = ChaCha8Rng::seed_from_u64(seed); for _ in 0..10000 { let table = Table::arbitrary(&mut rng); let num_rows = rng.gen_range(1..10); @@ -450,16 +450,18 @@ mod tests { let value = expr_to_value(&predicate.0, row, &table); assert!( value.as_ref().map_or(false, |value| value.into_bool()), - "Predicate: {:#?}\nValue: {:#?}", + "Predicate: {:#?}\nValue: {:#?}\nSeed: {}", predicate, - value + value, + seed ) } } #[test] fn fuzz_false_binary_predicate() { - let mut rng = get_rng(); + let seed = get_seed(); + let mut rng = ChaCha8Rng::seed_from_u64(seed); for _ in 0..10000 { let table = Table::arbitrary(&mut rng); let num_rows = rng.gen_range(1..10); @@ -477,16 +479,18 @@ mod tests { let value = expr_to_value(&predicate.0, row, &table); assert!( !value.as_ref().map_or(false, |value| value.into_bool()), - "Predicate: {:#?}\nValue: {:#?}", + "Predicate: {:#?}\nValue: {:#?}\nSeed: {}", predicate, - value + value, + seed ) } } #[test] fn fuzz_true_binary_simple_predicate() { - let mut rng = get_rng(); + let seed = get_seed(); + let mut rng = ChaCha8Rng::seed_from_u64(seed); for _ in 0..10000 { let mut table = Table::arbitrary(&mut rng); let num_rows = rng.gen_range(1..10); @@ -506,13 +510,14 @@ mod tests { .map(|row| predicate.0.test(row, &table)) .reduce(|accum, curr| accum || curr) .unwrap_or(false); - assert!(result, "Predicate: {:#?}", predicate) + assert!(result, "Predicate: {:#?}\nSeed: {}", predicate, seed) } } #[test] fn fuzz_false_binary_simple_predicate() { - let mut rng = get_rng(); + let seed = get_seed(); + let mut rng = ChaCha8Rng::seed_from_u64(seed); for _ in 0..10000 { let mut table = Table::arbitrary(&mut rng); let num_rows = rng.gen_range(1..10); @@ -531,7 +536,7 @@ mod tests { .iter() .map(|row| predicate.0.test(row, &table)) .any(|res| !res); - assert!(result, "Predicate: {:#?}", predicate) + assert!(result, "Predicate: {:#?}\nSeed: {}", predicate, seed) } } } diff --git a/simulator/generation/property.rs b/simulator/generation/property.rs index 058f28682..aead27bbe 100644 --- a/simulator/generation/property.rs +++ b/simulator/generation/property.rs @@ -1,4 +1,4 @@ -use limbo_core::{LimboError, Value}; +use limbo_core::LimboError; use serde::{Deserialize, Serialize}; use crate::{ @@ -418,14 +418,9 @@ impl Property { .iter() .filter(|vs| { let v = vs.first().unwrap(); - if let Value::Integer(i) = &v.0 { - *i == 1 - } else { - false - } + v.into_bool() }) .count(); - Ok(rows1 == rows2.len()) } _ => Ok(false), diff --git a/simulator/generation/table.rs b/simulator/generation/table.rs index 8309db9de..45b2a5a73 100644 --- a/simulator/generation/table.rs +++ b/simulator/generation/table.rs @@ -1,3 +1,5 @@ +use std::collections::HashSet; + use limbo_core::Value; use rand::Rng; @@ -16,9 +18,20 @@ impl Arbitrary for Name { impl Arbitrary for Table { fn arbitrary(rng: &mut R) -> Self { let name = Name::arbitrary(rng).0; - let columns = (1..=rng.gen_range(1..10)) - .map(|_| Column::arbitrary(rng)) - .collect(); + let columns = loop { + let columns = (1..=rng.gen_range(1..10)) + .map(|_| Column::arbitrary(rng)) + .collect::>(); + // TODO: see if there is a better way to detect duplicates here + let mut set = HashSet::with_capacity(columns.len()); + set.extend(columns.iter()); + // Has repeated column name inside so generate again + if set.len() != columns.len() { + continue; + } + break columns; + }; + Table { rows: Vec::new(), name, diff --git a/simulator/model/table.rs b/simulator/model/table.rs index d08283c19..e304cab0d 100644 --- a/simulator/model/table.rs +++ b/simulator/model/table.rs @@ -1,4 +1,4 @@ -use std::{fmt::Display, ops::Deref}; +use std::{fmt::Display, hash::Hash, ops::Deref}; use limbo_core::{numeric::Numeric, types}; use limbo_sqlite3_parser::ast; @@ -29,6 +29,21 @@ pub(crate) struct Column { pub(crate) unique: bool, } +// Uniquely defined by name in this case +impl Hash for Column { + fn hash(&self, state: &mut H) { + self.name.hash(state); + } +} + +impl PartialEq for Column { + fn eq(&self, other: &Self) -> bool { + self.name == other.name + } +} + +impl Eq for Column {} + #[derive(Debug, Clone, Serialize, Deserialize)] pub(crate) enum ColumnType { Integer,