mirror of
				https://github.com/catchorg/Catch2.git
				synced 2025-10-31 12:17:11 +01:00 
			
		
		
		
	Added support for manually registering test functions.
As discussed in #421
This commit is contained in:
		| @@ -96,6 +96,7 @@ | ||||
|     #define CATCH_TEST_CASE( ... ) INTERNAL_CATCH_TESTCASE( __VA_ARGS__ ) | ||||
|     #define CATCH_TEST_CASE_METHOD( className, ... ) INTERNAL_CATCH_TEST_CASE_METHOD( className, __VA_ARGS__ ) | ||||
|     #define CATCH_METHOD_AS_TEST_CASE( method, ... ) INTERNAL_CATCH_METHOD_AS_TEST_CASE( method, __VA_ARGS__ ) | ||||
|     #define CATCH_REGISTER_TEST_CASE( ... ) INTERNAL_CATCH_REGISTER_TESTCASE( __VA_ARGS__ ) | ||||
|     #define CATCH_SECTION( ... ) INTERNAL_CATCH_SECTION( __VA_ARGS__ ) | ||||
|     #define CATCH_FAIL( ... ) INTERNAL_CATCH_MSG( Catch::ResultWas::ExplicitFailure, Catch::ResultDisposition::Normal, "CATCH_FAIL", __VA_ARGS__ ) | ||||
|     #define CATCH_SUCCEED( ... ) INTERNAL_CATCH_MSG( Catch::ResultWas::Ok, Catch::ResultDisposition::ContinueOnFailure, "CATCH_SUCCEED", __VA_ARGS__ ) | ||||
| @@ -103,6 +104,7 @@ | ||||
|     #define CATCH_TEST_CASE( name, description ) INTERNAL_CATCH_TESTCASE( name, description ) | ||||
|     #define CATCH_TEST_CASE_METHOD( className, name, description ) INTERNAL_CATCH_TEST_CASE_METHOD( className, name, description ) | ||||
|     #define CATCH_METHOD_AS_TEST_CASE( method, name, description ) INTERNAL_CATCH_METHOD_AS_TEST_CASE( method, name, description ) | ||||
|     #define CATCH_REGISTER_TEST_CASE( function, name, description ) INTERNAL_CATCH_REGISTER_TESTCASE( function, name, description ) | ||||
|     #define CATCH_SECTION( name, description ) INTERNAL_CATCH_SECTION( name, description ) | ||||
|     #define CATCH_FAIL( msg ) INTERNAL_CATCH_MSG( Catch::ResultWas::ExplicitFailure, Catch::ResultDisposition::Normal, "CATCH_FAIL", msg ) | ||||
|     #define CATCH_SUCCEED( msg ) INTERNAL_CATCH_MSG( Catch::ResultWas::Ok, Catch::ResultDisposition::ContinueOnFailure, "CATCH_SUCCEED", msg ) | ||||
| @@ -161,6 +163,7 @@ | ||||
|     #define TEST_CASE( ... ) INTERNAL_CATCH_TESTCASE( __VA_ARGS__ ) | ||||
|     #define TEST_CASE_METHOD( className, ... ) INTERNAL_CATCH_TEST_CASE_METHOD( className, __VA_ARGS__ ) | ||||
|     #define METHOD_AS_TEST_CASE( method, ... ) INTERNAL_CATCH_METHOD_AS_TEST_CASE( method, __VA_ARGS__ ) | ||||
|     #define REGISTER_TEST_CASE( ... ) INTERNAL_CATCH_REGISTER_TESTCASE( __VA_ARGS__ ) | ||||
|     #define SECTION( ... ) INTERNAL_CATCH_SECTION( __VA_ARGS__ ) | ||||
|     #define FAIL( ... ) INTERNAL_CATCH_MSG( Catch::ResultWas::ExplicitFailure, Catch::ResultDisposition::Normal, "FAIL", __VA_ARGS__ ) | ||||
|     #define SUCCEED( ... ) INTERNAL_CATCH_MSG( Catch::ResultWas::Ok, Catch::ResultDisposition::ContinueOnFailure, "SUCCEED", __VA_ARGS__ ) | ||||
| @@ -168,6 +171,7 @@ | ||||
|     #define TEST_CASE( name, description ) INTERNAL_CATCH_TESTCASE( name, description ) | ||||
|     #define TEST_CASE_METHOD( className, name, description ) INTERNAL_CATCH_TEST_CASE_METHOD( className, name, description ) | ||||
|     #define METHOD_AS_TEST_CASE( method, name, description ) INTERNAL_CATCH_METHOD_AS_TEST_CASE( method, name, description ) | ||||
|     #define REGISTER_TEST_CASE( ... ) INTERNAL_CATCH_REGISTER_TESTCASE( __VA_ARGS__ ) | ||||
|     #define SECTION( name, description ) INTERNAL_CATCH_SECTION( name, description ) | ||||
|     #define FAIL( msg ) INTERNAL_CATCH_MSG( Catch::ResultWas::ExplicitFailure, Catch::ResultDisposition::Normal, "FAIL", msg ) | ||||
|     #define SUCCEED( msg ) INTERNAL_CATCH_MSG( Catch::ResultWas::Ok, Catch::ResultDisposition::ContinueOnFailure, "SUCCEED", msg ) | ||||
|   | ||||
| @@ -151,29 +151,38 @@ namespace Catch { | ||||
|         return className; | ||||
|     } | ||||
|  | ||||
|     void registerTestCase | ||||
|         (   ITestCase* testCase, | ||||
|             char const* classOrQualifiedMethodName, | ||||
|             NameAndDesc const& nameAndDesc, | ||||
|             SourceLineInfo const& lineInfo ) { | ||||
|          | ||||
|         getMutableRegistryHub().registerTest | ||||
|             ( makeTestCase | ||||
|                 (   testCase, | ||||
|                     extractClassName( classOrQualifiedMethodName ), | ||||
|                     nameAndDesc.name, | ||||
|                     nameAndDesc.description, | ||||
|                     lineInfo ) ); | ||||
|     } | ||||
|     void registerTestCaseFunction | ||||
|         (   TestFunction function, | ||||
|             SourceLineInfo const& lineInfo, | ||||
|             NameAndDesc const& nameAndDesc ) { | ||||
|         registerTestCase( new FreeFunctionTestCase( function ), "", nameAndDesc, lineInfo ); | ||||
|     } | ||||
|      | ||||
|     /////////////////////////////////////////////////////////////////////////// | ||||
|  | ||||
|     AutoReg::AutoReg(   TestFunction function, | ||||
|                         SourceLineInfo const& lineInfo, | ||||
|                         NameAndDesc const& nameAndDesc ) { | ||||
|         registerTestCase( new FreeFunctionTestCase( function ), "", nameAndDesc, lineInfo ); | ||||
|     AutoReg::AutoReg | ||||
|         (   TestFunction function, | ||||
|             SourceLineInfo const& lineInfo, | ||||
|             NameAndDesc const& nameAndDesc ) { | ||||
|         registerTestCaseFunction( function, lineInfo, nameAndDesc ); | ||||
|     } | ||||
|  | ||||
|     AutoReg::~AutoReg() {} | ||||
|  | ||||
|     void AutoReg::registerTestCase( ITestCase* testCase, | ||||
|                                     char const* classOrQualifiedMethodName, | ||||
|                                     NameAndDesc const& nameAndDesc, | ||||
|                                     SourceLineInfo const& lineInfo ) { | ||||
|  | ||||
|         getMutableRegistryHub().registerTest | ||||
|             ( makeTestCase( testCase, | ||||
|                             extractClassName( classOrQualifiedMethodName ), | ||||
|                             nameAndDesc.name, | ||||
|                             nameAndDesc.description, | ||||
|                             lineInfo ) ); | ||||
|     } | ||||
|  | ||||
| } // end namespace Catch | ||||
|  | ||||
|  | ||||
|   | ||||
| @@ -42,27 +42,32 @@ struct NameAndDesc { | ||||
|     const char* description; | ||||
| }; | ||||
|  | ||||
| void registerTestCase | ||||
|     (   ITestCase* testCase, | ||||
|         char const* className, | ||||
|         NameAndDesc const& nameAndDesc, | ||||
|         SourceLineInfo const& lineInfo ); | ||||
|  | ||||
| struct AutoReg { | ||||
|  | ||||
|     AutoReg(    TestFunction function, | ||||
|                 SourceLineInfo const& lineInfo, | ||||
|                 NameAndDesc const& nameAndDesc ); | ||||
|     AutoReg | ||||
|         (   TestFunction function, | ||||
|             SourceLineInfo const& lineInfo, | ||||
|             NameAndDesc const& nameAndDesc ); | ||||
|  | ||||
|     template<typename C> | ||||
|     AutoReg(    void (C::*method)(), | ||||
|                 char const* className, | ||||
|                 NameAndDesc const& nameAndDesc, | ||||
|                 SourceLineInfo const& lineInfo ) { | ||||
|         registerTestCase(   new MethodTestCase<C>( method ), | ||||
|                             className, | ||||
|                             nameAndDesc, | ||||
|                             lineInfo ); | ||||
|     } | ||||
|     AutoReg | ||||
|         (   void (C::*method)(), | ||||
|             char const* className, | ||||
|             NameAndDesc const& nameAndDesc, | ||||
|             SourceLineInfo const& lineInfo ) { | ||||
|  | ||||
|     void registerTestCase(  ITestCase* testCase, | ||||
|                             char const* className, | ||||
|                             NameAndDesc const& nameAndDesc, | ||||
|                             SourceLineInfo const& lineInfo ); | ||||
|         registerTestCase | ||||
|             (   new MethodTestCase<C>( method ), | ||||
|                 className, | ||||
|                 nameAndDesc, | ||||
|                 lineInfo ); | ||||
|     } | ||||
|  | ||||
|     ~AutoReg(); | ||||
|  | ||||
| @@ -71,6 +76,11 @@ private: | ||||
|     void operator= ( AutoReg const& ); | ||||
| }; | ||||
|  | ||||
| void registerTestCaseFunction | ||||
|     (   TestFunction function, | ||||
|         SourceLineInfo const& lineInfo, | ||||
|         NameAndDesc const& nameAndDesc ); | ||||
|  | ||||
| } // end namespace Catch | ||||
|  | ||||
| #ifdef CATCH_CONFIG_VARIADIC_MACROS | ||||
| @@ -94,6 +104,10 @@ private: | ||||
|         } \ | ||||
|         void INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_S_T____ )::test() | ||||
|  | ||||
|     /////////////////////////////////////////////////////////////////////////////// | ||||
|     #define INTERNAL_CATCH_REGISTER_TESTCASE( Function, ... ) \ | ||||
|         Catch::AutoReg( Function, CATCH_INTERNAL_LINEINFO, Catch::NameAndDesc( __VA_ARGS__ ) ); | ||||
|  | ||||
| #else | ||||
|     /////////////////////////////////////////////////////////////////////////////// | ||||
|     #define INTERNAL_CATCH_TESTCASE( Name, Desc ) \ | ||||
| @@ -115,6 +129,9 @@ private: | ||||
|         } \ | ||||
|         void INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_S_T____ )::test() | ||||
|  | ||||
|     /////////////////////////////////////////////////////////////////////////////// | ||||
|     #define INTERNAL_CATCH_REGISTER_TESTCASE( Function, Name, Desc ) \ | ||||
|         Catch::AutoReg( Function, CATCH_INTERNAL_LINEINFO, Catch::NameAndDesc( Name, Desc ) ); | ||||
| #endif | ||||
|  | ||||
| #endif // TWOBLUECUBES_CATCH_TEST_REGISTRY_HPP_INCLUDED | ||||
|   | ||||
| @@ -830,6 +830,6 @@ with expansion: | ||||
|   "first" == "second" | ||||
|  | ||||
| =============================================================================== | ||||
| test cases: 164 | 121 passed | 42 failed |  1 failed as expected | ||||
| assertions: 767 | 671 passed | 83 failed | 13 failed as expected | ||||
| test cases: 165 | 122 passed | 42 failed |  1 failed as expected | ||||
| assertions: 768 | 672 passed | 83 failed | 13 failed as expected | ||||
|  | ||||
|   | ||||
| @@ -4684,6 +4684,17 @@ with expansion: | ||||
|   ************************ | ||||
| ... message truncated due to excessive size | ||||
|  | ||||
| ------------------------------------------------------------------------------- | ||||
| ManuallyRegistered | ||||
| ------------------------------------------------------------------------------- | ||||
| TestMain.cpp:<line number> | ||||
| ............................................................................... | ||||
|  | ||||
| TestMain.cpp:<line number>: | ||||
| PASSED: | ||||
| with message: | ||||
|   was called | ||||
|  | ||||
| ------------------------------------------------------------------------------- | ||||
| Parsing a std::pair | ||||
| ------------------------------------------------------------------------------- | ||||
| @@ -7714,6 +7725,6 @@ with expansion: | ||||
|   1 > 0 | ||||
|  | ||||
| =============================================================================== | ||||
| test cases: 164 | 120 passed | 43 failed |  1 failed as expected | ||||
| assertions: 769 | 671 passed | 85 failed | 13 failed as expected | ||||
| test cases: 165 | 121 passed | 43 failed |  1 failed as expected | ||||
| assertions: 770 | 672 passed | 85 failed | 13 failed as expected | ||||
|  | ||||
|   | ||||
| @@ -1,5 +1,5 @@ | ||||
| <testsuites> | ||||
|   <testsuite name="CatchSelfTest" errors="13" failures="72" tests="769" hostname="tbd" time="{duration}" timestamp="tbd"> | ||||
|   <testsuite name="CatchSelfTest" errors="13" failures="72" tests="770" hostname="tbd" time="{duration}" timestamp="tbd"> | ||||
|     <testcase classname="global" name="toString(enum)" time="{duration}"/> | ||||
|     <testcase classname="global" name="toString(enum w/operator<<)" time="{duration}"/> | ||||
|     <testcase classname="global" name="toString(enum class)" time="{duration}"/> | ||||
| @@ -545,6 +545,7 @@ hello | ||||
|     </testcase> | ||||
|     <testcase classname="global" name="Text can be formatted using the Text class" time="{duration}"/> | ||||
|     <testcase classname="global" name="Long text is truncted" time="{duration}"/> | ||||
|     <testcase classname="global" name="ManuallyRegistered" time="{duration}"/> | ||||
|     <testcase classname="global" name="Parsing a std::pair" time="{duration}"/> | ||||
|     <testcase classname="global" name="Where there is more to the expression after the RHS" time="{duration}"/> | ||||
|     <testcase classname="global" name="Where the LHS is not a simple value" time="{duration}"/> | ||||
|   | ||||
| @@ -5110,6 +5110,9 @@ there" | ||||
|       </Expression> | ||||
|       <OverallResult success="true"/> | ||||
|     </TestCase> | ||||
|     <TestCase name="ManuallyRegistered"> | ||||
|       <OverallResult success="true"/> | ||||
|     </TestCase> | ||||
|     <TestCase name="Parsing a std::pair"> | ||||
|       <Expression success="true" type="REQUIRE" filename="projects/SelfTest/TrickyTests.cpp" > | ||||
|         <Original> | ||||
| @@ -8328,7 +8331,7 @@ there" | ||||
|       </Section> | ||||
|       <OverallResult success="true"/> | ||||
|     </TestCase> | ||||
|     <OverallResults successes="671" failures="85" expectedFailures="13"/> | ||||
|     <OverallResults successes="672" failures="85" expectedFailures="13"/> | ||||
|   </Group> | ||||
|   <OverallResults successes="671" failures="85" expectedFailures="13"/> | ||||
|   <OverallResults successes="672" failures="85" expectedFailures="13"/> | ||||
| </Catch> | ||||
|   | ||||
| @@ -449,3 +449,13 @@ TEST_CASE( "Long text is truncted", "[Text][Truncated]" ) { | ||||
|     CHECK_THAT( t.toString(), EndsWith( "... message truncated due to excessive size" ) ); | ||||
|  | ||||
| } | ||||
|  | ||||
| inline void manuallyRegisteredTestFunction() { | ||||
|     SUCCEED( "was called" ); | ||||
| } | ||||
| struct AutoTestReg { | ||||
|     AutoTestReg() { | ||||
|         REGISTER_TEST_CASE( manuallyRegisteredTestFunction, "ManuallyRegistered", "" ); | ||||
|     } | ||||
| }; | ||||
| AutoTestReg autoTestReg; | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 Phil Nash
					Phil Nash