3 Matchers are an alternative way to do assertions which are easily extensible and composable.
4 This makes them well suited to use with more complex types (such as collections) or your own custom types.
5 Matchers were first popularised by the [Hamcrest](https://en.wikipedia.org/wiki/Hamcrest) family of frameworks.
9 Matchers are introduced with the `REQUIRE_THAT` or `CHECK_THAT` macros, which take two arguments.
10 The first argument is the thing (object or value) under test. The second part is a match _expression_,
11 which consists of either a single matcher or one or more matchers combined using `&&`, `||` or `!` operators.
13 For example, to assert that a string ends with a certain substring:
16 using Catch::Matchers::EndsWith; // or Catch::EndsWith
17 std::string str = getStringFromSomewhere();
18 REQUIRE_THAT( str, EndsWith( "as a service" ) );
21 The matcher objects can take multiple arguments, allowing more fine tuning.
22 The built-in string matchers, for example, take a second argument specifying whether the comparison is
23 case sensitive or not:
26 REQUIRE_THAT( str, EndsWith( "as a service", Catch::CaseSensitive::No ) );
29 And matchers can be combined:
33 EndsWith( "as a service" ) ||
34 (StartsWith( "Big data" ) && !Contains( "web scale" ) ) );
38 Currently Catch has some string matchers and some vector matchers. They are in the `Catch::Matchers` and `Catch` namespaces.
39 The string matchers are `StartsWith`, `EndsWith`, `Contains` and `Equals`. Each of them also takes an optional second argument, that decides case sensitivity (by-default, they are case sensitive).
40 The vector matchers are `Contains`, `VectorContains` and `Equals`. `VectorContains` looks for a single element in the matched vector, `Contains` looks for a set (vector) of elements inside the matched vector.
44 It's easy to provide your own matchers to extend Catch or just to work with your own types.
46 You need to provide two things:
47 1. A matcher class, derived from `Catch::MatcherBase<T>` - where `T` is the type being tested.
48 The constructor takes and stores any arguments needed (e.g. something to compare against) and you must
49 override two methods: `match()` and `describe()`.
50 2. A simple builder function. This is what is actually called from the test code and allows overloading.
52 Here's an example for asserting that an integer falls within a given range
53 (note that it is all inline for the sake of keeping the example short):
57 class IntRange : public Catch::MatcherBase<int> {
60 IntRange( int begin, int end ) : m_begin( begin ), m_end( end ) {}
62 // Performs the test for this matcher
63 virtual bool match( int const& i ) const override {
64 return i >= m_begin && i <= m_end;
67 // Produces a string describing what this matcher does. It should
68 // include any provided data (the begin/ end in this case) and
69 // be written as if it were stating a fact (in the output it will be
70 // preceded by the value under test).
71 virtual std::string describe() const {
72 std::ostringstream ss;
73 ss << "is between " << m_begin << " and " << m_end;
78 // The builder function
79 inline IntRange IsBetween( int begin, int end ) {
80 return IntRange( begin, end );
86 TEST_CASE("Integers are within a range")
88 CHECK_THAT( 3, IsBetween( 1, 10 ) );
89 CHECK_THAT( 100, IsBetween( 1, 10 ) );
93 Running this test gives the following in the console:
96 /**/TestFile.cpp:123: FAILED:
97 CHECK_THAT( 100, IsBetween( 1, 10 ) )
99 100 is between 1 and 10