1 #ifndef WREPORT_TESTS_H 2 #define WREPORT_TESTS_H 73 std::string local_info;
76 : file(file_), line(line_), call(call_)
82 : file(file_), line(line_), call(call_), local_info(local_info_.str())
86 std::string format()
const;
88 void format(std::ostream& out)
const;
91 struct TestStack :
public std::vector<TestStackFrame>
113 template <
typename... Args>
116 add_stack_info(std::forward<Args>(args)...);
119 explicit TestFailed(
const std::string& message_) : message(message_) {}
121 template <
typename... Args>
122 TestFailed(
const std::string& message_, Args&&... args)
125 add_stack_info(std::forward<Args>(args)...);
128 const char* what()
const noexcept
override {
return message.c_str(); }
130 template <
typename... Args>
void add_stack_info(Args&&... args)
132 stack.emplace_back(std::forward<Args>(args)...);
151 #define WREPORT_TEST_INFO(name) \ 152 wreport::tests::LocationInfo wreport_test_location_info; \ 153 wreport::tests::LocationInfo& name = wreport_test_location_info 162 template <
typename A>
void assert_true(
const A& actual)
167 std::stringstream ss;
168 ss <<
"actual value " << actual <<
" is not true";
172 [[noreturn]]
void assert_true(std::nullptr_t actual);
175 template <
typename A>
void assert_false(
const A& actual)
179 std::stringstream ss;
180 ss <<
"actual value " << actual <<
" is not false";
181 throw TestFailed(ss.str());
184 void assert_false(std::nullptr_t actual);
186 template <
typename LIST>
187 static inline void _format_list(std::ostream& o,
const LIST& list)
191 for (
const auto& v : list)
202 template <
typename T>
203 void assert_equal(
const std::vector<T>& actual,
const std::vector<T>& expected)
205 if (actual == expected)
207 std::stringstream ss;
209 _format_list(ss, actual);
210 ss <<
" is different than the expected ";
211 _format_list(ss, expected);
212 throw TestFailed(ss.str());
215 template <
typename T>
216 void assert_equal(
const std::vector<T>& actual,
217 const std::initializer_list<T>& expected)
219 if (actual == expected)
221 std::stringstream ss;
223 _format_list(ss, actual);
224 ss <<
" is different than the expected ";
225 _format_list(ss, expected);
226 throw TestFailed(ss.str());
233 template <
typename A,
typename E>
234 void assert_equal(
const A& actual,
const E& expected)
236 if (actual == expected)
238 std::stringstream ss;
239 ss <<
"value '" << actual <<
"' is different than the expected '" 241 throw TestFailed(ss.str());
248 template <
typename A,
typename E>
249 void assert_not_equal(
const A& actual,
const E& expected)
251 if (actual != expected)
253 std::stringstream ss;
254 ss <<
"value '" << actual <<
"' is not different than the expected '" 256 throw TestFailed(ss.str());
260 template <
typename A,
typename E>
261 void assert_less(
const A& actual,
const E& expected)
263 if (actual < expected)
265 std::stringstream ss;
266 ss <<
"value '" << actual <<
"' is not less than the expected '" << expected
268 throw TestFailed(ss.str());
272 template <
typename A,
typename E>
273 void assert_less_equal(
const A& actual,
const E& expected)
275 if (actual <= expected)
277 std::stringstream ss;
278 ss <<
"value '" << actual
279 <<
"' is not less than or equals to the expected '" << expected <<
"'";
280 throw TestFailed(ss.str());
284 template <
typename A,
typename E>
285 void assert_greater(
const A& actual,
const E& expected)
287 if (actual > expected)
289 std::stringstream ss;
290 ss <<
"value '" << actual <<
"' is not greater than the expected '" 292 throw TestFailed(ss.str());
296 template <
typename A,
typename E>
297 void assert_greater_equal(
const A& actual,
const E& expected)
299 if (actual >= expected)
301 std::stringstream ss;
302 ss <<
"value '" << actual
303 <<
"' is not greater than or equals to the expected '" << expected
305 throw TestFailed(ss.str());
309 void assert_startswith(
const std::string& actual,
const std::string& expected);
312 void assert_endswith(
const std::string& actual,
const std::string& expected);
315 void assert_contains(
const std::string& actual,
const std::string& expected);
318 void assert_not_contains(
const std::string& actual,
319 const std::string& expected);
327 void assert_re_matches(
const std::string& actual,
const std::string& expected);
335 void assert_not_re_matches(
const std::string& actual,
336 const std::string& expected);
341 Actual(
const A& actual) : _actual(actual) {}
348 void istrue()
const { assert_true(_actual); }
349 void isfalse()
const { assert_false(_actual); }
350 template <
typename E>
void operator==(
const E& expected)
const 352 assert_equal(_actual, expected);
354 template <
typename E>
void operator!=(
const E& expected)
const 356 assert_not_equal(_actual, expected);
358 template <
typename E>
void operator<(
const E& expected)
const 360 return assert_less(_actual, expected);
362 template <
typename E>
void operator<=(
const E& expected)
const 364 return assert_less_equal(_actual, expected);
366 template <
typename E>
void operator>(
const E& expected)
const 368 return assert_greater(_actual, expected);
370 template <
typename E>
void operator>=(
const E& expected)
const 372 return assert_greater_equal(_actual, expected);
381 void istrue()
const {
return assert_true(_actual); }
382 void isfalse()
const {
return assert_false(_actual); }
383 void operator==(
const char* expected)
const;
384 void operator==(
const std::string& expected)
const;
385 void operator!=(
const char* expected)
const;
386 void operator!=(
const std::string& expected)
const;
387 void operator<(
const std::string& expected)
const;
388 void operator<=(
const std::string& expected)
const;
389 void operator>(
const std::string& expected)
const;
390 void operator>=(
const std::string& expected)
const;
391 void startswith(
const std::string& expected)
const;
392 void endswith(
const std::string& expected)
const;
393 void contains(
const std::string& expected)
const;
394 void not_contains(
const std::string& expected)
const;
395 void matches(
const std::string& re)
const;
396 void not_matches(
const std::string& re)
const;
404 void operator==(
const std::vector<uint8_t>& expected)
const;
406 void operator!=(
const std::vector<uint8_t>& expected)
const;
407 void startswith(
const std::string& expected)
const;
408 void endswith(
const std::string& expected)
const;
409 void contains(
const std::string& expected)
const;
410 void not_contains(
const std::string& expected)
const;
411 void matches(
const std::string& re)
const;
412 void not_matches(
const std::string& re)
const;
417 explicit ActualPath(
const std::filesystem::path& p)
426 void is(
const std::filesystem::path& expected)
const;
427 [[deprecated(
"Use path_startswith")]]
void 428 startswith(
const std::string& data)
const;
430 void path_startswith(
const std::filesystem::path& expected)
const;
431 void path_endswith(
const std::filesystem::path& expected)
const;
432 void path_contains(
const std::filesystem::path& expected)
const;
433 void path_not_contains(
const std::filesystem::path& expected)
const;
436 void not_exists()
const;
438 void not_empty()
const;
440 void contents_startwith(
const std::string& data)
const;
441 void contents_equal(
const std::string& data)
const;
442 void contents_equal(
const std::vector<uint8_t>& data)
const;
443 void contents_equal(
const std::initializer_list<std::string>& lines)
const;
444 void contents_match(
const std::string& data_re)
const;
446 contents_match(
const std::initializer_list<std::string>& lines_re)
const;
451 using Actual::Actual;
453 void almost_equal(
double expected,
unsigned places)
const;
454 void not_almost_equal(
double expected,
unsigned places)
const;
457 template <
typename A>
inline Actual<A> actual(
const A& actual)
461 inline ActualCString actual(
const char* actual)
463 return ActualCString(actual);
465 inline ActualCString actual(
char* actual) {
return ActualCString(actual); }
466 inline ActualStdString actual(
const std::string& actual)
468 return ActualStdString(actual);
470 inline ActualStdString actual(
const std::vector<uint8_t>& actual)
472 return ActualStdString(std::string(actual.begin(), actual.end()));
474 inline ActualPath actual(
const std::filesystem::path& actual)
476 return ActualPath(actual);
478 inline ActualDouble actual(
double actual) {
return ActualDouble(actual); }
482 using Actual::Actual;
484 void throws(
const std::string& what_match)
const;
487 inline ActualFunction actual_function(std::function<
void()> actual)
492 inline ActualPath actual_path(
const char* pathname)
494 return ActualPath(pathname);
496 inline ActualPath actual_path(
const std::string& pathname)
498 return ActualPath(pathname);
500 inline ActualPath actual_file(
const char* pathname)
502 return ActualPath(pathname);
504 inline ActualPath actual_file(
const std::string& pathname)
506 return ActualPath(pathname);
516 #define wassert(...) \ 523 catch (wreport::tests::TestFailed & e1) \ 525 e1.add_stack_info(__FILE__, __LINE__, #__VA_ARGS__, \ 526 wreport_test_location_info); \ 529 catch (std::exception & e2) \ 531 throw wreport::tests::TestFailed(e2, __FILE__, __LINE__, \ 533 wreport_test_location_info); \ 538 #define wassert_true(...) wassert(actual(__VA_ARGS__).istrue()) 541 #define wassert_false(...) wassert(actual(__VA_ARGS__).isfalse()) 548 #define wassert_throws(exc, ...) \ 553 wfail_test(#__VA_ARGS__ " did not throw " #exc); \ 555 catch (TestFailed & e1) \ 563 catch (std::exception & e3) \ 565 std::string msg(#__VA_ARGS__ " did not throw " #exc \ 567 msg += typeid(e3).name(); \ 580 #define wcallchecked(func) \ 586 catch (wreport::tests::TestFailed & e) \ 588 e.add_stack_info(__FILE__, __LINE__, #func, \ 589 wreport_test_location_info); \ 592 catch (std::exception & e) \ 594 throw wreport::tests::TestFailed(e, __FILE__, __LINE__, #func, \ 595 wreport_test_location_info); \ 602 #define wfail_test(msg) wassert(throw wreport::tests::TestFailed((msg))) 605 struct TestController;
607 struct TestCaseResult;
609 struct TestMethodResult;
631 TestMethod(
const std::string& name_, std::function<
void()> test_function_)
736 template <
typename... Args>
738 std::function<
void()> test_function)
740 methods.emplace_back(name_, test_function);
747 template <
typename... Args>
749 std::function<
void()> test_function)
751 methods.emplace_back(name_, test_function);
773 void test_teardown() {}
776 template <
typename Fixture,
typename... Args>
777 static inline Fixture* fixture_factory(Args... args)
788 typedef FIXTURE Fixture;
790 Fixture* fixture =
nullptr;
791 std::function<Fixture*()> make_fixture;
793 template <
typename... Args>
796 make_fixture = std::bind(fixture_factory<FIXTURE, Args...>, args...);
806 fixture = make_fixture();
820 fixture->test_setup();
826 fixture->test_teardown();
834 template <
typename... Args>
836 std::function<
void(FIXTURE&)> test_function)
845 template <
typename... Args>
847 std::function<
void(FIXTURE&)> test_function)
850 [=]() { test_function(*fixture); });
virtual TestCaseResult run_tests(TestController &controller)
Call setup(), run all the tests that have been registered, then call teardown().
Result of running a whole test case.
Definition: testrunner.h:92
Test case collecting several test methods, and self-registering with the singleton instance of TestRe...
Definition: utils/tests.h:641
std::string name
Name of the test case.
Definition: utils/tests.h:644
Information about one stack frame in the test execution stack.
Definition: utils/tests.h:68
Add information to the test backtrace for the tests run in the current scope.
Definition: utils/tests.h:56
Exception thrown when a test or a test case needs to be skipped.
Definition: utils/tests.h:139
virtual void method_setup(TestMethodResult &)
Set up before the test method is run.
Definition: utils/tests.h:692
void register_tests_once()
Idempotent wrapper for register_tests()
virtual void test_teardown()
Clean up after each test method is run.
Definition: utils/tests.h:687
bool tests_registered
Set to true the first time register_tests_once is run.
Definition: utils/tests.h:650
Abstract interface for the objects that supervise test execution.
Definition: testrunner.h:157
Definition: utils/tests.h:338
virtual void test_setup()
Set up before each test method is run.
Definition: utils/tests.h:682
virtual TestMethodResult run_test(TestController &controller, TestMethod &method)
Run a test method.
void teardown() override
Clean up after the test case is run.
Definition: utils/tests.h:809
Exception thrown when a test assertion fails, normally by Location::fail_test.
Definition: utils/tests.h:106
Definition: utils/tests.h:415
void method_teardown(TestMethodResult &mr) override
Clean up after the test method is run.
Definition: utils/tests.h:823
std::vector< TestMethod > methods
All registered test methods.
Definition: utils/tests.h:647
std::string backtrace() const
Return the formatted backtrace for this location.
TestMethod & add_method(const std::string &name_, const std::string &doc, std::function< void()> test_function)
Register a new test method, including documentation.
Definition: utils/tests.h:748
Definition: utils/tests.h:91
virtual void setup()
Set up the test case before it is run.
Definition: utils/tests.h:672
Definition: utils/tests.h:376
std::string doc
Documentation attached to this test method.
Definition: utils/tests.h:620
Definition: utils/tests.h:480
Definition: utils/tests.h:449
Result of running a test method.
Definition: testrunner.h:25
TestMethod & add_method(const std::string &name_, const std::string &doc, std::function< void(FIXTURE &)> test_function)
Register a new test method that takes a reference to the fixture as argument, including documentation...
Definition: utils/tests.h:846
void setup() override
Set up the test case before it is run.
Definition: utils/tests.h:803
std::function< void()> test_function
Main body of the test method.
Definition: utils/tests.h:627
void method_setup(TestMethodResult &mr) override
Set up before the test method is run.
Definition: utils/tests.h:816
Definition: utils/tests.h:399
virtual void register_tests()=0
This will be called before running the test case, to populate it with its test methods.
TestMethod & add_method(const std::string &name_)
Register a new test method, with the actual test function to be added later.
Definition: utils/tests.h:727
String functions.
Definition: benchmark.h:13
Test case that includes a fixture.
Definition: utils/tests.h:785
TestMethod & add_method(const std::string &name_, std::function< void()> test_function)
Register a new test method.
Definition: utils/tests.h:737
Test method information.
Definition: utils/tests.h:614
virtual void method_teardown(TestMethodResult &)
Clean up after the test method is run.
Definition: utils/tests.h:697
virtual void teardown()
Clean up after the test case is run.
Definition: utils/tests.h:677
TestMethod & add_method(const std::string &name_, std::function< void(FIXTURE &)> test_function)
Register a new test method that takes a reference to the fixture as argument.
Definition: utils/tests.h:835
std::string name
Name of the test method.
Definition: utils/tests.h:617
Base class for test fixtures.
Definition: utils/tests.h:767
std::ostream & operator()()
Clear the current information and return the output stream to which new information can be sent...