Open asomers opened 5 years ago
I just gave it a try and didn't have any problems
#!/usr/bin/env run-cargo-script
//! ```cargo
//! [package]
//! edition="2018"
//! [dependencies]
//! predicates = "1"
//! ```
use predicates::prelude::*;
fn main() {
let actual = std::path::PathBuf::from("Cargo.toml");
let expected = std::path::PathBuf::from("Cargo.toml");
let pred = predicate::path::eq_file(expected);
println!("{}", pred.eval(actual.as_path()));
}
Could you clarify where you are having lifetime problems at?
It worked for you because of that as_path()
on the last line. In my case I'm using predicates from a generic function, so I can't do that.
Could you provide an example so I can better understand the constraints and we can work out how predicates might be able to change to make it work?
It's basically like this. The matches
function doesn't know anything about what type it's handling. It's not very critical for me, though.
#!/usr/bin/env run-cargo-script
//! ```cargo
//! [package]
//! edition="2018"
//! [dependencies]
//! predicates = "1"
//! ```
fn matches<T, P: Predicate<T>>(value: &T, predicate: P) -> bool {
predicate.eval(value)
}
use predicates::prelude::*;
fn main() {
let actual = std::path::PathBuf::from("Cargo.toml");
let expected = std::path::PathBuf::from("Cargo.toml");
let pred = predicate::path::eq_file(expected);
println!("{}", matches(&actual, pred));
}
Thanks for the example. For me to better understand the needs / use cases, is there a reason matches(actual.as_path(), pred)
isn't sufficient?
Well, there's more generic code in front of that matches
, and that code takes its argument by value, like this:
#!/usr/bin/env run-cargo-script
//! ```cargo
//! [package]
//! edition="2018"
//! [dependencies]
//! predicates = "1"
//! ```
fn do_something_with_value<T>(_value: T) {
}
fn do_something_with_value_if_it_matches<T, P>(value: T, predicate: P)
where P: Predicate<T>
{
if matches(&value, predicate) {
do_something_with_value(value)
}
}
fn matches<T, P: Predicate<T>>(value: &T, predicate: P) -> bool {
predicate.eval(value)
}
use predicates::prelude::*;
fn main() {
let actual = std::path::PathBuf::from("Cargo.toml");
let expected = std::path::PathBuf::from("Cargo.toml");
let pred = predicate::path::eq_file(expected);
do_something_with_value_if_it_matches(actual, pred);
}
btw this is related to #20 where I ran into a lot of problems solving this generically.
Some options
PathBuf
predicates into Path
predicatesimpl Predicate
to each of our predicatesAsRef
/ Deref / Borrow are object safe, allowing us to take &dyn AsRef<Path>
.
It would be handy if
BinaryFilePredicate
implementedPredicate<PathBuf>
. There are some functions that, for lifetime reasons, must take a'static
argument, likePathBuf
. Right now those functions can't easily use predicates.