aboutsummaryrefslogtreecommitdiff
path: root/crates/test_utils/src/lib.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/test_utils/src/lib.rs')
-rw-r--r--crates/test_utils/src/lib.rs26
1 files changed, 17 insertions, 9 deletions
diff --git a/crates/test_utils/src/lib.rs b/crates/test_utils/src/lib.rs
index a49be4602..05940a546 100644
--- a/crates/test_utils/src/lib.rs
+++ b/crates/test_utils/src/lib.rs
@@ -321,12 +321,11 @@ fn lines_match_works() {
321/// as paths). You can use a `"{...}"` string literal as a wildcard for 321/// as paths). You can use a `"{...}"` string literal as a wildcard for
322/// arbitrary nested JSON. Arrays are sorted before comparison. 322/// arbitrary nested JSON. Arrays are sorted before comparison.
323pub fn find_mismatch<'a>(expected: &'a Value, actual: &'a Value) -> Option<(&'a Value, &'a Value)> { 323pub fn find_mismatch<'a>(expected: &'a Value, actual: &'a Value) -> Option<(&'a Value, &'a Value)> {
324 use serde_json::Value::*;
325 match (expected, actual) { 324 match (expected, actual) {
326 (&Number(ref l), &Number(ref r)) if l == r => None, 325 (Value::Number(l), Value::Number(r)) if l == r => None,
327 (&Bool(l), &Bool(r)) if l == r => None, 326 (Value::Bool(l), Value::Bool(r)) if l == r => None,
328 (&String(ref l), &String(ref r)) if lines_match(l, r) => None, 327 (Value::String(l), Value::String(r)) if lines_match(l, r) => None,
329 (&Array(ref l), &Array(ref r)) => { 328 (Value::Array(l), Value::Array(r)) => {
330 if l.len() != r.len() { 329 if l.len() != r.len() {
331 return Some((expected, actual)); 330 return Some((expected, actual));
332 } 331 }
@@ -350,17 +349,26 @@ pub fn find_mismatch<'a>(expected: &'a Value, actual: &'a Value) -> Option<(&'a
350 None 349 None
351 } 350 }
352 } 351 }
353 (&Object(ref l), &Object(ref r)) => { 352 (Value::Object(l), Value::Object(r)) => {
353 fn sorted_values(obj: &serde_json::Map<String, Value>) -> Vec<&Value> {
354 let mut entries = obj.iter().collect::<Vec<_>>();
355 entries.sort_by_key(|it| it.0);
356 entries.into_iter().map(|(_k, v)| v).collect::<Vec<_>>()
357 }
358
354 let same_keys = l.len() == r.len() && l.keys().all(|k| r.contains_key(k)); 359 let same_keys = l.len() == r.len() && l.keys().all(|k| r.contains_key(k));
355 if !same_keys { 360 if !same_keys {
356 return Some((expected, actual)); 361 return Some((expected, actual));
357 } 362 }
358 363
359 l.values().zip(r.values()).filter_map(|(l, r)| find_mismatch(l, r)).next() 364 let l = sorted_values(l);
365 let r = sorted_values(r);
366
367 l.into_iter().zip(r).filter_map(|(l, r)| find_mismatch(l, r)).next()
360 } 368 }
361 (&Null, &Null) => None, 369 (Value::Null, Value::Null) => None,
362 // magic string literal "{...}" acts as wildcard for any sub-JSON 370 // magic string literal "{...}" acts as wildcard for any sub-JSON
363 (&String(ref l), _) if l == "{...}" => None, 371 (Value::String(l), _) if l == "{...}" => None,
364 _ => Some((expected, actual)), 372 _ => Some((expected, actual)),
365 } 373 }
366} 374}