Warn when a #[should_panic] test has an unexpected message
This commit is contained in:
@@ -75,9 +75,9 @@ const TEST_WARN_TIMEOUT_S: u64 = 60;
|
|||||||
// to be used by rustc to compile tests in libtest
|
// to be used by rustc to compile tests in libtest
|
||||||
pub mod test {
|
pub mod test {
|
||||||
pub use {Bencher, TestName, TestResult, TestDesc, TestDescAndFn, TestOpts, TrFailed,
|
pub use {Bencher, TestName, TestResult, TestDesc, TestDescAndFn, TestOpts, TrFailed,
|
||||||
TrIgnored, TrOk, Metric, MetricMap, StaticTestFn, StaticTestName, DynTestName,
|
TrFailedMsg, TrIgnored, TrOk, Metric, MetricMap, StaticTestFn, StaticTestName,
|
||||||
DynTestFn, run_test, test_main, test_main_static, filter_tests, parse_opts,
|
DynTestName, DynTestFn, run_test, test_main, test_main_static, filter_tests,
|
||||||
StaticBenchFn, ShouldPanic};
|
parse_opts, StaticBenchFn, ShouldPanic};
|
||||||
}
|
}
|
||||||
|
|
||||||
pub mod stats;
|
pub mod stats;
|
||||||
@@ -473,6 +473,7 @@ pub struct BenchSamples {
|
|||||||
pub enum TestResult {
|
pub enum TestResult {
|
||||||
TrOk,
|
TrOk,
|
||||||
TrFailed,
|
TrFailed,
|
||||||
|
TrFailedMsg(String),
|
||||||
TrIgnored,
|
TrIgnored,
|
||||||
TrMetrics(MetricMap),
|
TrMetrics(MetricMap),
|
||||||
TrBench(BenchSamples),
|
TrBench(BenchSamples),
|
||||||
@@ -611,7 +612,7 @@ impl<T: Write> ConsoleTestState<T> {
|
|||||||
pub fn write_result(&mut self, result: &TestResult) -> io::Result<()> {
|
pub fn write_result(&mut self, result: &TestResult) -> io::Result<()> {
|
||||||
match *result {
|
match *result {
|
||||||
TrOk => self.write_ok(),
|
TrOk => self.write_ok(),
|
||||||
TrFailed => self.write_failed(),
|
TrFailed | TrFailedMsg(_) => self.write_failed(),
|
||||||
TrIgnored => self.write_ignored(),
|
TrIgnored => self.write_ignored(),
|
||||||
TrMetrics(ref mm) => {
|
TrMetrics(ref mm) => {
|
||||||
self.write_metric()?;
|
self.write_metric()?;
|
||||||
@@ -638,6 +639,7 @@ impl<T: Write> ConsoleTestState<T> {
|
|||||||
match *result {
|
match *result {
|
||||||
TrOk => "ok".to_owned(),
|
TrOk => "ok".to_owned(),
|
||||||
TrFailed => "failed".to_owned(),
|
TrFailed => "failed".to_owned(),
|
||||||
|
TrFailedMsg(ref msg) => format!("failed: {}", msg),
|
||||||
TrIgnored => "ignored".to_owned(),
|
TrIgnored => "ignored".to_owned(),
|
||||||
TrMetrics(ref mm) => mm.fmt_metrics(),
|
TrMetrics(ref mm) => mm.fmt_metrics(),
|
||||||
TrBench(ref bs) => fmt_bench_samples(bs),
|
TrBench(ref bs) => fmt_bench_samples(bs),
|
||||||
@@ -773,6 +775,14 @@ pub fn run_tests_console(opts: &TestOpts, tests: Vec<TestDescAndFn>) -> io::Resu
|
|||||||
st.failed += 1;
|
st.failed += 1;
|
||||||
st.failures.push((test, stdout));
|
st.failures.push((test, stdout));
|
||||||
}
|
}
|
||||||
|
TrFailedMsg(msg) => {
|
||||||
|
st.failed += 1;
|
||||||
|
let mut stdout = stdout;
|
||||||
|
stdout.extend_from_slice(
|
||||||
|
format!("note: {}", msg).as_bytes()
|
||||||
|
);
|
||||||
|
st.failures.push((test, stdout));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@@ -1270,12 +1280,16 @@ fn calc_result(desc: &TestDesc, task_result: Result<(), Box<Any + Send>>) -> Tes
|
|||||||
match (&desc.should_panic, task_result) {
|
match (&desc.should_panic, task_result) {
|
||||||
(&ShouldPanic::No, Ok(())) |
|
(&ShouldPanic::No, Ok(())) |
|
||||||
(&ShouldPanic::Yes, Err(_)) => TrOk,
|
(&ShouldPanic::Yes, Err(_)) => TrOk,
|
||||||
(&ShouldPanic::YesWithMessage(msg), Err(ref err))
|
(&ShouldPanic::YesWithMessage(msg), Err(ref err)) =>
|
||||||
if err.downcast_ref::<String>()
|
if err.downcast_ref::<String>()
|
||||||
.map(|e| &**e)
|
.map(|e| &**e)
|
||||||
.or_else(|| err.downcast_ref::<&'static str>().map(|e| *e))
|
.or_else(|| err.downcast_ref::<&'static str>().map(|e| *e))
|
||||||
.map(|e| e.contains(msg))
|
.map(|e| e.contains(msg))
|
||||||
.unwrap_or(false) => TrOk,
|
.unwrap_or(false) {
|
||||||
|
TrOk
|
||||||
|
} else {
|
||||||
|
TrFailedMsg(format!("Panic did not include expected string '{}'", msg))
|
||||||
|
},
|
||||||
_ => TrFailed,
|
_ => TrFailed,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1482,8 +1496,9 @@ pub mod bench {
|
|||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use test::{TrFailed, TrIgnored, TrOk, filter_tests, parse_opts, TestDesc, TestDescAndFn,
|
use test::{TrFailed, TrFailedMsg, TrIgnored, TrOk, filter_tests, parse_opts, TestDesc,
|
||||||
TestOpts, run_test, MetricMap, StaticTestName, DynTestName, DynTestFn, ShouldPanic};
|
TestDescAndFn, TestOpts, run_test, MetricMap, StaticTestName, DynTestName,
|
||||||
|
DynTestFn, ShouldPanic};
|
||||||
use std::sync::mpsc::channel;
|
use std::sync::mpsc::channel;
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
@@ -1565,18 +1580,20 @@ mod tests {
|
|||||||
fn f() {
|
fn f() {
|
||||||
panic!("an error message");
|
panic!("an error message");
|
||||||
}
|
}
|
||||||
|
let expected = "foobar";
|
||||||
|
let failed_msg = "Panic did not include expected string";
|
||||||
let desc = TestDescAndFn {
|
let desc = TestDescAndFn {
|
||||||
desc: TestDesc {
|
desc: TestDesc {
|
||||||
name: StaticTestName("whatever"),
|
name: StaticTestName("whatever"),
|
||||||
ignore: false,
|
ignore: false,
|
||||||
should_panic: ShouldPanic::YesWithMessage("foobar"),
|
should_panic: ShouldPanic::YesWithMessage(expected),
|
||||||
},
|
},
|
||||||
testfn: DynTestFn(Box::new(move |()| f())),
|
testfn: DynTestFn(Box::new(move |()| f())),
|
||||||
};
|
};
|
||||||
let (tx, rx) = channel();
|
let (tx, rx) = channel();
|
||||||
run_test(&TestOpts::new(), false, desc, tx);
|
run_test(&TestOpts::new(), false, desc, tx);
|
||||||
let (_, res, _) = rx.recv().unwrap();
|
let (_, res, _) = rx.recv().unwrap();
|
||||||
assert!(res == TrFailed);
|
assert!(res == TrFailedMsg(format!("{} '{}'", failed_msg, expected)));
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
|
|||||||
19
src/test/run-fail/test-should-panic-bad-message.rs
Normal file
19
src/test/run-fail/test-should-panic-bad-message.rs
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
// Copyright 2014 The Rust Project Developers. See the COPYRIGHT
|
||||||
|
// file at the top-level directory of this distribution and at
|
||||||
|
// http://rust-lang.org/COPYRIGHT.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||||
|
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||||
|
// option. This file may not be copied, modified, or distributed
|
||||||
|
// except according to those terms.
|
||||||
|
|
||||||
|
// compile-flags: --test
|
||||||
|
|
||||||
|
// error-pattern:panicked at 'bar'
|
||||||
|
// check-stdout
|
||||||
|
#[test]
|
||||||
|
#[should_panic(expected = "foo")]
|
||||||
|
pub fn test_bar() {
|
||||||
|
panic!("bar")
|
||||||
|
}
|
||||||
19
src/test/run-fail/test-should-panic-no-message.rs
Normal file
19
src/test/run-fail/test-should-panic-no-message.rs
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
// Copyright 2014 The Rust Project Developers. See the COPYRIGHT
|
||||||
|
// file at the top-level directory of this distribution and at
|
||||||
|
// http://rust-lang.org/COPYRIGHT.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||||
|
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||||
|
// option. This file may not be copied, modified, or distributed
|
||||||
|
// except according to those terms.
|
||||||
|
|
||||||
|
// compile-flags: --test
|
||||||
|
|
||||||
|
// error-pattern:panicked at 'explicit panic'
|
||||||
|
// check-stdout
|
||||||
|
#[test]
|
||||||
|
#[should_panic(expected = "foo")]
|
||||||
|
pub fn test_explicit() {
|
||||||
|
panic!()
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user