proptest/test_runner/
result_cache.rs1use crate::std_facade::fmt;
11use crate::std_facade::Box;
12#[cfg(feature = "std")]
13use std::collections::HashMap;
14
15use crate::test_runner::errors::TestCaseResult;
16
17#[derive(Debug)]
24pub struct ResultCacheKey<'a> {
25 value: &'a dyn fmt::Debug,
26}
27
28impl<'a> ResultCacheKey<'a> {
29 pub(crate) fn new(value: &'a dyn fmt::Debug) -> Self {
30 Self { value }
31 }
32
33 pub fn value_debug(&self) -> &dyn fmt::Debug {
35 self.value
36 }
37}
38
39pub trait ResultCache {
41 fn key(&self, key: &ResultCacheKey) -> u64;
47 fn put(&mut self, key: u64, result: &TestCaseResult);
52 fn get(&self, key: u64) -> Option<&TestCaseResult>;
55}
56
57#[cfg(feature = "std")]
58#[derive(Debug, Default, Clone)]
59struct BasicResultCache {
60 entries: HashMap<u64, TestCaseResult>,
61}
62
63#[cfg(feature = "std")]
64impl ResultCache for BasicResultCache {
65 fn key(&self, val: &ResultCacheKey) -> u64 {
66 use std::collections::hash_map::DefaultHasher;
67 use std::hash::Hasher;
68 use std::io::{self, Write};
69
70 struct HashWriter(DefaultHasher);
71 impl io::Write for HashWriter {
72 fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
73 self.0.write(buf);
74 Ok(buf.len())
75 }
76
77 fn flush(&mut self) -> io::Result<()> {
78 Ok(())
79 }
80 }
81
82 let mut hash = HashWriter(DefaultHasher::default());
83 write!(hash, "{:?}", val).expect("Debug format returned Err");
84 hash.0.finish()
85 }
86
87 fn put(&mut self, key: u64, result: &TestCaseResult) {
88 self.entries.insert(key, result.clone());
89 }
90
91 fn get(&self, key: u64) -> Option<&TestCaseResult> {
92 self.entries.get(&key)
93 }
94}
95
96#[cfg(feature = "std")]
100#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
101pub fn basic_result_cache() -> Box<dyn ResultCache> {
102 Box::new(BasicResultCache::default())
103}
104
105pub(crate) struct NoOpResultCache;
106impl ResultCache for NoOpResultCache {
107 fn key(&self, _: &ResultCacheKey) -> u64 {
108 0
109 }
110 fn put(&mut self, _: u64, _: &TestCaseResult) {}
111 fn get(&self, _: u64) -> Option<&TestCaseResult> {
112 None
113 }
114}
115
116pub fn noop_result_cache() -> Box<dyn ResultCache> {
120 Box::new(NoOpResultCache)
121}