Skip to content

Commit 1d0def2

Browse files
author
Ed Page
committed
fix(diff): Remove duplicated output
In the tree view, we already show the original and the current value, we shouldnt show an entire Diff that is only parseable by color. In changing this, we removed the more cosmetic atom selector. We also removed the edit distance, since there isn't a known case for it. Let us know if you needed this! Fixes #94 Fixes #105
1 parent 23c1360 commit 1d0def2

File tree

6 files changed

+42
-118
lines changed

6 files changed

+42
-118
lines changed

CHANGELOG.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,18 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
77
<!-- next-header -->
88
## [Unreleased] - ReleaseDate
99

10+
#### Breaking Changes
11+
12+
- `predicates::str::diff` was removed
13+
- `predicates::str::similar` was renamed to `diff`
14+
- The `difference` feature flag was renamed to `diff`
15+
- `diff().split` and `diff().distance` were removed
16+
17+
#### Fixes
18+
19+
- Shrink the output of Diffs because its redundant
20+
- Moved off of an unmaintained Diff library
21+
1022
## [1.0.8] - 2021-04-28
1123

1224
## [1.0.7] - 2021-01-29

Cargo.toml

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,14 +22,16 @@ azure-devops = { project = "assert-rs", pipeline = "predicates-rs" }
2222

2323
[dependencies]
2424
predicates-core = { version = "1.0", path = "crates/core" }
25-
difference = { version = "2.0", optional = true }
25+
difflib = { version = "0.4", optional = true }
2626
normalize-line-endings = { version = "0.3.0", optional = true }
2727
regex = { version="1.0", optional = true }
2828
float-cmp = { version="0.8", optional = true }
29+
itertools = "0.10"
2930

3031
[dev-dependencies]
3132
predicates-tree = { version = "1.0", path = "crates/tree" }
3233

3334
[features]
34-
default = ["difference", "regex", "float-cmp", "normalize-line-endings"]
35+
default = ["diff", "regex", "float-cmp", "normalize-line-endings"]
36+
diff = ["difflib"]
3537
unstable = []

src/lib.rs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -137,9 +137,8 @@
137137
//! - [`predicate::str::is_empty`]: Specified string must be empty
138138
//! - [`str_pred = predicate::path::eq_file(...).utf8`]: Specified string must equal the contents
139139
//! of the given file.
140-
//! - [`predicate::str::similar`]: Same as `eq` except report a diff. See [`DifferencePredicate`]
140+
//! - [`predicate::str::diff`]: Same as `eq` except report a diff. See [`DifferencePredicate`]
141141
//! for more features.
142-
//! - [`predicate::str::diff`]: Same as `ne`. See [`DifferencePredicate`] for more features.
143142
//! - [`predicate::str::starts_with`]: Specified string must start with the given needle.
144143
//! - [`predicate::str::ends_with`]: Specified string must end with the given needle.
145144
//! - [`predicate::str::contains`]: Specified string must contain the given needle.
@@ -194,7 +193,6 @@
194193
//! [`predicate::str::is_empty`]: prelude::predicate::str::is_empty()
195194
//! [`predicate::str::is_match(...).count`]: str::RegexPredicate::count()
196195
//! [`predicate::str::is_match`]: prelude::predicate::str::is_match()
197-
//! [`predicate::str::similar`]: prelude::predicate::str::similar()
198196
//! [`predicate::str::starts_with`]: prelude::predicate::str::starts_with()
199197
//! [`str_pred = predicate::path::eq_file(...).utf8`]: path::BinaryFilePredicate::utf8()
200198
//! [`str_pred.normalize`]: prelude::PredicateStrExt::normalize()

src/prelude.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,8 @@ pub mod predicate {
3030
pub use crate::str::is_empty;
3131
pub use crate::str::{contains, ends_with, starts_with};
3232

33-
#[cfg(feature = "difference")]
34-
pub use crate::str::{diff, similar};
33+
#[cfg(feature = "diff")]
34+
pub use crate::str::diff;
3535

3636
#[cfg(feature = "regex")]
3737
pub use crate::str::is_match;

src/str/difference.rs

Lines changed: 20 additions & 108 deletions
Original file line numberDiff line numberDiff line change
@@ -12,95 +12,36 @@ use std::fmt;
1212
use crate::reflection;
1313
use crate::Predicate;
1414

15-
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
16-
enum DistanceOp {
17-
Similar,
18-
Different,
19-
}
20-
21-
impl DistanceOp {
22-
fn eval(self, limit: i32, distance: i32) -> bool {
23-
match self {
24-
DistanceOp::Similar => distance <= limit,
25-
DistanceOp::Different => limit < distance,
26-
}
27-
}
28-
}
29-
3015
/// Predicate that diffs two strings.
3116
///
32-
/// This is created by the `predicate::str::similar`.
17+
/// This is created by the `predicate::str::diff`.
3318
#[derive(Debug, Clone, PartialEq, Eq)]
3419
pub struct DifferencePredicate {
3520
orig: borrow::Cow<'static, str>,
36-
split: borrow::Cow<'static, str>,
37-
distance: i32,
38-
op: DistanceOp,
39-
}
40-
41-
impl DifferencePredicate {
42-
/// The split used when identifying changes.
43-
///
44-
/// Common splits include:
45-
/// - `""` for char-level.
46-
/// - `" "` for word-level.
47-
/// - `"\n"` for line-level.
48-
///
49-
/// Default: `"\n"`
50-
///
51-
/// # Examples
52-
///
53-
/// ```
54-
/// use predicates::prelude::*;
55-
///
56-
/// let predicate_fn = predicate::str::similar("Hello World").split(" ");
57-
/// assert_eq!(true, predicate_fn.eval("Hello World"));
58-
/// ```
59-
pub fn split<S>(mut self, split: S) -> Self
60-
where
61-
S: Into<borrow::Cow<'static, str>>,
62-
{
63-
self.split = split.into();
64-
self
65-
}
66-
67-
/// The maximum allowed edit distance.
68-
///
69-
/// Default: `0`
70-
///
71-
/// # Examples
72-
///
73-
/// ```
74-
/// use predicates::prelude::*;
75-
///
76-
/// let predicate_fn = predicate::str::similar("Hello World!").split("").distance(1);
77-
/// assert_eq!(true, predicate_fn.eval("Hello World!"));
78-
/// assert_eq!(true, predicate_fn.eval("Hello World"));
79-
/// assert_eq!(false, predicate_fn.eval("Hello World?"));
80-
/// ```
81-
pub fn distance(mut self, distance: i32) -> Self {
82-
self.distance = distance;
83-
self
84-
}
8521
}
8622

8723
impl Predicate<str> for DifferencePredicate {
8824
fn eval(&self, edit: &str) -> bool {
89-
let change = difference::Changeset::new(&self.orig, edit, &self.split);
90-
self.op.eval(self.distance, change.distance)
25+
edit == self.orig
9126
}
9227

9328
fn find_case<'a>(&'a self, expected: bool, variable: &str) -> Option<reflection::Case<'a>> {
94-
let change = difference::Changeset::new(&self.orig, variable, &self.split);
95-
let result = self.op.eval(self.distance, change.distance);
29+
let result = variable != self.orig;
9630
if result == expected {
31+
None
32+
} else {
33+
let orig: Vec<_> = self.orig.lines().map(|l| format!("{}\n", l)).collect();
34+
let variable: Vec<_> = variable.lines().map(|l| format!("{}\n", l)).collect();
35+
let mut diff =
36+
difflib::unified_diff(&orig, &variable, "value", "value", "expected", "actual", 0);
37+
diff.insert(0, "\n".to_owned());
38+
9739
Some(
98-
reflection::Case::new(Some(self), result)
99-
.add_product(reflection::Product::new("actual distance", change.distance))
100-
.add_product(reflection::Product::new("diff", change)),
40+
reflection::Case::new(Some(self), result).add_product(reflection::Product::new(
41+
"diff",
42+
itertools::join(diff.iter(), ""),
43+
)),
10144
)
102-
} else {
103-
None
10445
}
10546
}
10647
}
@@ -114,10 +55,7 @@ impl reflection::PredicateReflection for DifferencePredicate {
11455

11556
impl fmt::Display for DifferencePredicate {
11657
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
117-
match self.op {
118-
DistanceOp::Similar => write!(f, "var - original <= {}", self.distance),
119-
DistanceOp::Different => write!(f, "{} < var - original", self.distance),
120-
}
58+
write!(f, "diff var original")
12159
}
12260
}
12361

@@ -129,40 +67,14 @@ impl fmt::Display for DifferencePredicate {
12967
/// use predicates::prelude::*;
13068
///
13169
/// let predicate_fn = predicate::str::diff("Hello World");
132-
/// assert_eq!(false, predicate_fn.eval("Hello World"));
133-
/// assert_eq!(true, predicate_fn.eval("Goodbye World"));
134-
/// ```
135-
pub fn diff<S>(orig: S) -> DifferencePredicate
136-
where
137-
S: Into<borrow::Cow<'static, str>>,
138-
{
139-
DifferencePredicate {
140-
orig: orig.into(),
141-
split: "\n".into(),
142-
distance: 0,
143-
op: DistanceOp::Different,
144-
}
145-
}
146-
147-
/// Creates a new `Predicate` that checks strings for how similar they are.
148-
///
149-
/// # Examples
150-
///
151-
/// ```
152-
/// use predicates::prelude::*;
153-
///
154-
/// let predicate_fn = predicate::str::similar("Hello World");
15570
/// assert_eq!(true, predicate_fn.eval("Hello World"));
71+
/// assert!(predicate_fn.find_case(true, "Hello World").is_none());
15672
/// assert_eq!(false, predicate_fn.eval("Goodbye World"));
73+
/// assert!(predicate_fn.find_case(true, "Goodbye World").is_some());
15774
/// ```
158-
pub fn similar<S>(orig: S) -> DifferencePredicate
75+
pub fn diff<S>(orig: S) -> DifferencePredicate
15976
where
16077
S: Into<borrow::Cow<'static, str>>,
16178
{
162-
DifferencePredicate {
163-
orig: orig.into(),
164-
split: "\n".into(),
165-
distance: 0,
166-
op: DistanceOp::Similar,
167-
}
79+
DifferencePredicate { orig: orig.into() }
16880
}

src/str/mod.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,10 @@ pub use self::basics::*;
1515
mod adapters;
1616
pub use self::adapters::*;
1717

18-
#[cfg(feature = "difference")]
18+
#[cfg(feature = "diff")]
1919
mod difference;
20-
#[cfg(feature = "difference")]
21-
pub use self::difference::{diff, similar, DifferencePredicate};
20+
#[cfg(feature = "diff")]
21+
pub use self::difference::{diff, DifferencePredicate};
2222
#[cfg(feature = "normalize-line-endings")]
2323
mod normalize;
2424
#[cfg(feature = "normalize-line-endings")]

0 commit comments

Comments
 (0)