use crate::{db::numeric::compare_numeric_or_strict_order, value::Value};
use std::cmp::Ordering;
pub(in crate::db) trait OrderingSemantics<T: ?Sized> {
fn compare(left: &T, right: &T) -> Ordering;
}
pub(in crate::db) struct CanonicalValueOrderingSemantics;
impl OrderingSemantics<Value> for CanonicalValueOrderingSemantics {
fn compare(left: &Value, right: &Value) -> Ordering {
if let Some(ordering) = compare_numeric_or_strict_order(left, right) {
return ordering;
}
Value::canonical_cmp(left, right)
}
}
#[must_use]
pub(in crate::db) fn canonical_value_compare(left: &Value, right: &Value) -> Ordering {
CanonicalValueOrderingSemantics::compare(left, right)
}
#[cfg(test)]
mod tests {
use crate::{db::contracts::canonical_value_compare, value::Value};
use std::cmp::Ordering;
#[test]
fn canonical_value_ordering_uses_value_canonical_order() {
assert_eq!(
canonical_value_compare(&Value::Uint(7), &Value::Uint(8)),
Ordering::Less
);
assert_eq!(
canonical_value_compare(&Value::Text("x".to_string()), &Value::Text("x".to_string())),
Ordering::Equal
);
}
#[test]
fn canonical_value_ordering_prefers_shared_numeric_or_strict_authority() {
assert_eq!(
canonical_value_compare(&Value::Int(7), &Value::Uint(7)),
Ordering::Equal
);
}
}