use core::cell::Cell;
use core::ops::Deref;
use crate::AssertThat;
use crate::actual::Actual;
use crate::mode::Panic;
#[doc(hidden)]
pub struct Fallback<T>(pub Cell<Option<T>>);
#[doc(hidden)]
pub struct Wrap<T> {
pub inner: Fallback<T>,
}
impl<'a, T> Wrap<&'a T> {
#[track_caller]
#[must_use]
pub fn into_assert_that(&self) -> AssertThat<'a, T, Panic> {
AssertThat::new_panicking(Actual::Borrowed(
self.inner
.0
.take()
.expect("assertr: value already consumed"),
))
}
}
impl<T> Deref for Wrap<T> {
type Target = Fallback<T>;
fn deref(&self) -> &Fallback<T> {
&self.inner
}
}
impl<T> Fallback<T> {
#[track_caller]
#[must_use]
pub fn into_assert_that<'t>(&self) -> AssertThat<'t, T, Panic>
where
T: 't,
{
AssertThat::new_panicking(Actual::Owned(
self.0.take().expect("assertr: value already consumed"),
))
}
}
#[cfg(test)]
mod tests {
mod owned_values {
use crate::prelude::*;
#[test]
fn works_with_integer() {
assert_that!(42).is_equal_to(42);
}
#[test]
fn works_with_string() {
assert_that!(String::from("hello")).is_equal_to("hello".to_string());
}
#[test]
fn works_with_vec() {
assert_that!(vec![1, 2, 3]).has_length(3);
}
#[test]
fn works_with_bool() {
assert_that!(true).is_true();
}
#[test]
fn works_with_option() {
assert_that!(Some(42)).is_some().is_equal_to(42);
}
#[test]
fn works_with_result() {
assert_that!(Result::<i32, ()>::Ok(42))
.is_ok()
.is_equal_to(42);
}
}
mod unsized_reference_targets {
use crate::prelude::*;
#[test]
fn works_with_str_slice() {
assert_that!("hello").starts_with("hel");
}
#[cfg(feature = "std")]
#[test]
fn works_with_path() {
use std::path::Path;
let path = Path::new("foo/bar.rs");
assert_that!(path).has_file_name("bar.rs");
}
}
mod borrowed_values {
use crate::prelude::*;
#[test]
fn works_with_borrowed_integer() {
let value = 42;
assert_that!(&value).is_equal_to(42);
let _ = value;
}
#[test]
fn works_with_borrowed_string() {
let value = String::from("hello");
assert_that!(&value).is_equal_to("hello".to_string());
let _ = value;
}
#[test]
fn works_with_borrowed_vec() {
let value = vec![1, 2, 3];
assert_that!(&value).has_length(3);
let _ = value;
}
#[test]
fn works_with_borrowed_option() {
let value = Some(42);
assert_that!(&value).is_some().is_equal_to(42);
let _ = value;
}
#[cfg(feature = "std")]
#[test]
fn works_with_borrowed_mutex() {
use std::sync::Mutex;
let mutex = Mutex::new(42);
let guard = mutex.lock().expect("lock");
assert_that!(&mutex).is_locked();
drop(guard);
}
#[test]
fn works_with_variable_holding_reference() {
let value = 42;
let r: &i32 = &value;
assert_that!(r).is_equal_to(42);
}
}
mod chaining {
use crate::prelude::*;
#[test]
fn allows_chaining_multiple_assertions() {
assert_that!(42).is_equal_to(42).is_not_equal_to(43);
}
}
mod capture_mode {
use crate::prelude::*;
#[test]
fn works_with_capture() {
let failures = assert_that!(42)
.with_capture()
.is_equal_to(43)
.capture_failures();
assert_that!(failures).has_length(1);
}
}
}