Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Chapter 11.1 - Explain that it's not possible to expect a test to return an error when the return type is Result #2085

Closed
TomLouisKeller opened this issue Sep 9, 2019 · 3 comments
Labels
Milestone

Comments

@TomLouisKeller
Copy link

Hy,

In Chapter 11.1 - How to Write Tests - at the bottom of the page it is explained, how to
write a test, when we expect the compiler to panic. The book then goes on to explain how to write a test, when we expect Result::Ok, but when it comes to an expected Result::Err is only states:

You can’t use the #[should_panic] annotation on tests that use Result<T, E>.
Instead, you should return an Err value directly when the test should fail.

I interpret this as we have to write something in the lines of:

#[test]
fn expect_err() -> Result::Err {
    Err(String::from("This is an expected error"))
}

This doesn't work because Result::Err is a variant, not a type.
I've found these two ways to test for Result:Err:

#[test]
fn expect_err() {
    let res: Result<(), &str> = Err("This is an expected error");

    res.expect_err("This should have panicked");
    // or
    assert_eq!(res.is_ok(), false);
}

It would be nice if there was a code example, after the quoted sentence.

Thank you very much to everyone who worked on the book. I thoroughly enjoy it.

@rusty-snake
Copy link

should_panic means that a test pass if it panics.
Example: test1 will fail, test2 will pass.

#[test]
#[should_panic]
fn test1() -> Result<(), Box<dyn std::error::Error>> {
    Ok(())
}
#[test]
#[should_panic]
fn test2() -> Result<(), Box<dyn std::error::Error>> {
    Err(std::io::Error)
}

Or if care about the error:

fn test3() {
    assert!(if let Err(MyError::V1) = something() {
        true
    } else {
        false
    });
}

@TomLouisKeller
Copy link
Author

@rusty-snake test1 and test2 throw a compiling error:

functions using #[should_panic] must return ()

@carols10cents carols10cents added this to the ch11 milestone Jul 17, 2021
@carols10cents carols10cents changed the title Chapter 11.1 - Request for an example of a test with expected Result::Err Chapter 11.1 - Explain that it's not possible to expect a test to return an error when the return type is Result Nov 28, 2021
@carols10cents
Copy link
Member

Yep, it's not possible to do #[should_panic] with a test that returns Result. The purpose of having a test function return Result is so that you can use ? in the test to mean "this operation should succeed, if not, fail the test".

The way to check that an operation within a test returns an Err as expected is to not use ? on that value, but instead use assert!(val.is_err()) or val.expect_err(...) or match.

Relevant threads:

The book text definitely needs to be clarified in this regard, but I wanted to save my research.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants