mirror of
https://github.com/catchorg/Catch2.git
synced 2024-11-17 03:02:24 +01:00
merge from tags
This commit is contained in:
commit
760eed1ad6
6
.gitignore
vendored
6
.gitignore
vendored
@ -10,6 +10,12 @@ Debug
|
||||
Release
|
||||
ipch
|
||||
TestResults
|
||||
projects/VS2010/TestCatch/Visual Lint
|
||||
projects/VS2010/ManagedTestCatch/Visual Lint
|
||||
projects/VS2012/ManagedTestCatch/Visual Lint
|
||||
projects/VS2012/NativeTestCatch/Visual Lint
|
||||
DebugMbcs
|
||||
ReleaseMbcs
|
||||
*.user
|
||||
*.xcuserstate
|
||||
*.o
|
||||
|
8
docs/vs/VScommandlinetags.md
Normal file
8
docs/vs/VScommandlinetags.md
Normal file
@ -0,0 +1,8 @@
|
||||
If you've used the Catch command line, you might know that Catch can selectively include and exclude tests using tags. For example, you might want to exclude long running tests from each check-in to your CI server, so you might tag those tests with `[slow]` and run Catch with `example.exe ~[slow]`.
|
||||
|
||||
It doesn't look like it's possible to reproduce the flexibility of Catch but it is possible to do some basic filtering using Catch tags.
|
||||
|
||||
|
||||
---
|
||||
|
||||
[Home](../../README.md)
|
@ -20,7 +20,15 @@ We can do the same for VS2012 - [see this page for instructions on how to do thi
|
||||
|
||||
# Running tests from the command line
|
||||
|
||||
Tests can also be run from the command line. [For VS2010 see these details](VS2010commandline.md) and [for VS2012 see these](VS2012commandline.md)
|
||||
Tests can also be run from the command line. [For VS2010 see these details](VS2010commandline.md) and [for VS2012 see these](VS2012commandline.md).
|
||||
|
||||
# Running tests using Catch tags
|
||||
|
||||
If you've used the Catch command line, you'll know that Catch can selectively include and exclude tests using tags. For example, you might want to exclude long running tests from each check-in to your CI server, so you might tag those tests with `[slow]` and run Catch with `example.exe ~[slow]`.
|
||||
|
||||
It doesn't look like it's possible to reproduce the flexibility of Catch but it is possible to do some basic filtering using Catch tags.
|
||||
|
||||
[This page details how to do this.](VScommandlinetags.md)
|
||||
|
||||
# Differences in behaviour
|
||||
|
||||
@ -34,7 +42,7 @@ There are some minor differences in behaviour between Catch and Visual Studio pr
|
||||
|
||||
You can still use the same names that you would normally use for Catch TEST_CASE names, however we use an internal name for the actual function name that the test lives in. This means that you won't see the Catch names in the Test View (VS2010) unless you 'Group By' Description, or in VS2012 you select the 'Traits' view Test Explorer - see the screen shots above.
|
||||
|
||||
## Catch tests always stop on first failure.
|
||||
## When running from the GUI, Catch tests always stop on first failure.
|
||||
|
||||
A Catch test that uses SECTIONS will continue to run further sections if one fails; in VS this doesn't make much sense because in a visual environment we want to capture the context of where the test failed. If we allowed the test to continue then we lose this context, so instead we always stop on each failure. You can still use the CHECK macros if you don't want the test to stop.
|
||||
|
||||
|
@ -19,6 +19,7 @@
|
||||
|
||||
#if (_MANAGED == 1) || (_M_CEE == 1) // detect CLR
|
||||
#define INTERNAL_CATCH_VS_MANAGED
|
||||
#define INTERNAL_CATCH_INLINE inline
|
||||
#else
|
||||
|
||||
#if defined(_WINDLL)
|
||||
@ -26,6 +27,7 @@
|
||||
// It's possible that this is not enough for someone so allow it to be overridden...
|
||||
#if !defined( CATCH_CONFIG_MAIN ) && !defined( CATCH_CONFIG_RUNNER )
|
||||
#define INTERNAL_CATCH_VS_NATIVE
|
||||
#define INTERNAL_CATCH_INLINE inline
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@ -52,7 +54,6 @@
|
||||
#endif
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED) || defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
#define INTERNAL_CATCH_INLINE inline
|
||||
#ifdef INTERNAL_CATCH_VS_MANAGED
|
||||
#include "internal/catch_vs_managed_impl.hpp"
|
||||
#else // INTERNAL_CATCH_VS_MANAGED
|
||||
@ -203,6 +204,16 @@
|
||||
#define THEN( desc ) SECTION( " Then: " desc, "" )
|
||||
#define AND_THEN( desc ) SECTION( " And: " desc, "" )
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED) || defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
#define CATCH_MAP_CATEGORY_TO_TAG( Category, Tag ) INTERNAL_CATCH_MAP_CATEGORY_TO_TAG( Category, Tag )
|
||||
#define CATCH_CONFIG_SHOW_SUCCESS( v ) CATCH_INTERNAL_CONFIG_SHOW_SUCCESS( v )
|
||||
#define CATCH_CONFIG_WARN_MISSING_ASSERTIONS( v ) CATCH_INTERNAL_CONFIG_WARN_MISSING_ASSERTIONS( v )
|
||||
#else
|
||||
#define CATCH_MAP_CATEGORY_TO_TAG( Category, Tag )
|
||||
#define CATCH_CONFIG_SHOW_SUCCESS( v )
|
||||
#define CATCH_CONFIG_WARN_MISSING_ASSERTIONS( v )
|
||||
#endif
|
||||
|
||||
using Catch::Detail::Approx;
|
||||
|
||||
#ifdef __clang__
|
||||
|
@ -108,6 +108,8 @@ namespace Catch {
|
||||
std::set<TestCase> m_testsAlreadyRun;
|
||||
};
|
||||
|
||||
#if !defined(INTERNAL_CATCH_VS_MANAGED) && !defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
|
||||
class Session {
|
||||
static bool alreadyInstantiated;
|
||||
|
||||
@ -232,6 +234,8 @@ namespace Catch {
|
||||
|
||||
bool Session::alreadyInstantiated = false;
|
||||
|
||||
#endif // !VS_MANAGED && !VS_NATIVE
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_RUNNER_HPP_INCLUDED
|
||||
|
@ -58,11 +58,7 @@ namespace Catch {
|
||||
.setResultType( matcher.match( arg ) );
|
||||
}
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED)
|
||||
// TestFailureException not defined for CLR
|
||||
#else // detect CLR
|
||||
struct TestFailureException{};
|
||||
#endif
|
||||
struct TestFailureException{};
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
@ -72,7 +68,6 @@ struct TestFailureException{};
|
||||
#if !defined(INTERNAL_CATCH_VS_MANAGED) && !defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
|
||||
// normal Catch
|
||||
#define INTERNAL_CATCH_TEST_FAILURE_EXCEPTION const Catch::TestFailureException&
|
||||
#define INTERNAL_CATCH_TEST_THROW_FAILURE throw Catch::TestFailureException();
|
||||
|
||||
#else // VS integration
|
||||
@ -86,10 +81,9 @@ struct TestFailureException{};
|
||||
std::stringstream _sf; \
|
||||
_sf << r->getExpressionInMacro().c_str() << ", " << r->getMessage().c_str(); \
|
||||
std::string fail = _sf.str(); \
|
||||
Assert::Fail(Catch::convert_string_to_managed(fail)); \
|
||||
Assert::Fail(Catch::convert_string_for_assert(fail)); \
|
||||
}
|
||||
|
||||
#define INTERNAL_CATCH_TEST_FAILURE_EXCEPTION AssertFailedException^
|
||||
#else
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
@ -108,8 +102,6 @@ struct TestFailureException{};
|
||||
Assert::Fail(ws2.c_str(), &li); \
|
||||
}
|
||||
|
||||
#define INTERNAL_CATCH_TEST_FAILURE_EXCEPTION const Catch::TestFailureException&
|
||||
|
||||
#endif // INTERNAL_CATCH_VS_MANAGED
|
||||
|
||||
#endif // detect CLR
|
||||
@ -121,7 +113,7 @@ struct TestFailureException{};
|
||||
if( Catch::ResultAction::Value internal_catch_action = Catch::getResultCapture().acceptExpression( evaluatedExpr, INTERNAL_CATCH_ASSERTIONINFO_NAME ) ) { \
|
||||
if( internal_catch_action & Catch::ResultAction::Debug ) CATCH_BREAK_INTO_DEBUGGER(); \
|
||||
if( internal_catch_action & Catch::ResultAction::Abort ) { INTERNAL_CATCH_TEST_THROW_FAILURE } \
|
||||
if( !Catch::shouldContinueOnFailure( resultDisposition ) ) { INTERNAL_CATCH_TEST_THROW_FAILURE } \
|
||||
if( !Catch::shouldContinueOnFailure( resultDisposition ) ) { throw Catch::TestFailureException(); } \
|
||||
Catch::isTrue( false && originalExpr ); \
|
||||
}
|
||||
|
||||
@ -135,7 +127,7 @@ struct TestFailureException{};
|
||||
INTERNAL_CATCH_ACCEPT_INFO( #expr, macroName, resultDisposition ); \
|
||||
try { \
|
||||
INTERNAL_CATCH_ACCEPT_EXPR( ( Catch::ExpressionDecomposer()->*expr ).endExpression( resultDisposition ), resultDisposition, expr ); \
|
||||
} catch( INTERNAL_CATCH_TEST_FAILURE_EXCEPTION ) { \
|
||||
} catch( const Catch::TestFailureException& ) { \
|
||||
throw; \
|
||||
} catch( ... ) { \
|
||||
INTERNAL_CATCH_ACCEPT_EXPR( Catch::ExpressionResultBuilder( Catch::ResultWas::ThrewException ) << Catch::translateActiveException(), \
|
||||
@ -174,7 +166,7 @@ struct TestFailureException{};
|
||||
INTERNAL_CATCH_ACCEPT_EXPR( Catch::ExpressionResultBuilder( Catch::ResultWas::DidntThrowException ), resultDisposition, false ); \
|
||||
} \
|
||||
} \
|
||||
catch( INTERNAL_CATCH_TEST_FAILURE_EXCEPTION ) { \
|
||||
catch( const Catch::TestFailureException& ) { \
|
||||
throw; \
|
||||
} \
|
||||
catch( exceptionType ) { \
|
||||
@ -218,7 +210,7 @@ struct TestFailureException{};
|
||||
INTERNAL_CATCH_ACCEPT_INFO( #arg " " #matcher, macroName, resultDisposition ); \
|
||||
try { \
|
||||
INTERNAL_CATCH_ACCEPT_EXPR( ( Catch::expressionResultBuilderFromMatcher( ::Catch::Matchers::matcher, arg, #matcher ) ), resultDisposition, false ); \
|
||||
} catch( INTERNAL_CATCH_TEST_FAILURE_EXCEPTION ) { \
|
||||
} catch( const Catch::TestFailureException& ) { \
|
||||
throw; \
|
||||
} catch( ... ) { \
|
||||
INTERNAL_CATCH_ACCEPT_EXPR( ( Catch::ExpressionResultBuilder( Catch::ResultWas::ThrewException ) << Catch::translateActiveException() ), \
|
||||
|
@ -22,6 +22,138 @@
|
||||
#define CATCH_CONFIG_CONSOLE_WIDTH 80
|
||||
#endif
|
||||
|
||||
namespace CatchOverrides {
|
||||
|
||||
class ConfigGuard
|
||||
{
|
||||
public:
|
||||
ConfigGuard()
|
||||
: origConfig(Catch::getCurrentContext().getConfig())
|
||||
{}
|
||||
~ConfigGuard()
|
||||
{
|
||||
Catch::getCurrentMutableContext().setConfig(origConfig);
|
||||
}
|
||||
const Catch::Ptr<Catch::IConfig const>& value() const {return origConfig;}
|
||||
private:
|
||||
ConfigGuard(const ConfigGuard&);
|
||||
ConfigGuard& operator=(const ConfigGuard&);
|
||||
|
||||
const Catch::Ptr<Catch::IConfig const> origConfig;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
class Config
|
||||
{
|
||||
typedef std::map<int, bool> LineData;
|
||||
typedef std::map<std::string, LineData> FileLineData;
|
||||
public:
|
||||
bool includeSuccessfulResults(const std::string& file, int c) const
|
||||
{
|
||||
bool result(false);
|
||||
FileLineData::const_iterator it = showSuccessfulTestsData.find(file);
|
||||
if( it != showSuccessfulTestsData.end() )
|
||||
{
|
||||
for( LineData::const_iterator lineIt = it->second.begin(); lineIt != it->second.end(); ++lineIt )
|
||||
{
|
||||
if( c <= lineIt->first )
|
||||
break;
|
||||
result = lineIt->second;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
void insertSuccessfulResults(const std::string& file, int c, bool v)
|
||||
{
|
||||
FileLineData::iterator it = showSuccessfulTestsData.find(file);
|
||||
if( it == showSuccessfulTestsData.end() )
|
||||
{
|
||||
LineData tmp;
|
||||
tmp.insert(std::make_pair(c,v));
|
||||
showSuccessfulTestsData.insert(std::make_pair(file, tmp));
|
||||
}
|
||||
else
|
||||
{
|
||||
it->second.insert(std::make_pair(c,v));
|
||||
}
|
||||
}
|
||||
bool warnAboutMissingAssertions(const std::string& file, int c) const
|
||||
{
|
||||
bool result(false);
|
||||
FileLineData::const_iterator it = missingAssertionData.find(file);
|
||||
if( it != missingAssertionData.end() )
|
||||
{
|
||||
for( LineData::const_iterator lineIt = it->second.begin(); lineIt != it->second.end(); ++lineIt )
|
||||
{
|
||||
if( c <= lineIt->first )
|
||||
break;
|
||||
result = lineIt->second;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
void insertMissingAssertions(const std::string& file, int c, bool v)
|
||||
{
|
||||
FileLineData::iterator it = missingAssertionData.find(file);
|
||||
if( it == missingAssertionData.end() )
|
||||
{
|
||||
LineData tmp;
|
||||
tmp.insert(std::make_pair(c,v));
|
||||
missingAssertionData.insert(std::make_pair(file, tmp));
|
||||
}
|
||||
else
|
||||
{
|
||||
it->second.insert(std::make_pair(c,v));
|
||||
}
|
||||
}
|
||||
static Config<T>& instance()
|
||||
{
|
||||
if( !s_instance )
|
||||
{
|
||||
s_instance = new Config<T>();
|
||||
}
|
||||
return *s_instance;
|
||||
}
|
||||
private:
|
||||
FileLineData showSuccessfulTestsData;
|
||||
FileLineData missingAssertionData;
|
||||
|
||||
static Config<T>* s_instance;
|
||||
};
|
||||
template <typename T>
|
||||
Config<T>* Config<T>::s_instance = NULL;
|
||||
|
||||
template <typename T>
|
||||
struct ConfigReset
|
||||
{
|
||||
ConfigReset( const std::string& file, int c )
|
||||
{
|
||||
Config<T>::instance().insertSuccessfulResults(file, c, false);
|
||||
Config<T>::instance().insertMissingAssertions(file, c, false);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct ConfigShowSuccessfulTests
|
||||
{
|
||||
template <typename U>
|
||||
ConfigShowSuccessfulTests( const std::string& file, int c, U v )
|
||||
{
|
||||
Config<T>::instance().insertSuccessfulResults(file, c, v ? true : false);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct ConfigWarnMissingAssertions
|
||||
{
|
||||
template <typename U>
|
||||
ConfigWarnMissingAssertions( const std::string& file, int c, U v )
|
||||
{
|
||||
Config<T>::instance().insertMissingAssertions(file, c, v ? true : false);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
namespace Catch {
|
||||
|
||||
struct ConfigData {
|
||||
@ -41,6 +173,21 @@ namespace Catch {
|
||||
showDurations( ShowDurations::DefaultForReporter )
|
||||
{}
|
||||
|
||||
explicit ConfigData(const IConfig* other)
|
||||
: listTests( false ),
|
||||
listTags( false ),
|
||||
listReporters( false ),
|
||||
showSuccessfulTests( other ? other->includeSuccessfulResults() : false ),
|
||||
shouldDebugBreak( false ),
|
||||
noThrow( other ? !other->allowThrows() : false ),
|
||||
showHelp( false ),
|
||||
abortAfter( -1 ),
|
||||
verbosity( Verbosity::Normal ),
|
||||
warnings( other ? (other->warnAboutMissingAssertions() ? WarnAbout::NoAssertions : WarnAbout::Nothing) : WarnAbout::Nothing ),
|
||||
showDurations( other ? other->showDurations() : ShowDurations::DefaultForReporter ),
|
||||
name( other ? other->name() : std::string() )
|
||||
{}
|
||||
|
||||
bool listTests;
|
||||
bool listTags;
|
||||
bool listReporters;
|
||||
|
@ -12,10 +12,6 @@
|
||||
|
||||
namespace Catch {
|
||||
|
||||
namespace Detail {
|
||||
struct IColourImpl;
|
||||
}
|
||||
|
||||
struct Colour {
|
||||
enum Code {
|
||||
None = 0,
|
||||
@ -53,12 +49,6 @@ namespace Catch {
|
||||
// Use constructed object for RAII guard
|
||||
Colour( Code _colourCode );
|
||||
~Colour();
|
||||
|
||||
// Use static method for one-shot changes
|
||||
static void use( Code _colourCode );
|
||||
|
||||
private:
|
||||
static Detail::IColourImpl* impl;
|
||||
};
|
||||
|
||||
} // end namespace Catch
|
||||
|
@ -10,13 +10,6 @@
|
||||
|
||||
#include "catch_console_colour.hpp"
|
||||
|
||||
namespace Catch { namespace Detail {
|
||||
struct IColourImpl {
|
||||
virtual ~IColourImpl() {}
|
||||
virtual void use( Colour::Code _colourCode ) = 0;
|
||||
};
|
||||
}}
|
||||
|
||||
#if defined ( CATCH_PLATFORM_WINDOWS ) /////////////////////////////////////////
|
||||
|
||||
#ifndef NOMINMAX
|
||||
@ -32,7 +25,7 @@ namespace Catch { namespace Detail {
|
||||
namespace Catch {
|
||||
namespace {
|
||||
|
||||
class Win32ColourImpl : public Detail::IColourImpl {
|
||||
class Win32ColourImpl {
|
||||
public:
|
||||
Win32ColourImpl() : stdoutHandle( GetStdHandle(STD_OUTPUT_HANDLE) )
|
||||
{
|
||||
@ -41,7 +34,7 @@ namespace {
|
||||
originalAttributes = csbiInfo.wAttributes;
|
||||
}
|
||||
|
||||
virtual void use( Colour::Code _colourCode ) {
|
||||
void use( Colour::Code _colourCode ) {
|
||||
switch( _colourCode ) {
|
||||
case Colour::None: return setTextAttribute( originalAttributes );
|
||||
case Colour::White: return setTextAttribute( FOREGROUND_GREEN | FOREGROUND_RED | FOREGROUND_BLUE );
|
||||
@ -73,7 +66,7 @@ namespace {
|
||||
return true;
|
||||
}
|
||||
|
||||
Win32ColourImpl platformColourImpl;
|
||||
typedef Win32ColourImpl PlatformColourImpl;
|
||||
|
||||
} // end anon namespace
|
||||
} // end namespace Catch
|
||||
@ -89,9 +82,9 @@ namespace {
|
||||
// Thanks to Adam Strzelecki for original contribution
|
||||
// (http://github.com/nanoant)
|
||||
// https://github.com/philsquared/Catch/pull/131
|
||||
class PosixColourImpl : public Detail::IColourImpl {
|
||||
class PosixColourImpl {
|
||||
public:
|
||||
virtual void use( Colour::Code _colourCode ) {
|
||||
void use( Colour::Code _colourCode ) {
|
||||
switch( _colourCode ) {
|
||||
case Colour::None:
|
||||
case Colour::White: return setColour( "[0m" );
|
||||
@ -120,7 +113,7 @@ namespace {
|
||||
return isatty(STDOUT_FILENO);
|
||||
}
|
||||
|
||||
PosixColourImpl platformColourImpl;
|
||||
typedef PosixColourImpl PlatformColourImpl;
|
||||
|
||||
} // end anon namespace
|
||||
} // end namespace Catch
|
||||
@ -129,24 +122,24 @@ namespace {
|
||||
|
||||
namespace Catch {
|
||||
|
||||
namespace {
|
||||
struct NoColourImpl : Detail::IColourImpl {
|
||||
void use( Colour::Code ) {}
|
||||
};
|
||||
NoColourImpl noColourImpl;
|
||||
static const bool shouldUseColour = shouldUseColourForPlatform() &&
|
||||
!isDebuggerActive();
|
||||
}
|
||||
template <typename Impl>
|
||||
struct ColourChange
|
||||
{
|
||||
static Impl impl;
|
||||
static const bool shouldUseColour;
|
||||
};
|
||||
template <typename Impl>
|
||||
Impl ColourChange<Impl>::impl;
|
||||
template <typename Impl>
|
||||
const bool ColourChange<Impl>::shouldUseColour = shouldUseColourForPlatform() &&
|
||||
!isDebuggerActive();;
|
||||
|
||||
Colour::Colour( Code _colourCode ){ use( _colourCode ); }
|
||||
Colour::~Colour(){ use( None ); }
|
||||
void Colour::use( Code _colourCode ) {
|
||||
impl->use( _colourCode );
|
||||
INTERNAL_CATCH_INLINE Colour::Colour( Code _colourCode ) {
|
||||
if( ColourChange<PlatformColourImpl>::shouldUseColour ) ColourChange<PlatformColourImpl>::impl.use( _colourCode );
|
||||
}
|
||||
INTERNAL_CATCH_INLINE Colour::~Colour() {
|
||||
if( ColourChange<PlatformColourImpl>::shouldUseColour ) ColourChange<PlatformColourImpl>::impl.use( Colour::None );
|
||||
}
|
||||
|
||||
Detail::IColourImpl* Colour::impl = shouldUseColour
|
||||
? static_cast<Detail::IColourImpl*>( &platformColourImpl )
|
||||
: static_cast<Detail::IColourImpl*>( &noColourImpl );
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
|
@ -15,9 +15,10 @@
|
||||
|
||||
namespace Catch {
|
||||
|
||||
template <typename Runner, typename ResultCapture>
|
||||
class Context : public IMutableContext {
|
||||
|
||||
Context() : m_config( NULL ), m_runner( NULL ), m_resultCapture( NULL ) {}
|
||||
Context() : m_config( NULL ), m_runner( &nullRunner ), m_resultCapture( &nullResultCapture ) {}
|
||||
Context( Context const& );
|
||||
void operator=( Context const& );
|
||||
|
||||
@ -81,15 +82,28 @@ namespace Catch {
|
||||
IRunner* m_runner;
|
||||
IResultCapture* m_resultCapture;
|
||||
std::map<std::string, IGeneratorsForTest*> m_generatorsByTestName;
|
||||
|
||||
static ResultCapture nullResultCapture;
|
||||
static Runner nullRunner;
|
||||
public:
|
||||
static Context* currentContext;
|
||||
};
|
||||
|
||||
namespace {
|
||||
template <typename Runner, typename ResultCapture>
|
||||
ResultCapture Context<Runner, ResultCapture>::nullResultCapture;
|
||||
template <typename Runner, typename ResultCapture>
|
||||
Runner Context<Runner, ResultCapture>::nullRunner;
|
||||
template <typename Runner, typename ResultCapture>
|
||||
Context<Runner,ResultCapture>* Context<Runner, ResultCapture>::currentContext = NULL;
|
||||
|
||||
/*namespace {
|
||||
Context* currentContext = NULL;
|
||||
}
|
||||
}*/
|
||||
typedef Context<NullRunner, NullResultCapture> DefaultContext;
|
||||
INTERNAL_CATCH_INLINE IMutableContext& getCurrentMutableContext() {
|
||||
if( !currentContext )
|
||||
currentContext = new Context();
|
||||
return *currentContext;
|
||||
if( !DefaultContext::currentContext )
|
||||
DefaultContext::currentContext = new DefaultContext();
|
||||
return *DefaultContext::currentContext;
|
||||
}
|
||||
INTERNAL_CATCH_INLINE IContext& getCurrentContext() {
|
||||
return getCurrentMutableContext();
|
||||
@ -104,8 +118,8 @@ namespace Catch {
|
||||
}
|
||||
|
||||
INTERNAL_CATCH_INLINE void cleanUpContext() {
|
||||
delete currentContext;
|
||||
currentContext = NULL;
|
||||
delete DefaultContext::currentContext;
|
||||
DefaultContext::currentContext = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -41,6 +41,23 @@ namespace Catch {
|
||||
virtual std::string getCurrentTestName() const = 0;
|
||||
virtual const AssertionResult* getLastResult() const = 0;
|
||||
};
|
||||
|
||||
struct NullResultCapture : public IResultCapture {
|
||||
|
||||
virtual void assertionEnded( AssertionResult const& ) {}
|
||||
virtual bool sectionStarted( SectionInfo const& ,
|
||||
Counts& ) {return false;}
|
||||
virtual void sectionEnded( SectionInfo const& , Counts const& , double ) {}
|
||||
virtual void pushScopedMessage( MessageInfo const& ) {}
|
||||
virtual void popScopedMessage( MessageInfo const& ) {}
|
||||
|
||||
virtual bool shouldDebugBreak() const {return false;}
|
||||
|
||||
virtual ResultAction::Value acceptExpression( ExpressionResultBuilder const& , AssertionInfo const& ) {return ResultAction::Abort;}
|
||||
|
||||
virtual std::string getCurrentTestName() const {return std::string();}
|
||||
virtual const AssertionResult* getLastResult() const {return NULL;}
|
||||
};
|
||||
}
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_INTERFACES_CAPTURE_H_INCLUDED
|
||||
|
@ -14,6 +14,10 @@ namespace Catch {
|
||||
struct IRunner {
|
||||
virtual ~IRunner();
|
||||
};
|
||||
|
||||
struct NullRunner : public IRunner
|
||||
{
|
||||
};
|
||||
}
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_INTERFACES_RUNNER_H_INCLUDED
|
||||
|
@ -16,64 +16,68 @@
|
||||
|
||||
namespace Catch {
|
||||
|
||||
namespace {
|
||||
class RegistryHub : public IRegistryHub, public IMutableRegistryHub {
|
||||
|
||||
class RegistryHub : public IRegistryHub, public IMutableRegistryHub {
|
||||
RegistryHub( RegistryHub const& );
|
||||
void operator=( RegistryHub const& );
|
||||
|
||||
RegistryHub( RegistryHub const& );
|
||||
void operator=( RegistryHub const& );
|
||||
public: // IRegistryHub
|
||||
RegistryHub() {
|
||||
}
|
||||
virtual IReporterRegistry const& getReporterRegistry() const {
|
||||
return m_reporterRegistry;
|
||||
}
|
||||
virtual ITestCaseRegistry const& getTestCaseRegistry() const {
|
||||
return m_testCaseRegistry;
|
||||
}
|
||||
virtual IExceptionTranslatorRegistry& getExceptionTranslatorRegistry() {
|
||||
return m_exceptionTranslatorRegistry;
|
||||
}
|
||||
|
||||
public: // IRegistryHub
|
||||
RegistryHub() {
|
||||
}
|
||||
virtual IReporterRegistry const& getReporterRegistry() const {
|
||||
return m_reporterRegistry;
|
||||
}
|
||||
virtual ITestCaseRegistry const& getTestCaseRegistry() const {
|
||||
return m_testCaseRegistry;
|
||||
}
|
||||
virtual IExceptionTranslatorRegistry& getExceptionTranslatorRegistry() {
|
||||
return m_exceptionTranslatorRegistry;
|
||||
}
|
||||
public: // IMutableRegistryHub
|
||||
virtual void registerReporter( std::string const& name, IReporterFactory* factory ) {
|
||||
m_reporterRegistry.registerReporter( name, factory );
|
||||
}
|
||||
virtual void registerTest( TestCase const& testInfo ) {
|
||||
m_testCaseRegistry.registerTest( testInfo );
|
||||
}
|
||||
virtual void registerTranslator( const IExceptionTranslator* translator ) {
|
||||
m_exceptionTranslatorRegistry.registerTranslator( translator );
|
||||
}
|
||||
|
||||
public: // IMutableRegistryHub
|
||||
virtual void registerReporter( std::string const& name, IReporterFactory* factory ) {
|
||||
m_reporterRegistry.registerReporter( name, factory );
|
||||
}
|
||||
virtual void registerTest( TestCase const& testInfo ) {
|
||||
m_testCaseRegistry.registerTest( testInfo );
|
||||
}
|
||||
virtual void registerTranslator( const IExceptionTranslator* translator ) {
|
||||
m_exceptionTranslatorRegistry.registerTranslator( translator );
|
||||
}
|
||||
private:
|
||||
TestRegistry m_testCaseRegistry;
|
||||
ReporterRegistry m_reporterRegistry;
|
||||
ExceptionTranslatorRegistry m_exceptionTranslatorRegistry;
|
||||
};
|
||||
|
||||
private:
|
||||
TestRegistry m_testCaseRegistry;
|
||||
ReporterRegistry m_reporterRegistry;
|
||||
ExceptionTranslatorRegistry m_exceptionTranslatorRegistry;
|
||||
};
|
||||
|
||||
// Single, global, instance
|
||||
inline RegistryHub*& getTheRegistryHub() {
|
||||
static RegistryHub* theRegistryHub = NULL;
|
||||
// Single, global, instance
|
||||
template <typename T>
|
||||
struct GlobalRegistryHub
|
||||
{
|
||||
static T*& instance()
|
||||
{
|
||||
if( !theRegistryHub )
|
||||
theRegistryHub = new RegistryHub();
|
||||
theRegistryHub = new T();
|
||||
return theRegistryHub;
|
||||
}
|
||||
}
|
||||
static T* theRegistryHub;
|
||||
};
|
||||
template <typename T>
|
||||
T* GlobalRegistryHub<T>::theRegistryHub = NULL;
|
||||
|
||||
IRegistryHub& getRegistryHub() {
|
||||
return *getTheRegistryHub();
|
||||
INTERNAL_CATCH_INLINE IRegistryHub& getRegistryHub() {
|
||||
return *GlobalRegistryHub<RegistryHub>::instance();
|
||||
}
|
||||
IMutableRegistryHub& getMutableRegistryHub() {
|
||||
return *getTheRegistryHub();
|
||||
INTERNAL_CATCH_INLINE IMutableRegistryHub& getMutableRegistryHub() {
|
||||
return *GlobalRegistryHub<RegistryHub>::instance();
|
||||
}
|
||||
void cleanUp() {
|
||||
delete getTheRegistryHub();
|
||||
getTheRegistryHub() = NULL;
|
||||
INTERNAL_CATCH_INLINE void cleanUp() {
|
||||
delete GlobalRegistryHub<RegistryHub>::instance();
|
||||
GlobalRegistryHub<RegistryHub>::instance() = NULL;
|
||||
cleanUpContext();
|
||||
}
|
||||
std::string translateActiveException() {
|
||||
INTERNAL_CATCH_INLINE std::string translateActiveException() {
|
||||
return getRegistryHub().getExceptionTranslatorRegistry().translateActiveException();
|
||||
}
|
||||
|
||||
|
@ -48,7 +48,6 @@ namespace Catch {
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
class RunContext : public IResultCapture, public IRunner {
|
||||
|
||||
RunContext( RunContext const& );
|
||||
@ -105,18 +104,16 @@ namespace Catch {
|
||||
}
|
||||
|
||||
Totals runTest( TestCase const& testCase ) {
|
||||
Totals prevTotals = m_totals;
|
||||
|
||||
std::string redirectedCout;
|
||||
std::string redirectedCerr;
|
||||
|
||||
TestCaseInfo testInfo = testCase.getTestCaseInfo();
|
||||
|
||||
m_reporter->testCaseStarting( testInfo );
|
||||
UnwindTestCaseOnCompletion finaliser(*this, m_totals, m_reporter, testInfo, redirectedCout, redirectedCerr);
|
||||
|
||||
m_activeTestCase = &testCase;
|
||||
m_testCaseTracker = TestCaseTracker( testInfo.name );
|
||||
|
||||
do {
|
||||
do {
|
||||
runCurrentTest( redirectedCout, redirectedCerr );
|
||||
@ -125,18 +122,10 @@ namespace Catch {
|
||||
}
|
||||
while( getCurrentContext().advanceGeneratorsForCurrentTest() && !aborting() );
|
||||
|
||||
Totals deltaTotals = m_totals.delta( prevTotals );
|
||||
m_totals.testCases += deltaTotals.testCases;
|
||||
m_reporter->testCaseEnded( TestCaseStats( testInfo,
|
||||
deltaTotals,
|
||||
redirectedCout,
|
||||
redirectedCerr,
|
||||
aborting() ) );
|
||||
|
||||
m_activeTestCase = NULL;
|
||||
m_testCaseTracker.reset();
|
||||
|
||||
return deltaTotals;
|
||||
return finaliser.report();
|
||||
}
|
||||
|
||||
Ptr<IConfig const> config() const {
|
||||
@ -194,12 +183,7 @@ namespace Catch {
|
||||
return true;
|
||||
}
|
||||
|
||||
virtual void sectionEnded( SectionInfo const& info, Counts const& prevAssertions, double _durationInSeconds ) {
|
||||
if( std::uncaught_exception() ) {
|
||||
m_unfinishedSections.push_back( UnfinishedSections( info, prevAssertions, _durationInSeconds ) );
|
||||
return;
|
||||
}
|
||||
|
||||
void unwindSection(SectionInfo const& info, Counts const& prevAssertions, double _durationInSeconds ) {
|
||||
Counts assertions = m_totals.assertions - prevAssertions;
|
||||
bool missingAssertions = testForMissingAssertions( assertions );
|
||||
|
||||
@ -209,6 +193,15 @@ namespace Catch {
|
||||
m_messages.clear();
|
||||
}
|
||||
|
||||
virtual void sectionEnded( SectionInfo const& info, Counts const& prevAssertions, double _durationInSeconds ) {
|
||||
if( std::uncaught_exception() ) {
|
||||
m_unfinishedSections.push_back( UnfinishedSections( info, prevAssertions, _durationInSeconds ) );
|
||||
return;
|
||||
}
|
||||
|
||||
unwindSection(info, prevAssertions, _durationInSeconds);
|
||||
}
|
||||
|
||||
virtual void pushScopedMessage( MessageInfo const& message ) {
|
||||
m_messages.push_back( message );
|
||||
}
|
||||
@ -257,16 +250,13 @@ namespace Catch {
|
||||
|
||||
void runCurrentTest( std::string& redirectedCout, std::string& redirectedCerr ) {
|
||||
TestCaseInfo const& testCaseInfo = m_activeTestCase->getTestCaseInfo();
|
||||
SectionInfo testCaseSection( testCaseInfo.name, testCaseInfo.description, testCaseInfo.lineInfo );
|
||||
m_reporter->sectionStarting( testCaseSection );
|
||||
Counts prevAssertions = m_totals.assertions;
|
||||
double duration = 0;
|
||||
|
||||
UnwindSectionOnCompletion finaliser(*this, m_totals, m_reporter, testCaseInfo, m_unfinishedSections, m_messages);
|
||||
try {
|
||||
m_lastAssertionInfo = AssertionInfo( "TEST_CASE", testCaseInfo.lineInfo, "", ResultDisposition::Normal );
|
||||
TestCaseTracker::Guard guard( *m_testCaseTracker );
|
||||
|
||||
Timer timer;
|
||||
timer.start();
|
||||
finaliser.startTimer();
|
||||
if( m_reporter->getPreferences().shouldRedirectStdOut ) {
|
||||
StreamRedirect coutRedir( std::cout, redirectedCout );
|
||||
StreamRedirect cerrRedir( std::cerr, redirectedCerr );
|
||||
@ -275,37 +265,16 @@ namespace Catch {
|
||||
else {
|
||||
m_activeTestCase->invoke();
|
||||
}
|
||||
duration = timer.getElapsedSeconds();
|
||||
finaliser.stopTimer();
|
||||
}
|
||||
#ifdef INTERNAL_CATCH_VS_MANAGED // detect CLR
|
||||
catch(AssertFailedException^) {
|
||||
throw; // CLR always rethrows - stop on first assert
|
||||
}
|
||||
#else
|
||||
catch( INTERNAL_CATCH_TEST_FAILURE_EXCEPTION ) {
|
||||
catch( const Catch::TestFailureException& ) {
|
||||
// This just means the test was aborted due to failure
|
||||
}
|
||||
#endif
|
||||
catch(...) {
|
||||
ExpressionResultBuilder exResult( ResultWas::ThrewException );
|
||||
exResult << translateActiveException();
|
||||
actOnCurrentResult( exResult.buildResult( m_lastAssertionInfo ) );
|
||||
}
|
||||
// If sections ended prematurely due to an exception we stored their
|
||||
// infos here so we can tear them down outside the unwind process.
|
||||
for( std::vector<UnfinishedSections>::const_iterator it = m_unfinishedSections.begin(),
|
||||
itEnd = m_unfinishedSections.end();
|
||||
it != itEnd;
|
||||
++it )
|
||||
sectionEnded( it->info, it->prevAssertions, it->durationInSeconds );
|
||||
m_unfinishedSections.clear();
|
||||
m_messages.clear();
|
||||
|
||||
Counts assertions = m_totals.assertions - prevAssertions;
|
||||
bool missingAssertions = testForMissingAssertions( assertions );
|
||||
|
||||
SectionStats testCaseSectionStats( testCaseSection, assertions, duration, missingAssertions );
|
||||
m_reporter->sectionEnded( testCaseSectionStats );
|
||||
}
|
||||
|
||||
private:
|
||||
@ -319,6 +288,111 @@ namespace Catch {
|
||||
double durationInSeconds;
|
||||
};
|
||||
|
||||
class UnwindSectionOnCompletion
|
||||
{
|
||||
public:
|
||||
UnwindSectionOnCompletion(RunContext& context, Totals& totals, Ptr<IStreamingReporter>& reporter, TestCaseInfo const& testCaseInfo,
|
||||
std::vector<UnfinishedSections>& unfinishedSections, std::vector<MessageInfo>& messages)
|
||||
: m_context(context)
|
||||
, m_totals(totals)
|
||||
, m_reporter(reporter)
|
||||
, m_testCaseSection( testCaseInfo.name, testCaseInfo.description, testCaseInfo.lineInfo )
|
||||
, m_unfinishedSections(unfinishedSections)
|
||||
, m_messages(messages)
|
||||
, m_duration(0.0)
|
||||
{
|
||||
m_prevAssertions = m_totals.assertions;
|
||||
m_reporter->sectionStarting( m_testCaseSection );
|
||||
}
|
||||
~UnwindSectionOnCompletion()
|
||||
{
|
||||
// If sections ended prematurely due to an exception we stored their
|
||||
// infos here so we can tear them down.
|
||||
for( std::vector<UnfinishedSections>::const_iterator it = m_unfinishedSections.begin(),
|
||||
itEnd = m_unfinishedSections.end();
|
||||
it != itEnd;
|
||||
++it ) {
|
||||
m_context.unwindSection( it->info, it->prevAssertions, it->durationInSeconds );
|
||||
}
|
||||
m_unfinishedSections.clear();
|
||||
m_messages.clear();
|
||||
|
||||
Counts assertions = m_totals.assertions - m_prevAssertions;
|
||||
bool missingAssertions = m_context.testForMissingAssertions( assertions );
|
||||
|
||||
SectionStats testCaseSectionStats( m_testCaseSection, assertions, m_duration, missingAssertions );
|
||||
m_reporter->sectionEnded( testCaseSectionStats );
|
||||
}
|
||||
void startTimer()
|
||||
{
|
||||
m_timer.start();
|
||||
}
|
||||
void stopTimer()
|
||||
{
|
||||
m_duration = m_timer.getElapsedSeconds();
|
||||
}
|
||||
private:
|
||||
// non-copyable
|
||||
UnwindSectionOnCompletion(const UnwindSectionOnCompletion&);
|
||||
UnwindSectionOnCompletion& operator=(const UnwindSectionOnCompletion&);
|
||||
|
||||
RunContext& m_context;
|
||||
Totals& m_totals;
|
||||
Ptr<IStreamingReporter>& m_reporter;
|
||||
SectionInfo m_testCaseSection;
|
||||
std::vector<UnfinishedSections>& m_unfinishedSections;
|
||||
std::vector<MessageInfo>& m_messages;
|
||||
Timer m_timer;
|
||||
Counts m_prevAssertions;
|
||||
double m_duration;
|
||||
};
|
||||
|
||||
class UnwindTestCaseOnCompletion
|
||||
{
|
||||
public:
|
||||
UnwindTestCaseOnCompletion(RunContext& context, Totals& totals, Ptr<IStreamingReporter>& reporter, TestCaseInfo& testInfo,
|
||||
std::string& redirectedCout, std::string& redirectedCerr)
|
||||
: m_context(context), m_totals(totals), m_reporter(reporter), m_testInfo(testInfo)
|
||||
, m_redirectedCout(redirectedCout), m_redirectedCerr(redirectedCerr)
|
||||
, m_reported(false)
|
||||
{
|
||||
m_prevTotals = m_totals;
|
||||
m_reporter->testCaseStarting( m_testInfo );
|
||||
}
|
||||
~UnwindTestCaseOnCompletion()
|
||||
{
|
||||
if( !m_reported )
|
||||
{
|
||||
report();
|
||||
}
|
||||
}
|
||||
Totals report()
|
||||
{
|
||||
m_reported = true;
|
||||
Totals deltaTotals = m_totals.delta( m_prevTotals );
|
||||
m_totals.testCases += deltaTotals.testCases;
|
||||
m_reporter->testCaseEnded( TestCaseStats( m_testInfo,
|
||||
deltaTotals,
|
||||
m_redirectedCout,
|
||||
m_redirectedCerr,
|
||||
m_context.aborting() ) );
|
||||
return deltaTotals;
|
||||
}
|
||||
private:
|
||||
// non-copyable
|
||||
UnwindTestCaseOnCompletion(const UnwindTestCaseOnCompletion&);
|
||||
UnwindTestCaseOnCompletion& operator=(const UnwindTestCaseOnCompletion&);
|
||||
|
||||
RunContext& m_context;
|
||||
Totals& m_totals;
|
||||
Ptr<IStreamingReporter>& m_reporter;
|
||||
TestCaseInfo& m_testInfo;
|
||||
std::string& m_redirectedCout;
|
||||
std::string& m_redirectedCerr;
|
||||
bool m_reported;
|
||||
Totals m_prevTotals;
|
||||
};
|
||||
|
||||
TestRunInfo m_runInfo;
|
||||
IMutableContext& m_context;
|
||||
TestCase const* m_activeTestCase;
|
||||
|
@ -8,7 +8,11 @@
|
||||
#ifndef TWOBLUECUBES_CATCH_TEST_CASE_REGISTRY_IMPL_HPP_INCLUDED
|
||||
#define TWOBLUECUBES_CATCH_TEST_CASE_REGISTRY_IMPL_HPP_INCLUDED
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED) || defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
#include "internal/catch_vs_test_registry.hpp"
|
||||
#else
|
||||
#include "catch_test_registry.hpp"
|
||||
#endif
|
||||
#include "catch_test_case_info.h"
|
||||
#include "catch_test_spec.h"
|
||||
#include "catch_context.h"
|
||||
@ -124,15 +128,15 @@ namespace Catch {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
AutoReg::AutoReg( TestFunction function,
|
||||
INTERNAL_CATCH_INLINE AutoReg::AutoReg( TestFunction function,
|
||||
SourceLineInfo const& lineInfo,
|
||||
NameAndDesc const& nameAndDesc ) {
|
||||
registerTestCase( new FreeFunctionTestCase( function ), "", nameAndDesc, lineInfo );
|
||||
}
|
||||
|
||||
AutoReg::~AutoReg() {}
|
||||
INTERNAL_CATCH_INLINE AutoReg::~AutoReg() {}
|
||||
|
||||
void AutoReg::registerTestCase( ITestCase* testCase,
|
||||
INTERNAL_CATCH_INLINE void AutoReg::registerTestCase( ITestCase* testCase,
|
||||
char const* classOrQualifiedMethodName,
|
||||
NameAndDesc const& nameAndDesc,
|
||||
SourceLineInfo const& lineInfo ) {
|
||||
|
@ -24,15 +24,25 @@ namespace Catch {
|
||||
|
||||
namespace {
|
||||
#ifdef CATCH_PLATFORM_WINDOWS
|
||||
template <typename T>
|
||||
struct CounterDefaults
|
||||
{
|
||||
static T hz;
|
||||
static T hzo;
|
||||
};
|
||||
template <typename T>
|
||||
T CounterDefaults<T>::hz = 0;
|
||||
template <typename T>
|
||||
T CounterDefaults<T>::hzo = 0;
|
||||
|
||||
INTERNAL_CATCH_INLINE uint64_t getCurrentTicks() {
|
||||
static uint64_t hz=0, hzo=0;
|
||||
if (!hz) {
|
||||
QueryPerformanceFrequency((LARGE_INTEGER*)&hz);
|
||||
QueryPerformanceCounter((LARGE_INTEGER*)&hzo);
|
||||
if (!CounterDefaults<uint64_t>::hz) {
|
||||
QueryPerformanceFrequency((LARGE_INTEGER*)&CounterDefaults<uint64_t>::hz);
|
||||
QueryPerformanceCounter((LARGE_INTEGER*)&CounterDefaults<uint64_t>::hzo);
|
||||
}
|
||||
uint64_t t;
|
||||
QueryPerformanceCounter((LARGE_INTEGER*)&t);
|
||||
return ((t-hzo)*1000000)/hz;
|
||||
return ((t-CounterDefaults<uint64_t>::hzo)*1000000)/CounterDefaults<uint64_t>::hz;
|
||||
}
|
||||
#else
|
||||
INTERNAL_CATCH_INLINE uint64_t getCurrentTicks() {
|
||||
|
@ -95,7 +95,11 @@ struct StringMaker<T*> {
|
||||
if( !p )
|
||||
return INTERNAL_CATCH_STRINGIFY( NULL );
|
||||
std::ostringstream oss;
|
||||
#ifdef _MSC_VER
|
||||
oss << "0x" << p;
|
||||
#else
|
||||
oss << p;
|
||||
#endif
|
||||
return oss.str();
|
||||
}
|
||||
};
|
||||
|
@ -18,7 +18,7 @@ using namespace System::Collections::Generic;
|
||||
using namespace Microsoft::VisualStudio::TestTools::UnitTesting;
|
||||
|
||||
namespace Catch {
|
||||
inline String^ convert_string_to_managed(const std::string& s)
|
||||
inline String^ convert_string_for_assert(const std::string& s)
|
||||
{
|
||||
String^ result = gcnew String(s.c_str());
|
||||
return result;
|
||||
@ -33,67 +33,50 @@ namespace Catch {
|
||||
#include "catch_section.hpp"
|
||||
#include "internal/catch_timer.hpp"
|
||||
#include "internal/catch_vs_test_registry.hpp"
|
||||
#include "internal/catch_reporter_registrars.hpp"
|
||||
#include "reporters/catch_vs_reporter.hpp"
|
||||
|
||||
#include "internal/catch_exception_translator_registry.hpp"
|
||||
#include "catch_registry_hub.hpp"
|
||||
#include "internal/catch_console_colour_impl.hpp"
|
||||
#include "catch_runner.hpp"
|
||||
|
||||
namespace Catch {
|
||||
inline NonCopyable::~NonCopyable() {}
|
||||
inline IShared::~IShared() {}
|
||||
inline StreamBufBase::~StreamBufBase() throw() {}
|
||||
inline IContext::~IContext() {}
|
||||
inline IResultCapture::~IResultCapture() {}
|
||||
inline ITestCase::~ITestCase() {}
|
||||
inline ITestCaseRegistry::~ITestCaseRegistry() {}
|
||||
inline IRegistryHub::~IRegistryHub() {}
|
||||
inline IMutableRegistryHub::~IMutableRegistryHub() {}
|
||||
inline IExceptionTranslator::~IExceptionTranslator() {}
|
||||
inline IExceptionTranslatorRegistry::~IExceptionTranslatorRegistry() {}
|
||||
inline IReporter::~IReporter() {}
|
||||
inline IReporterFactory::~IReporterFactory() {}
|
||||
inline IReporterRegistry::~IReporterRegistry() {}
|
||||
inline IStreamingReporter::~IStreamingReporter() {}
|
||||
inline AssertionStats::~AssertionStats() {}
|
||||
inline SectionStats::~SectionStats() {}
|
||||
inline TestCaseStats::~TestCaseStats() {}
|
||||
inline TestGroupStats::~TestGroupStats() {}
|
||||
inline TestRunStats::~TestRunStats() {}
|
||||
|
||||
class ExceptionRegistryHub : public IRegistryHub, public IMutableRegistryHub {
|
||||
inline IRunner::~IRunner() {}
|
||||
inline IMutableContext::~IMutableContext() {}
|
||||
inline IConfig::~IConfig() {}
|
||||
inline TestRegistry::~TestRegistry() {}
|
||||
inline FreeFunctionTestCase::~FreeFunctionTestCase() {}
|
||||
inline IGeneratorInfo::~IGeneratorInfo() {}
|
||||
inline IGeneratorsForTest::~IGeneratorsForTest() {}
|
||||
|
||||
ExceptionRegistryHub( ExceptionRegistryHub const& );
|
||||
void operator=( ExceptionRegistryHub const& );
|
||||
|
||||
public: // IRegistryHub
|
||||
ExceptionRegistryHub() {
|
||||
}
|
||||
virtual IReporterRegistry const& getReporterRegistry() const {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual ITestCaseRegistry const& getTestCaseRegistry() const {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual IExceptionTranslatorRegistry& getExceptionTranslatorRegistry() {
|
||||
return m_exceptionTranslatorRegistry;
|
||||
}
|
||||
|
||||
public: // IMutableRegistryHub
|
||||
virtual void registerReporter( std::string const&, IReporterFactory* ) {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual void registerTest( TestCase const& ) {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual void registerTranslator( const IExceptionTranslator* translator ) {
|
||||
m_exceptionTranslatorRegistry.registerTranslator( translator );
|
||||
}
|
||||
|
||||
private:
|
||||
ExceptionTranslatorRegistry m_exceptionTranslatorRegistry;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct GlobalRegistryHub
|
||||
{
|
||||
static T& instance()
|
||||
{
|
||||
if( !theRegistryHub )
|
||||
theRegistryHub = new T();
|
||||
return *theRegistryHub;
|
||||
}
|
||||
static T* theRegistryHub;
|
||||
};
|
||||
template <typename T>
|
||||
T* GlobalRegistryHub<T>::theRegistryHub = NULL;
|
||||
|
||||
INTERNAL_CATCH_INLINE IMutableRegistryHub& getMutableRegistryHub() {
|
||||
return GlobalRegistryHub<ExceptionRegistryHub>::instance();
|
||||
}
|
||||
INTERNAL_CATCH_INLINE std::string translateActiveException() {
|
||||
return GlobalRegistryHub<ExceptionRegistryHub>::instance().getExceptionTranslatorRegistry().translateActiveException();
|
||||
}
|
||||
inline Matchers::Impl::StdString::Equals::~Equals() {}
|
||||
inline Matchers::Impl::StdString::Contains::~Contains() {}
|
||||
inline Matchers::Impl::StdString::StartsWith::~StartsWith() {}
|
||||
inline Matchers::Impl::StdString::EndsWith::~EndsWith() {}
|
||||
|
||||
inline void Config::dummy() {}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#endif // TWOBLUECUBES_CATCH_VS_MANAGED_HPP_INCLUDED
|
||||
|
@ -16,8 +16,6 @@ using Microsoft::VisualStudio::CppUnitTestFramework::Logger;
|
||||
using Microsoft::VisualStudio::CppUnitTestFramework::Assert;
|
||||
using Microsoft::VisualStudio::CppUnitTestFramework::__LineInfo;
|
||||
|
||||
#define INTERNAL_CATCH_INLINE inline
|
||||
|
||||
#include <cvt/wstring>
|
||||
#include <codecvt>
|
||||
|
||||
@ -26,66 +24,50 @@ using Microsoft::VisualStudio::CppUnitTestFramework::__LineInfo;
|
||||
#include "catch_tags.hpp"
|
||||
#include "catch_test_spec.hpp"
|
||||
#include "catch_section.hpp"
|
||||
#include "internal/catch_timer.hpp"
|
||||
#include "internal/catch_vs_test_registry.hpp"
|
||||
#include "internal/catch_reporter_registrars.hpp"
|
||||
#include "reporters/catch_vs_reporter.hpp"
|
||||
#include "catch_registry_hub.hpp"
|
||||
#include "internal/catch_timer.hpp"
|
||||
#include "internal/catch_console_colour_impl.hpp"
|
||||
#include "catch_runner.hpp"
|
||||
|
||||
namespace Catch {
|
||||
inline NonCopyable::~NonCopyable() {}
|
||||
inline IShared::~IShared() {}
|
||||
inline StreamBufBase::~StreamBufBase() throw() {}
|
||||
inline IContext::~IContext() {}
|
||||
inline IResultCapture::~IResultCapture() {}
|
||||
inline ITestCase::~ITestCase() {}
|
||||
inline ITestCaseRegistry::~ITestCaseRegistry() {}
|
||||
inline IRegistryHub::~IRegistryHub() {}
|
||||
inline IMutableRegistryHub::~IMutableRegistryHub() {}
|
||||
inline IExceptionTranslator::~IExceptionTranslator() {}
|
||||
inline IExceptionTranslatorRegistry::~IExceptionTranslatorRegistry() {}
|
||||
inline IReporter::~IReporter() {}
|
||||
inline IReporterFactory::~IReporterFactory() {}
|
||||
inline IReporterRegistry::~IReporterRegistry() {}
|
||||
inline IStreamingReporter::~IStreamingReporter() {}
|
||||
inline AssertionStats::~AssertionStats() {}
|
||||
inline SectionStats::~SectionStats() {}
|
||||
inline TestCaseStats::~TestCaseStats() {}
|
||||
inline TestGroupStats::~TestGroupStats() {}
|
||||
inline TestRunStats::~TestRunStats() {}
|
||||
|
||||
class ExceptionRegistryHub : public IRegistryHub, public IMutableRegistryHub {
|
||||
inline IRunner::~IRunner() {}
|
||||
inline IMutableContext::~IMutableContext() {}
|
||||
inline IConfig::~IConfig() {}
|
||||
inline TestRegistry::~TestRegistry() {}
|
||||
inline FreeFunctionTestCase::~FreeFunctionTestCase() {}
|
||||
inline IGeneratorInfo::~IGeneratorInfo() {}
|
||||
inline IGeneratorsForTest::~IGeneratorsForTest() {}
|
||||
|
||||
ExceptionRegistryHub( ExceptionRegistryHub const& );
|
||||
void operator=( ExceptionRegistryHub const& );
|
||||
|
||||
public: // IRegistryHub
|
||||
ExceptionRegistryHub() {
|
||||
}
|
||||
virtual IReporterRegistry const& getReporterRegistry() const {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual ITestCaseRegistry const& getTestCaseRegistry() const {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual IExceptionTranslatorRegistry& getExceptionTranslatorRegistry() {
|
||||
return m_exceptionTranslatorRegistry;
|
||||
}
|
||||
|
||||
public: // IMutableRegistryHub
|
||||
virtual void registerReporter( std::string const&, IReporterFactory* ) {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual void registerTest( TestCase const& ) {
|
||||
throw std::runtime_error("can't do this for Visual Studio tests!");
|
||||
}
|
||||
virtual void registerTranslator( const IExceptionTranslator* translator ) {
|
||||
m_exceptionTranslatorRegistry.registerTranslator( translator );
|
||||
}
|
||||
|
||||
private:
|
||||
ExceptionTranslatorRegistry m_exceptionTranslatorRegistry;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct GlobalRegistryHub
|
||||
{
|
||||
static T& instance()
|
||||
{
|
||||
if( !theRegistryHub )
|
||||
theRegistryHub = new T();
|
||||
return *theRegistryHub;
|
||||
}
|
||||
static T* theRegistryHub;
|
||||
};
|
||||
template <typename T>
|
||||
T* GlobalRegistryHub<T>::theRegistryHub = NULL;
|
||||
|
||||
INTERNAL_CATCH_INLINE IMutableRegistryHub& getMutableRegistryHub() {
|
||||
return GlobalRegistryHub<ExceptionRegistryHub>::instance();
|
||||
}
|
||||
INTERNAL_CATCH_INLINE std::string translateActiveException() {
|
||||
return GlobalRegistryHub<ExceptionRegistryHub>::instance().getExceptionTranslatorRegistry().translateActiveException();
|
||||
}
|
||||
inline Matchers::Impl::StdString::Equals::~Equals() {}
|
||||
inline Matchers::Impl::StdString::Contains::~Contains() {}
|
||||
inline Matchers::Impl::StdString::StartsWith::~StartsWith() {}
|
||||
inline Matchers::Impl::StdString::EndsWith::~EndsWith() {}
|
||||
|
||||
inline void Config::dummy() {}
|
||||
}
|
||||
|
||||
#endif // INTERNAL_CATCH_VS_NATIVE
|
||||
|
@ -16,27 +16,11 @@
|
||||
#include "catch_common.h"
|
||||
#include "catch_interfaces_testcase.h"
|
||||
#include "internal/catch_compiler_capabilities.h"
|
||||
#include "internal/clara.h"
|
||||
#include <tchar.h>
|
||||
|
||||
namespace Catch {
|
||||
|
||||
typedef void(*TestFunction)();
|
||||
|
||||
class FreeFunctionTestCase : public SharedImpl<ITestCase> {
|
||||
public:
|
||||
|
||||
FreeFunctionTestCase( TestFunction fun ) : m_fun( fun ) {}
|
||||
|
||||
virtual void invoke() const {
|
||||
m_fun();
|
||||
}
|
||||
|
||||
private:
|
||||
virtual ~FreeFunctionTestCase();
|
||||
|
||||
TestFunction m_fun;
|
||||
};
|
||||
|
||||
class MethodTestCase : public SharedImpl<ITestCase> {
|
||||
|
||||
struct placeholder
|
||||
@ -79,7 +63,7 @@ private:
|
||||
typedef void(*TestFunction)();
|
||||
|
||||
struct NameAndDesc {
|
||||
#if (_MANAGED == 1) || (_M_CEE == 1) // detect CLR
|
||||
#ifdef INTERNAL_CATCH_VS_MANAGED
|
||||
NameAndDesc( const char* _name = "", const char* _description= "" )
|
||||
: name( _name ), description( _description )
|
||||
{}
|
||||
@ -90,14 +74,35 @@ struct NameAndDesc {
|
||||
NameAndDesc( const wchar_t* _name, const char* _description= "" )
|
||||
: name(), description( _description )
|
||||
{
|
||||
stdext::cvt::wstring_convert<std::codecvt_utf8<wchar_t> > conv1;
|
||||
name = conv1.to_bytes(_name);
|
||||
assignName(_name);
|
||||
}
|
||||
NameAndDesc( const wchar_t* _name, int )
|
||||
: name(), description( "" )
|
||||
{
|
||||
assignName(_name);
|
||||
}
|
||||
void assignName(const wchar_t* _name)
|
||||
{
|
||||
stdext::cvt::wstring_convert<std::codecvt_utf8<wchar_t> > conv1;
|
||||
name = conv1.to_bytes(_name);
|
||||
std::string tmp = conv1.to_bytes(_name);
|
||||
if( tmp.empty() )
|
||||
{
|
||||
name = tmp;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::string::iterator startIter = tmp.begin();
|
||||
if(*startIter == '\"')
|
||||
{
|
||||
++startIter;
|
||||
}
|
||||
std::string::reverse_iterator endIter = tmp.rbegin();
|
||||
if(*endIter == '\"')
|
||||
{
|
||||
++endIter;
|
||||
}
|
||||
name.assign(startIter, endIter.base());
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -105,9 +110,38 @@ struct NameAndDesc {
|
||||
std::string description;
|
||||
};
|
||||
|
||||
struct AutoReg {
|
||||
|
||||
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( method ),
|
||||
className,
|
||||
nameAndDesc,
|
||||
lineInfo );
|
||||
}
|
||||
|
||||
void registerTestCase( ITestCase* testCase,
|
||||
char const* className,
|
||||
NameAndDesc const& nameAndDesc,
|
||||
SourceLineInfo const& lineInfo );
|
||||
|
||||
~AutoReg();
|
||||
|
||||
private:
|
||||
AutoReg( AutoReg const& );
|
||||
void operator= ( AutoReg const& );
|
||||
};
|
||||
|
||||
} // end namespace Catch
|
||||
|
||||
#if (_MANAGED == 1) || (_M_CEE == 1) // detect CLR
|
||||
#ifdef INTERNAL_CATCH_VS_MANAGED
|
||||
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM2( name ) name##""
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM(...) CATCH_INTERNAL_HANDLE_EMPTY_PARAM2( INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__) )
|
||||
@ -134,7 +168,7 @@ struct NameAndDesc {
|
||||
|
||||
#define CATCH_INTERNAL_NAMESPACE( Ext )
|
||||
|
||||
#define INTERNAL_CATCH_TEST_METHOD( Method, UniqueExt, Name, Desc ) \
|
||||
#define INTERNAL_CATCH_TEST_METHOD( Count, UniqueExt, Name, Desc ) \
|
||||
public: \
|
||||
[TestMethod] \
|
||||
[Description( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name) )] \
|
||||
@ -142,22 +176,24 @@ struct NameAndDesc {
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) () \
|
||||
{ \
|
||||
Catch::NameAndDesc name_desc( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name), Desc ); \
|
||||
CATCH_INTERNAL_RUN_SINGLE_TEST( Method ); \
|
||||
CATCH_INTERNAL_RUN_SINGLE_TEST(Count); \
|
||||
}
|
||||
|
||||
#define INTERNAL_CATCH_TEST_CLASS_METHOD( Method, UniqueExt, Name, Desc ) \
|
||||
#define BEGIN_INTERNAL_CATCH_BATCH_METHOD( Tags, UniqueExt ) \
|
||||
public: \
|
||||
[TestMethod] \
|
||||
[Description( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name) )] \
|
||||
[TestProperty( "Description", CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name) )] \
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) () \
|
||||
{ \
|
||||
Catch::NameAndDesc name_desc( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name), Desc ); \
|
||||
CATCH_INTERNAL_RUN_SINGLE_CLASS_TEST( Method ); \
|
||||
}
|
||||
[TestCategory( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Tags) )] \
|
||||
[Description( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Tags) )] \
|
||||
[TestProperty( "Description", CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Tags) )] \
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) ()
|
||||
|
||||
#define CHECK_FOR_TEST_CASE_CLASH
|
||||
|
||||
#define INTERNAL_CATCH_MAP_CATEGORY_TO_TAG( Category, Tag ) \
|
||||
INTERNAL_CATCH_MAP_CATEGORY_TO_TAG2( #Category, Tag, __COUNTER__ )
|
||||
|
||||
#define FAIL_STRING( str ) _T( str )
|
||||
|
||||
#else // detect CLR
|
||||
|
||||
// Native tests
|
||||
@ -173,99 +209,161 @@ struct NameAndDesc {
|
||||
#define TEST_IMPL_2(tuple) TEST_IMPL2 tuple
|
||||
#define TEST_IMPL2( INTERNAL_CATCH_SPLIT_ARG_1,INTERNAL_CATCH_SPLIT_ARG_2,N,...) L#INTERNAL_CATCH_SPLIT_ARG_1
|
||||
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM(...) CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPL( (__VA_ARGS__, 2, 1) )
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPL(tuple) CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPL2 tuple
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPL2( INTERNAL_CATCH_SPLIT_ARG_1,INTERNAL_CATCH_SPLIT_ARG_2,N,...) #INTERNAL_CATCH_SPLIT_ARG_1
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(...) CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPLW( (__VA_ARGS__, 2, 1) )
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM(...) CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPLW( (__VA_ARGS__, 2, 1) )
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPLW(tuple) CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPL2W tuple
|
||||
#define CATCH_INTERNAL_HANDLE_EMPTY_PARAM_IMPL2W( INTERNAL_CATCH_SPLIT_ARG_1,INTERNAL_CATCH_SPLIT_ARG_2,N,...) L#INTERNAL_CATCH_SPLIT_ARG_1
|
||||
|
||||
#define INTERNAL_CATCH_TEST_METHOD( Method, UniqueExt, Name, Desc ) \
|
||||
#define INTERNAL_CATCH_TEST_METHOD( Count, UniqueExt, Name, Desc ) \
|
||||
public: \
|
||||
BEGIN_TEST_METHOD_ATTRIBUTE( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) ) \
|
||||
TEST_OWNER( CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(Name) ) \
|
||||
TEST_DESCRIPTION( CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(Name) ) \
|
||||
TEST_OWNER( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name) ) \
|
||||
TEST_DESCRIPTION( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name) ) \
|
||||
END_TEST_METHOD_ATTRIBUTE() \
|
||||
TEST_METHOD( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) ) \
|
||||
{ \
|
||||
Catch::NameAndDesc name_desc(CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(Name), Desc ); \
|
||||
CATCH_INTERNAL_RUN_SINGLE_TEST( Method ); \
|
||||
Catch::NameAndDesc name_desc(CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name), Desc ); \
|
||||
CATCH_INTERNAL_RUN_SINGLE_TEST(Count); \
|
||||
}
|
||||
|
||||
#define INTERNAL_CATCH_TEST_CLASS_METHOD( Method, UniqueExt, Name, Desc ) \
|
||||
#define BEGIN_INTERNAL_CATCH_BATCH_METHOD( Tags, UniqueExt ) \
|
||||
public: \
|
||||
BEGIN_TEST_METHOD_ATTRIBUTE( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) ) \
|
||||
TEST_OWNER( CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(Name) ) \
|
||||
TEST_DESCRIPTION( CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(Name) ) \
|
||||
END_TEST_METHOD_ATTRIBUTE() \
|
||||
TEST_METHOD( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) ) \
|
||||
{ \
|
||||
Catch::NameAndDesc name_desc( CATCH_INTERNAL_HANDLE_EMPTY_PARAMW(Name), Desc ); \
|
||||
CATCH_INTERNAL_RUN_SINGLE_CLASS_TEST( Method ); \
|
||||
}
|
||||
BEGIN_TEST_METHOD_ATTRIBUTE( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) ) \
|
||||
TEST_OWNER( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Tags) ) \
|
||||
TEST_DESCRIPTION( CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Tags) ) \
|
||||
END_TEST_METHOD_ATTRIBUTE() \
|
||||
TEST_METHOD( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H___M_E_T_H_O_D___, UniqueExt) )
|
||||
|
||||
#define CHECK_FOR_TEST_CASE_CLASH void INTERNAL_CATCH_UNIQUE_NAME_LINE( if_you_get_this_error_you_have_a_test_case_name_clash_please_put_a_namespace_around_the_test_case_at_line_, __LINE__ )() {}
|
||||
|
||||
#define INTERNAL_CATCH_MAP_CATEGORY_TO_TAG( Category, Tag ) \
|
||||
INTERNAL_CATCH_MAP_CATEGORY_TO_TAG2( Category, Tag, __COUNTER__ )
|
||||
|
||||
#define FAIL_STRING( str ) WIDEN( str )
|
||||
|
||||
#endif // detect CLR
|
||||
|
||||
#define INTERNAL_CATCH_CONCAT_LINE_COUNTER INTERNAL_CATCH_UNIQUE_NAME_LINE( INTERNAL_CATCH_UNIQUE_NAME_LINE( __LINE__, _ ), __COUNTER__ )
|
||||
#define INTERNAL_CATCH_CONCAT_LINE_COUNTER( count ) INTERNAL_CATCH_UNIQUE_NAME_LINE( INTERNAL_CATCH_UNIQUE_NAME_LINE( __LINE__, _ ), count )
|
||||
|
||||
#define CATCH_INTERNAL_RUN_SINGLE_TEST( Method ) \
|
||||
{ Catch::ConfigData cd; \
|
||||
#define CATCH_INTERNAL_CONFIG_SHOW_SUCCESS2( v, Count ) \
|
||||
namespace { CatchOverrides::ConfigShowSuccessfulTests<Catch::IConfig const*> INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H_____O_V_E_R_R_I_D_E____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(__FILE__, Count, v); }
|
||||
|
||||
#define CATCH_INTERNAL_CONFIG_WARN_MISSING_ASSERTIONS2( v, Count ) \
|
||||
namespace { CatchOverrides::ConfigWarnMissingAssertions<Catch::IConfig const*> INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H_____O_V_E_R_R_I_D_E____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(__FILE__, Count, v); }
|
||||
|
||||
#define CATCH_INTERNAL_CONFIG_SHOW_SUCCESS( v ) \
|
||||
CATCH_INTERNAL_CONFIG_SHOW_SUCCESS2( v, __COUNTER__)
|
||||
|
||||
#define CATCH_INTERNAL_CONFIG_WARN_MISSING_ASSERTIONS( v ) \
|
||||
CATCH_INTERNAL_CONFIG_WARN_MISSING_ASSERTIONS2( v, __COUNTER__)
|
||||
|
||||
#define CATCH_INTERNAL_RUN_SINGLE_TEST( Count ) \
|
||||
{ CatchOverrides::ConfigGuard cg; \
|
||||
Catch::ConfigData cd(cg.value().get()); \
|
||||
cd.name = name_desc.name; \
|
||||
cd.abortAfter = 1; \
|
||||
cd.showSuccessfulTests = CatchOverrides::Config<Catch::IConfig const*>::instance().includeSuccessfulResults(__FILE__, Count ); \
|
||||
cd.warnings = (CatchOverrides::Config<Catch::IConfig const*>::instance().warnAboutMissingAssertions(__FILE__, Count ) ? Catch::WarnAbout::NoAssertions : Catch::WarnAbout::Nothing); \
|
||||
Catch::Ptr<Catch::Config> config(new Catch::Config(cd)); \
|
||||
Catch::MSTestReporter* rep = new Catch::MSTestReporter(config.get()); \
|
||||
Catch::RunContext tr(config.get(), rep); \
|
||||
Catch::TestCase tc = Catch::makeTestCase( new Catch::FreeFunctionTestCase( & Method ), "", name_desc.name, name_desc.description, CATCH_INTERNAL_LINEINFO ); \
|
||||
tr.runTest(tc); \
|
||||
std::vector<Catch::TestCase> testCase = Catch::getRegistryHub().getTestCaseRegistry().getMatchingTestCases(name_desc.name); \
|
||||
if( testCase.empty() ) Assert::Fail(FAIL_STRING("No tests match")); \
|
||||
if( testCase.size() > 1 ) Assert::Fail(FAIL_STRING("More than one test with the same name")); \
|
||||
Catch::Totals totals = tr.runTest(*testCase.begin()); \
|
||||
if( totals.assertions.failed > 0 ) { \
|
||||
INTERNAL_CATCH_TEST_THROW_FAILURE \
|
||||
} \
|
||||
}
|
||||
|
||||
#define CATCH_INTERNAL_RUN_SINGLE_CLASS_TEST( ClassMethod ) \
|
||||
{ Catch::ConfigData cd; \
|
||||
cd.name = name_desc.name; \
|
||||
Catch::Ptr<Catch::Config> config(new Catch::Config(cd)); \
|
||||
Catch::MSTestReporter* rep = new Catch::MSTestReporter(config.get()); \
|
||||
Catch::RunContext tr(config.get(), rep); \
|
||||
Catch::TestCase tc = Catch::makeTestCase( new Catch::MethodTestCase( & ClassMethod ), # ClassMethod, name_desc.name, name_desc.description, CATCH_INTERNAL_LINEINFO ); \
|
||||
tr.runTest(tc); \
|
||||
}
|
||||
|
||||
#define INTERNAL_CATCH_TESTCASE2( UniqueExt, Name, Desc ) \
|
||||
#define INTERNAL_CATCH_TESTCASE2( Count, Name, Desc ) \
|
||||
CHECK_FOR_TEST_CASE_CLASH \
|
||||
static void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt )(); \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( UniqueExt ) { \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, UniqueExt ) ) \
|
||||
static void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(); \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) { \
|
||||
Catch::AutoReg INTERNAL_CATCH_UNIQUE_NAME( autoRegistrar )( & INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ), CATCH_INTERNAL_LINEINFO, Catch::NameAndDesc(CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name), Desc) ); \
|
||||
CatchOverrides::ConfigReset<Catch::IConfig const*> INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_O_N_F_I_G___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(__FILE__, Count); \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) ) \
|
||||
{ \
|
||||
INTERNAL_CATCH_CLASS_CONTEXT \
|
||||
INTERNAL_CATCH_TEST_METHOD( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt ), UniqueExt, Name, Desc ) \
|
||||
INTERNAL_CATCH_TEST_METHOD( Count, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ), Name, Desc ) \
|
||||
}; \
|
||||
} \
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt )()
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )()
|
||||
|
||||
#define INTERNAL_CATCH_METHOD_AS_TEST_CASE2( QualifiedMethod, UniqueExt, Name, Desc ) \
|
||||
#define INTERNAL_CATCH_METHOD_AS_TEST_CASE2( QualifiedMethod, Count, Name, Desc ) \
|
||||
CHECK_FOR_TEST_CASE_CLASH \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( UniqueExt ) { \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, UniqueExt ) ) \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) { \
|
||||
Catch::AutoReg INTERNAL_CATCH_UNIQUE_NAME( autoRegistrar )( & QualifiedMethod, "&" # QualifiedMethod, Catch::NameAndDesc(CATCH_INTERNAL_HANDLE_EMPTY_PARAM(Name), Desc), CATCH_INTERNAL_LINEINFO ); \
|
||||
CatchOverrides::ConfigReset<Catch::IConfig const*> INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_O_N_F_I_G___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(__FILE__, Count); \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) ) \
|
||||
{ \
|
||||
INTERNAL_CATCH_CLASS_CONTEXT \
|
||||
INTERNAL_CATCH_TEST_CLASS_METHOD( QualifiedMethod, UniqueExt, Name, Desc ) \
|
||||
INTERNAL_CATCH_TEST_METHOD( Count, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ), Name, Desc ) \
|
||||
}; \
|
||||
};
|
||||
|
||||
#define INTERNAL_CATCH_TEST_CASE_METHOD2( ClassName, UniqueExt, TestName, Desc ) \
|
||||
#define INTERNAL_CATCH_TEST_CASE_METHOD2( ClassName, Count, TestName, Desc ) \
|
||||
CHECK_FOR_TEST_CASE_CLASH \
|
||||
struct INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt ) : ClassName { \
|
||||
struct INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) : ClassName { \
|
||||
void test(); \
|
||||
static void invoke() { INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt ) tmp; tmp.test(); } \
|
||||
static void invoke() { INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) tmp; tmp.test(); } \
|
||||
}; \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( UniqueExt ) { \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, UniqueExt ) ) \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) { \
|
||||
Catch::AutoReg INTERNAL_CATCH_UNIQUE_NAME( autoRegistrar )( & INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )::invoke, CATCH_INTERNAL_LINEINFO, Catch::NameAndDesc(CATCH_INTERNAL_HANDLE_EMPTY_PARAM(TestName), Desc) ); \
|
||||
CatchOverrides::ConfigReset<Catch::IConfig const*> INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_O_N_F_I_G___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(__FILE__, Count); \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) ) \
|
||||
{ \
|
||||
INTERNAL_CATCH_CLASS_CONTEXT \
|
||||
INTERNAL_CATCH_TEST_METHOD( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt )::invoke, UniqueExt, TestName, Desc ) \
|
||||
INTERNAL_CATCH_TEST_METHOD( Count, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ), TestName, Desc ) \
|
||||
}; \
|
||||
} \
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, UniqueExt )::test()
|
||||
void INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )::test()
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED)
|
||||
|
||||
#define INTERNAL_CATCH_TEST_REPORT_BATCH_FAILURE( count ) \
|
||||
{ \
|
||||
std::stringstream _sf; \
|
||||
_sf << count << " assertions failed - check output for results."; \
|
||||
std::string fail = _sf.str(); \
|
||||
Assert::Fail(Catch::convert_string_for_assert(fail)); \
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
#define INTERNAL_CATCH_TEST_REPORT_BATCH_FAILURE( count ) \
|
||||
{ \
|
||||
std::wstringstream _s; \
|
||||
_s << count << " assertions failed - check output for results."; \
|
||||
std::wstring ws = _s.str(); \
|
||||
Assert::Fail(ws.c_str()); \
|
||||
}
|
||||
#endif
|
||||
|
||||
#define INTERNAL_CATCH_MAP_CATEGORY_TO_TAG2( Category, Tag, Count ) \
|
||||
CHECK_FOR_TEST_CASE_CLASH \
|
||||
namespace CATCH_INTERNAL_NAMESPACE( INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) { \
|
||||
CatchOverrides::ConfigReset<Catch::IConfig const*> INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_O_N_F_I_G___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) )(__FILE__, Count); \
|
||||
INTERNAL_CATCH_CLASS_DEFINITION( INTERNAL_CATCH_UNIQUE_NAME_LINE( C_A_T_C_H____T_E_S_T____C_L_A_S_S___, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) ) \
|
||||
{ \
|
||||
INTERNAL_CATCH_CLASS_CONTEXT \
|
||||
BEGIN_INTERNAL_CATCH_BATCH_METHOD( Category, INTERNAL_CATCH_CONCAT_LINE_COUNTER( Count ) ) \
|
||||
{ \
|
||||
Catch::ConfigData cd; \
|
||||
cd.showSuccessfulTests = CatchOverrides::Config<Catch::IConfig const*>::instance().includeSuccessfulResults(__FILE__, Count ); \
|
||||
cd.warnings = (CatchOverrides::Config<Catch::IConfig const*>::instance().warnAboutMissingAssertions(__FILE__, Count ) ? Catch::WarnAbout::NoAssertions : Catch::WarnAbout::Nothing); \
|
||||
cd.reporterName = "vs_reporter"; \
|
||||
cd.name = "Batch run using tag : " Tag; \
|
||||
cd.testsOrTags.push_back( Tag ); \
|
||||
Catch::Ptr<Catch::Config> config(new Catch::Config(cd)); \
|
||||
Catch::ReporterRegistrar<Catch::MSTestReporter> reporterReg("vs_reporter"); \
|
||||
Catch::Runner runner(config); \
|
||||
Catch::Totals totals = runner.runTests(); \
|
||||
if( totals.assertions.failed > 0 ) { \
|
||||
INTERNAL_CATCH_TEST_REPORT_BATCH_FAILURE(totals.assertions.failed) \
|
||||
} \
|
||||
} \
|
||||
}; \
|
||||
}
|
||||
|
||||
//#undef CATCH_CONFIG_VARIADIC_MACROS
|
||||
|
||||
@ -279,29 +377,29 @@ struct NameAndDesc {
|
||||
#define INTERNAL_CATCH_SPLIT_TAGS_IMPL_(INTERNAL_CATCH_SPLIT_ARG_1,INTERNAL_CATCH_SPLIT_ARG_2,N,...) INTERNAL_CATCH_SPLIT_ARG_2
|
||||
|
||||
#define INTERNAL_CATCH_TESTCASE( ... ) \
|
||||
INTERNAL_CATCH_TESTCASE2( INTERNAL_CATCH_CONCAT_LINE_COUNTER, INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__), INTERNAL_CATCH_SPLIT_TAGS(__VA_ARGS__) )
|
||||
INTERNAL_CATCH_TESTCASE2( __COUNTER__ , INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__), INTERNAL_CATCH_SPLIT_TAGS(__VA_ARGS__) )
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#define INTERNAL_CATCH_METHOD_AS_TEST_CASE( QualifiedMethod, ... ) \
|
||||
INTERNAL_CATCH_METHOD_AS_TEST_CASE2( QualifiedMethod, INTERNAL_CATCH_CONCAT_LINE_COUNTER, INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__), INTERNAL_CATCH_SPLIT_TAGS(__VA_ARGS__) )
|
||||
INTERNAL_CATCH_METHOD_AS_TEST_CASE2( QualifiedMethod, __COUNTER__, INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__), INTERNAL_CATCH_SPLIT_TAGS(__VA_ARGS__) )
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#define INTERNAL_CATCH_TEST_CASE_METHOD( ClassName, ... )\
|
||||
INTERNAL_CATCH_TEST_CASE_METHOD2(ClassName, INTERNAL_CATCH_CONCAT_LINE_COUNTER, INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__), INTERNAL_CATCH_SPLIT_TAGS(__VA_ARGS__) )
|
||||
INTERNAL_CATCH_TEST_CASE_METHOD2(ClassName, __COUNTER__, INTERNAL_CATCH_SPLIT_ARGS_2(__VA_ARGS__), INTERNAL_CATCH_SPLIT_TAGS(__VA_ARGS__) )
|
||||
|
||||
#else
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#define INTERNAL_CATCH_TESTCASE( Name, Desc ) \
|
||||
INTERNAL_CATCH_TESTCASE2( INTERNAL_CATCH_CONCAT_LINE_COUNTER, Name, Desc )
|
||||
INTERNAL_CATCH_TESTCASE2( __COUNTER__ , Name, Desc )
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#define INTERNAL_CATCH_METHOD_AS_TEST_CASE( QualifiedMethod, Name, Desc ) \
|
||||
INTERNAL_CATCH_METHOD_AS_TEST_CASE2( QualifiedMethod, INTERNAL_CATCH_CONCAT_LINE_COUNTER, Name, Desc )
|
||||
INTERNAL_CATCH_METHOD_AS_TEST_CASE2( QualifiedMethod, __COUNTER__, Name, Desc )
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#define INTERNAL_CATCH_TEST_CASE_METHOD( ClassName, TestName, Desc )\
|
||||
INTERNAL_CATCH_TEST_CASE_METHOD2(ClassName, INTERNAL_CATCH_CONCAT_LINE_COUNTER, TestName, Desc )
|
||||
INTERNAL_CATCH_TEST_CASE_METHOD2(ClassName, __COUNTER__, TestName, Desc )
|
||||
|
||||
#endif
|
||||
|
||||
@ -320,51 +418,6 @@ struct NameAndDesc {
|
||||
|
||||
#include "catch_exception_translator_registry.hpp"
|
||||
|
||||
namespace Catch {
|
||||
inline NonCopyable::~NonCopyable() {}
|
||||
inline IShared::~IShared() {}
|
||||
inline StreamBufBase::~StreamBufBase() throw() {}
|
||||
inline IContext::~IContext() {}
|
||||
inline IResultCapture::~IResultCapture() {}
|
||||
inline ITestCase::~ITestCase() {}
|
||||
inline ITestCaseRegistry::~ITestCaseRegistry() {}
|
||||
inline IRegistryHub::~IRegistryHub() {}
|
||||
inline IMutableRegistryHub::~IMutableRegistryHub() {}
|
||||
inline IExceptionTranslator::~IExceptionTranslator() {}
|
||||
inline IExceptionTranslatorRegistry::~IExceptionTranslatorRegistry() {}
|
||||
inline IReporterFactory::~IReporterFactory() {}
|
||||
inline IReporterRegistry::~IReporterRegistry() {}
|
||||
inline IStreamingReporter::~IStreamingReporter() {}
|
||||
inline AssertionStats::~AssertionStats() {}
|
||||
inline SectionStats::~SectionStats() {}
|
||||
inline TestCaseStats::~TestCaseStats() {}
|
||||
inline TestGroupStats::~TestGroupStats() {}
|
||||
inline TestRunStats::~TestRunStats() {}
|
||||
//CumulativeReporterBase::SectionNode::~SectionNode() {}
|
||||
//CumulativeReporterBase::~CumulativeReporterBase() {}
|
||||
|
||||
//StreamingReporterBase::~StreamingReporterBase() {}
|
||||
//ConsoleReporter::~ConsoleReporter() {}
|
||||
inline IRunner::~IRunner() {}
|
||||
inline IMutableContext::~IMutableContext() {}
|
||||
inline IConfig::~IConfig() {}
|
||||
//XmlReporter::~XmlReporter() {}
|
||||
//JunitReporter::~JunitReporter() {}
|
||||
//TestRegistry::~TestRegistry() {}
|
||||
inline FreeFunctionTestCase::~FreeFunctionTestCase() {}
|
||||
inline IGeneratorInfo::~IGeneratorInfo() {}
|
||||
inline IGeneratorsForTest::~IGeneratorsForTest() {}
|
||||
|
||||
inline Matchers::Impl::StdString::Equals::~Equals() {}
|
||||
inline Matchers::Impl::StdString::Contains::~Contains() {}
|
||||
inline Matchers::Impl::StdString::StartsWith::~StartsWith() {}
|
||||
inline Matchers::Impl::StdString::EndsWith::~EndsWith() {}
|
||||
|
||||
inline void Config::dummy() {}
|
||||
|
||||
//INTERNAL_CATCH_REGISTER_LEGACY_REPORTER( "xml", XmlReporter )
|
||||
}
|
||||
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic pop
|
||||
#endif
|
||||
|
@ -46,15 +46,27 @@ namespace Catch {
|
||||
#endif // detect CLR
|
||||
|
||||
struct MSTestReporter : SharedImpl<IStreamingReporter> {
|
||||
MSTestReporter( ReporterConfig const& _config )
|
||||
: m_config( _config.fullConfig() ),
|
||||
m_headerPrinted( false ),
|
||||
m_atLeastOneTestCasePrinted( false ),
|
||||
m_failed(0)
|
||||
{}
|
||||
|
||||
MSTestReporter( Ptr<IConfig> const& _fullConfig )
|
||||
: m_config( _fullConfig ),
|
||||
m_headerPrinted( false ),
|
||||
m_atLeastOneTestCasePrinted( false )
|
||||
m_atLeastOneTestCasePrinted( false ),
|
||||
m_failed(0)
|
||||
{}
|
||||
|
||||
virtual ~MSTestReporter() {
|
||||
if( m_atLeastOneTestCasePrinted ) {
|
||||
write_output_message(stream.str());
|
||||
/*if( m_failed )
|
||||
{
|
||||
Assert::IsTrue(false, L"At least one test failed - examine output for failures.");
|
||||
}*/
|
||||
}
|
||||
}
|
||||
|
||||
@ -120,9 +132,6 @@ namespace Catch {
|
||||
write_output_message(_testCaseStats.stdErr);
|
||||
write_output_message(getDoubleDashes());
|
||||
}
|
||||
if( _testCaseStats.totals.assertions.failed ) {
|
||||
Assert::IsTrue(false, L"At least one test failed - examine output for CHECK failures.");
|
||||
}
|
||||
m_headerPrinted = false;
|
||||
currentTestCaseInfo.reset();
|
||||
assert( m_sectionStack.empty() );
|
||||
@ -141,6 +150,7 @@ namespace Catch {
|
||||
printTotalsDivider();
|
||||
printTotals( _testRunStats.totals );
|
||||
stream << "\r\n" << "\r\n";
|
||||
m_failed = _testRunStats.totals.testCases.failed;
|
||||
currentTestCaseInfo.reset();
|
||||
currentGroupInfo.reset();
|
||||
currentTestRunInfo.reset();
|
||||
@ -448,6 +458,7 @@ namespace Catch {
|
||||
std::vector<SectionInfo> m_sectionStack;
|
||||
bool m_headerPrinted;
|
||||
bool m_atLeastOneTestCasePrinted;
|
||||
size_t m_failed;
|
||||
};
|
||||
|
||||
} // end namespace Catch
|
||||
|
@ -15,21 +15,24 @@ namespace Counter {
|
||||
int g_haveCountedMessages = 0;
|
||||
}
|
||||
|
||||
// This test works with the equivalent in MessageInstantiationTests2.cpp
|
||||
// The first test to reach this point will increment the MessageInfo counter. Subsequent tests
|
||||
// just check the value. The purpose of this test is to verify that the compiler's
|
||||
// greedy instantiation (or whatever process it uses) eliminate all other
|
||||
// references to the globalCount
|
||||
|
||||
TEST_CASE("message counting1","")
|
||||
namespace MI1
|
||||
{
|
||||
if( Counter::g_haveCountedMessages > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<unsigned int>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
// This test works with the equivalent in MessageInstantiationTests2.cpp
|
||||
// The first test to reach this point will increment the MessageInfo counter. Subsequent tests
|
||||
// just check the value. The purpose of this test is to verify that the compiler's
|
||||
// greedy instantiation (or whatever process it uses) eliminate all other
|
||||
// references to the globalCount
|
||||
|
||||
TEST_CASE("message counting1","")
|
||||
{
|
||||
++Catch::MessageInfoCounter<unsigned int>::globalCount;
|
||||
Counter::g_haveCountedMessages = 1;
|
||||
if( Counter::g_haveCountedMessages > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<unsigned int>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
{
|
||||
++Catch::MessageInfoCounter<unsigned int>::globalCount;
|
||||
Counter::g_haveCountedMessages = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -37,14 +40,17 @@ namespace LongCounter {
|
||||
int g_haveCountedMessagesLong = 0;
|
||||
}
|
||||
|
||||
TEST_CASE("long message counting1","")
|
||||
namespace MI1
|
||||
{
|
||||
if( LongCounter::g_haveCountedMessagesLong > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<long>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
TEST_CASE("long message counting1","")
|
||||
{
|
||||
++Catch::MessageInfoCounter<long>::globalCount;
|
||||
LongCounter::g_haveCountedMessagesLong = 1;
|
||||
if( LongCounter::g_haveCountedMessagesLong > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<long>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
{
|
||||
++Catch::MessageInfoCounter<long>::globalCount;
|
||||
LongCounter::g_haveCountedMessagesLong = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -14,21 +14,24 @@ namespace Counter {
|
||||
extern int g_haveCountedMessages;
|
||||
}
|
||||
|
||||
// This test works with the equivalent in MessageInstantiationTests1.cpp
|
||||
// The first test to reach this point will increment the MessageInfo counter. Subsequent tests
|
||||
// just check the value. The purpose of this test is to verify that the compiler's
|
||||
// greedy instantiation (or whatever process it uses) eliminate all other
|
||||
// references to the globalCount
|
||||
|
||||
TEST_CASE("message counting2","")
|
||||
namespace MI2
|
||||
{
|
||||
if( Counter::g_haveCountedMessages > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<unsigned int>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
// This test works with the equivalent in MessageInstantiationTests1.cpp
|
||||
// The first test to reach this point will increment the MessageInfo counter. Subsequent tests
|
||||
// just check the value. The purpose of this test is to verify that the compiler's
|
||||
// greedy instantiation (or whatever process it uses) eliminate all other
|
||||
// references to the globalCount
|
||||
|
||||
TEST_CASE("message counting2","")
|
||||
{
|
||||
++Catch::MessageInfoCounter<unsigned int>::globalCount;
|
||||
Counter::g_haveCountedMessages = 1;
|
||||
if( Counter::g_haveCountedMessages > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<unsigned int>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
{
|
||||
++Catch::MessageInfoCounter<unsigned int>::globalCount;
|
||||
Counter::g_haveCountedMessages = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -36,14 +39,17 @@ namespace LongCounter {
|
||||
extern int g_haveCountedMessagesLong;
|
||||
}
|
||||
|
||||
TEST_CASE("long message counting2","")
|
||||
namespace MI2
|
||||
{
|
||||
if( LongCounter::g_haveCountedMessagesLong > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<long>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
TEST_CASE("long message counting2","")
|
||||
{
|
||||
++Catch::MessageInfoCounter<long>::globalCount;
|
||||
LongCounter::g_haveCountedMessagesLong = 1;
|
||||
if( LongCounter::g_haveCountedMessagesLong > 0 ) {
|
||||
REQUIRE( Catch::MessageInfoCounter<long>::globalCount > 0 );
|
||||
}
|
||||
else
|
||||
{
|
||||
++Catch::MessageInfoCounter<long>::globalCount;
|
||||
LongCounter::g_haveCountedMessagesLong = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
187
projects/SelfTest/RunAllTests.cpp
Normal file
187
projects/SelfTest/RunAllTests.cpp
Normal file
@ -0,0 +1,187 @@
|
||||
/*
|
||||
* Created by Phil on 22/10/2010.
|
||||
* Copyright 2010 Two Blue Cubes Ltd
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
* file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
|
||||
#include "catch.hpp"
|
||||
#include "internal/catch_text.h"
|
||||
#include "internal/catch_console_colour.hpp"
|
||||
|
||||
namespace AllTestsRunner {
|
||||
|
||||
class NullStreamingReporter : public Catch::SharedImpl<Catch::IStreamingReporter> {
|
||||
public:
|
||||
|
||||
virtual ~NullStreamingReporter();
|
||||
|
||||
static std::string getDescription() {
|
||||
return "null reporter";
|
||||
}
|
||||
|
||||
private: // IStreamingReporter
|
||||
|
||||
virtual Catch::ReporterPreferences getPreferences() const {
|
||||
return Catch::ReporterPreferences();
|
||||
}
|
||||
|
||||
virtual void noMatchingTestCases( std::string const& ) {}
|
||||
virtual void testRunStarting( Catch::TestRunInfo const& ) {}
|
||||
virtual void testGroupStarting( Catch::GroupInfo const& ) {}
|
||||
virtual void testCaseStarting( Catch::TestCaseInfo const& ) {}
|
||||
virtual void sectionStarting( Catch::SectionInfo const& ) {}
|
||||
virtual void assertionStarting( Catch::AssertionInfo const& ) {}
|
||||
virtual bool assertionEnded( Catch::AssertionStats const& ) { return false; }
|
||||
virtual void sectionEnded( Catch::SectionStats const& ) {}
|
||||
virtual void testCaseEnded( Catch::TestCaseStats const& ) {}
|
||||
virtual void testGroupEnded( Catch::TestGroupStats const& ) {}
|
||||
virtual void testRunEnded( Catch::TestRunStats const& ) {}
|
||||
};
|
||||
|
||||
class EmbeddedRunner {
|
||||
|
||||
public:
|
||||
EmbeddedRunner() : m_reporter( new NullStreamingReporter() ) {}
|
||||
|
||||
Catch::Totals runMatching( const std::string& rawTestSpec,
|
||||
std::size_t groupIndex,
|
||||
std::size_t groupsCount,
|
||||
const std::string& reporter = "console" );
|
||||
|
||||
private:
|
||||
Catch::Ptr<Catch::IStreamingReporter> m_reporter;
|
||||
};
|
||||
|
||||
class MetaTestRunner {
|
||||
|
||||
public:
|
||||
struct Expected { enum Result {
|
||||
ToSucceed,
|
||||
ToFail
|
||||
}; };
|
||||
|
||||
MetaTestRunner( Expected::Result expectedResult, std::size_t groupIndex, std::size_t groupsCount )
|
||||
: m_expectedResult( expectedResult ),
|
||||
m_groupIndex( groupIndex ),
|
||||
m_groupsCount( groupsCount )
|
||||
{}
|
||||
|
||||
static void runMatching( const std::string& testSpec,
|
||||
Expected::Result expectedResult,
|
||||
std::size_t groupIndex,
|
||||
std::size_t groupsCount ) {
|
||||
forEach( Catch::getRegistryHub().getTestCaseRegistry().getMatchingTestCases( testSpec ),
|
||||
MetaTestRunner( expectedResult, groupIndex, groupsCount ) );
|
||||
}
|
||||
|
||||
void operator()( const Catch::TestCase& testCase ) {
|
||||
std::string name;
|
||||
Catch::Totals totals;
|
||||
{
|
||||
EmbeddedRunner runner;
|
||||
name = testCase.getTestCaseInfo().name;
|
||||
totals = runner.runMatching( name, m_groupIndex, m_groupsCount );
|
||||
}
|
||||
switch( m_expectedResult ) {
|
||||
case Expected::ToSucceed:
|
||||
if( totals.assertions.failed > 0 ) {
|
||||
FAIL( "Expected test case '"
|
||||
<< name
|
||||
<< "' to succeed but there was/ were "
|
||||
<< totals.assertions.failed << " failure(s)" );
|
||||
}
|
||||
else {
|
||||
SUCCEED( "Tests passed, as expected" );
|
||||
}
|
||||
break;
|
||||
case Expected::ToFail:
|
||||
if( totals.assertions.failed == 0 ) {
|
||||
FAIL( "Expected test case '"
|
||||
<< name
|
||||
<< "' to fail but there was/ were "
|
||||
<< totals.assertions.passed << " success(es)" );
|
||||
}
|
||||
else {
|
||||
SUCCEED( "Tests failed, as expected" );
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
Expected::Result m_expectedResult;
|
||||
std::size_t m_groupIndex;
|
||||
std::size_t m_groupsCount;
|
||||
};
|
||||
|
||||
NullStreamingReporter::~NullStreamingReporter() {}
|
||||
|
||||
Catch::Totals EmbeddedRunner::runMatching( const std::string& rawTestSpec, std::size_t groupIndex, std::size_t groupsCount, const std::string& ) {
|
||||
std::ostringstream oss;
|
||||
Catch::Ptr<Catch::Config> config = new Catch::Config();
|
||||
config->setStreamBuf( oss.rdbuf() );
|
||||
|
||||
Catch::Totals totals;
|
||||
|
||||
// Scoped because RunContext doesn't report EndTesting until its destructor
|
||||
{
|
||||
Catch::RunContext runner( config.get(), m_reporter.get() );
|
||||
totals = runner.runMatching( rawTestSpec, groupIndex, groupsCount );
|
||||
}
|
||||
return totals;
|
||||
}
|
||||
|
||||
TEST_CASE( "Run all failing and succeeding tests", "[vsall]" ) {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
SECTION( "selftest/expected result",
|
||||
"Tests do what they claim" ) {
|
||||
|
||||
#ifdef _UNICODE
|
||||
std::cout << "using Unicode..." << std::endl;
|
||||
#else
|
||||
std::cout << "using Mbcs..." << std::endl;
|
||||
#endif
|
||||
|
||||
SECTION( "selftest/expected result/failing tests",
|
||||
"Tests in the 'failing' branch fail" ) {
|
||||
std::cout << "Tests in the 'failing' branch fail" << std::endl;
|
||||
MetaTestRunner::runMatching( "./failing/*", MetaTestRunner::Expected::ToFail, 0, 2 );
|
||||
}
|
||||
|
||||
SECTION( "selftest/expected result/succeeding tests",
|
||||
"Tests in the 'succeeding' branch succeed" ) {
|
||||
std::cout << "Tests in the 'succeeding' branch succeed" << std::endl;
|
||||
MetaTestRunner::runMatching( "./succeeding/*", MetaTestRunner::Expected::ToSucceed, 1, 2 );
|
||||
}
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
SECTION( "selftest/test counts",
|
||||
"Number of test cases that run is fixed" ) {
|
||||
EmbeddedRunner runner;
|
||||
|
||||
SECTION( "selftest/test counts/succeeding tests",
|
||||
"Number of 'succeeding' tests is fixed" ) {
|
||||
std::cout << "Number of 'succeeding' tests is fixed" << std::endl;
|
||||
Catch::Totals totals = runner.runMatching( "./succeeding/*", 0, 2 );
|
||||
CHECK( totals.assertions.passed == 298 );
|
||||
CHECK( totals.assertions.failed == 0 );
|
||||
}
|
||||
|
||||
SECTION( "selftest/test counts/failing tests",
|
||||
"Number of 'failing' tests is fixed" ) {
|
||||
std::cout << "Number of 'failing' tests is fixed" << std::endl;
|
||||
Catch::Totals totals = runner.runMatching( "./failing/*", 1, 2 );
|
||||
CHECK( totals.assertions.passed == 2 );
|
||||
CHECK( totals.assertions.failed == 77 );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED) || defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
CATCH_MAP_CATEGORY_TO_TAG(all, "[vsall]");
|
||||
#endif
|
||||
}
|
@ -346,35 +346,35 @@ TEST_CASE( "Long strings can be wrapped", "[wrap]" ) {
|
||||
std::string testString = "one two three four";
|
||||
|
||||
SECTION( "No wrapping", "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 80 ) ).toString() == testString );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 18 ) ).toString() == testString );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 80 ) ).toString() == testString );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 18 ) ).toString() == testString );
|
||||
}
|
||||
SECTION( "Wrapped once", "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 17 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 16 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 14 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 13 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 12 ) ).toString() == "one two\nthree four" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 17 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 16 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 14 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 13 ) ).toString() == "one two three\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 12 ) ).toString() == "one two\nthree four" );
|
||||
}
|
||||
SECTION( "Wrapped twice", "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 9 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 8 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 7 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 9 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 8 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 7 ) ).toString() == "one two\nthree\nfour" );
|
||||
}
|
||||
SECTION( "Wrapped three times", "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 6 ) ).toString() == "one\ntwo\nthree\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 5 ) ).toString() == "one\ntwo\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 6 ) ).toString() == "one\ntwo\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 5 ) ).toString() == "one\ntwo\nthree\nfour" );
|
||||
}
|
||||
SECTION( "Short wrap", "" ) {
|
||||
CHECK( Text( "abcdef", TextAttributes().setWidth( 4 ) ).toString() == "abc-\ndef" );
|
||||
CHECK( Text( "abcdefg", TextAttributes().setWidth( 4 ) ).toString() == "abc-\ndefg" );
|
||||
CHECK( Text( "abcdefgh", TextAttributes().setWidth( 4 ) ).toString() == "abc-\ndef-\ngh" );
|
||||
CHECK( Catch::Text( "abcdef", TextAttributes().setWidth( 4 ) ).toString() == "abc-\ndef" );
|
||||
CHECK( Catch::Text( "abcdefg", TextAttributes().setWidth( 4 ) ).toString() == "abc-\ndefg" );
|
||||
CHECK( Catch::Text( "abcdefgh", TextAttributes().setWidth( 4 ) ).toString() == "abc-\ndef-\ngh" );
|
||||
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 4 ) ).toString() == "one\ntwo\nthr-\nee\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 3 ) ).toString() == "one\ntwo\nth-\nree\nfo-\nur" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 4 ) ).toString() == "one\ntwo\nthr-\nee\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 3 ) ).toString() == "one\ntwo\nth-\nree\nfo-\nur" );
|
||||
}
|
||||
SECTION( "As container", "" ) {
|
||||
Text text( testString, TextAttributes().setWidth( 6 ) );
|
||||
Catch::Text text( testString, TextAttributes().setWidth( 6 ) );
|
||||
REQUIRE( text.size() == 4 );
|
||||
CHECK( text[0] == "one" );
|
||||
CHECK( text[1] == "two" );
|
||||
@ -382,7 +382,7 @@ TEST_CASE( "Long strings can be wrapped", "[wrap]" ) {
|
||||
CHECK( text[3] == "four" );
|
||||
}
|
||||
SECTION( "Indent first line differently", "" ) {
|
||||
Text text( testString, TextAttributes()
|
||||
Catch::Text text( testString, TextAttributes()
|
||||
.setWidth( 10 )
|
||||
.setIndent( 4 )
|
||||
.setInitialIndent( 1 ) );
|
||||
@ -397,22 +397,22 @@ TEST_CASE( "Long strings can be wrapped", "[wrap]" ) {
|
||||
std::string testString = "one two\nthree four";
|
||||
|
||||
SECTION( "No wrapping" , "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 80 ) ).toString() == testString );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 18 ) ).toString() == testString );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 10 ) ).toString() == testString );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 80 ) ).toString() == testString );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 18 ) ).toString() == testString );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 10 ) ).toString() == testString );
|
||||
}
|
||||
SECTION( "Trailing newline" , "" ) {
|
||||
CHECK( Text( "abcdef\n", TextAttributes().setWidth( 10 ) ).toString() == "abcdef\n" );
|
||||
CHECK( Text( "abcdef", TextAttributes().setWidth( 6 ) ).toString() == "abcdef" );
|
||||
CHECK( Text( "abcdef\n", TextAttributes().setWidth( 6 ) ).toString() == "abcdef\n" );
|
||||
CHECK( Catch::Text( "abcdef\n", TextAttributes().setWidth( 10 ) ).toString() == "abcdef\n" );
|
||||
CHECK( Catch::Text( "abcdef", TextAttributes().setWidth( 6 ) ).toString() == "abcdef" );
|
||||
CHECK( Catch::Text( "abcdef\n", TextAttributes().setWidth( 6 ) ).toString() == "abcdef\n" );
|
||||
}
|
||||
SECTION( "Wrapped once", "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 9 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 8 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 7 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 9 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 8 ) ).toString() == "one two\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 7 ) ).toString() == "one two\nthree\nfour" );
|
||||
}
|
||||
SECTION( "Wrapped twice", "" ) {
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 6 ) ).toString() == "one\ntwo\nthree\nfour" );
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 6 ) ).toString() == "one\ntwo\nthree\nfour" );
|
||||
}
|
||||
}
|
||||
|
||||
@ -421,7 +421,7 @@ TEST_CASE( "Long strings can be wrapped", "[wrap]" ) {
|
||||
// guide: 1234567890123456789
|
||||
std::string testString = "one two \tthree four five six";
|
||||
|
||||
CHECK( Text( testString, TextAttributes().setWidth( 15 ) ).toString()
|
||||
CHECK( Catch::Text( testString, TextAttributes().setWidth( 15 ) ).toString()
|
||||
== "one two three\n four\n five\n six" );
|
||||
}
|
||||
|
||||
@ -522,12 +522,12 @@ TEST_CASE( "Strings can be rendered with colour", "[colour]" ) {
|
||||
|
||||
TEST_CASE( "Text can be formatted using the Text class", "" ) {
|
||||
|
||||
CHECK( Text( "hi there" ).toString() == "hi there" );
|
||||
CHECK( Catch::Text( "hi there" ).toString() == "hi there" );
|
||||
|
||||
TextAttributes narrow;
|
||||
narrow.setWidth( 6 );
|
||||
|
||||
CHECK( Text( "hi there", narrow ).toString() == "hi\nthere" );
|
||||
CHECK( Catch::Text( "hi there", narrow ).toString() == "hi\nthere" );
|
||||
}
|
||||
|
||||
TEST_CASE( "Long text is truncted", "[Text][Truncated]" ) {
|
||||
@ -537,7 +537,7 @@ TEST_CASE( "Long text is truncted", "[Text][Truncated]" ) {
|
||||
std::ostringstream oss;
|
||||
for(int i = 0; i < 600; ++i )
|
||||
oss << longLine << longLine << "\n";
|
||||
Text t( oss.str() );
|
||||
Catch::Text t( oss.str() );
|
||||
CHECK_THAT( t.toString(), EndsWith( "... message truncated due to excessive size" ) );
|
||||
|
||||
}
|
||||
|
@ -24,7 +24,7 @@ namespace Catch
|
||||
}
|
||||
}
|
||||
|
||||
namespace TrickTests
|
||||
namespace TrickyTests
|
||||
{
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
TEST_CASE
|
||||
@ -209,177 +209,180 @@ namespace ObjectWithNonConstEqualityOperator
|
||||
}
|
||||
}
|
||||
|
||||
namespace EnumBitFieldTests
|
||||
namespace TrickyTests
|
||||
{
|
||||
enum Bits {bit0 = 0x0001, bit1 = 0x0002, bit2 = 0x0004, bit3 = 0x0008, bit1and2 = 0x0006,
|
||||
bit30 = 0x40000000, bit31 = 0x80000000,
|
||||
bit30and31 = 0xc0000000};
|
||||
|
||||
TEST_CASE( "Test enum bit values", "[Tricky]" )
|
||||
namespace EnumBitFieldTests
|
||||
{
|
||||
REQUIRE( 0xc0000000 == bit30and31 );
|
||||
}
|
||||
}
|
||||
enum Bits {bit0 = 0x0001, bit1 = 0x0002, bit2 = 0x0004, bit3 = 0x0008, bit1and2 = 0x0006,
|
||||
bit30 = 0x40000000, bit31 = 0x80000000,
|
||||
bit30and31 = 0xc0000000};
|
||||
|
||||
struct Obj
|
||||
{
|
||||
Obj():prop(&p){}
|
||||
|
||||
int p;
|
||||
int* prop;
|
||||
};
|
||||
|
||||
TEST_CASE("boolean member", "[Tricky]")
|
||||
{
|
||||
Obj obj;
|
||||
REQUIRE( obj.prop != NULL );
|
||||
}
|
||||
|
||||
// Tests for a problem submitted by Ralph McArdell
|
||||
//
|
||||
// The static bool value should not need to be defined outside the
|
||||
// struct it is declared in - but when evaluating it in a deduced
|
||||
// context it appears to require the extra definition.
|
||||
// The issue was fixed by adding bool overloads to bypass the
|
||||
// templates that were there to deduce it.
|
||||
template <bool B>
|
||||
struct is_true
|
||||
{
|
||||
static const bool value = B;
|
||||
};
|
||||
|
||||
TEST_CASE( "(unimplemented) static bools can be evaluated", "[Tricky]" )
|
||||
{
|
||||
SECTION("compare to true","")
|
||||
{
|
||||
REQUIRE( is_true<true>::value == true );
|
||||
REQUIRE( true == is_true<true>::value );
|
||||
}
|
||||
SECTION("compare to false","")
|
||||
{
|
||||
REQUIRE( is_true<false>::value == false );
|
||||
REQUIRE( false == is_true<false>::value );
|
||||
TEST_CASE( "Test enum bit values", "[Tricky]" )
|
||||
{
|
||||
REQUIRE( 0xc0000000 == bit30and31 );
|
||||
}
|
||||
}
|
||||
|
||||
SECTION("negation", "")
|
||||
struct Obj
|
||||
{
|
||||
REQUIRE( !is_true<false>::value );
|
||||
Obj():prop(&p){}
|
||||
|
||||
int p;
|
||||
int* prop;
|
||||
};
|
||||
|
||||
TEST_CASE("boolean member", "[Tricky]")
|
||||
{
|
||||
Obj obj;
|
||||
REQUIRE( obj.prop != NULL );
|
||||
}
|
||||
|
||||
SECTION("double negation","")
|
||||
// Tests for a problem submitted by Ralph McArdell
|
||||
//
|
||||
// The static bool value should not need to be defined outside the
|
||||
// struct it is declared in - but when evaluating it in a deduced
|
||||
// context it appears to require the extra definition.
|
||||
// The issue was fixed by adding bool overloads to bypass the
|
||||
// templates that were there to deduce it.
|
||||
template <bool B>
|
||||
struct is_true
|
||||
{
|
||||
REQUIRE( !!is_true<true>::value );
|
||||
static const bool value = B;
|
||||
};
|
||||
|
||||
TEST_CASE( "(unimplemented) static bools can be evaluated", "[Tricky]" )
|
||||
{
|
||||
SECTION("compare to true","")
|
||||
{
|
||||
REQUIRE( is_true<true>::value == true );
|
||||
REQUIRE( true == is_true<true>::value );
|
||||
}
|
||||
SECTION("compare to false","")
|
||||
{
|
||||
REQUIRE( is_true<false>::value == false );
|
||||
REQUIRE( false == is_true<false>::value );
|
||||
}
|
||||
|
||||
SECTION("negation", "")
|
||||
{
|
||||
REQUIRE( !is_true<false>::value );
|
||||
}
|
||||
|
||||
SECTION("double negation","")
|
||||
{
|
||||
REQUIRE( !!is_true<true>::value );
|
||||
}
|
||||
|
||||
SECTION("direct","")
|
||||
{
|
||||
REQUIRE( is_true<true>::value );
|
||||
REQUIRE_FALSE( is_true<false>::value );
|
||||
}
|
||||
}
|
||||
|
||||
SECTION("direct","")
|
||||
// Uncomment these tests to produce an error at test registration time
|
||||
/*
|
||||
TEST_CASE( "Tests with the same name are not allowed", "[Tricky]" )
|
||||
{
|
||||
REQUIRE( is_true<true>::value );
|
||||
REQUIRE_FALSE( is_true<false>::value );
|
||||
|
||||
}
|
||||
}
|
||||
TEST_CASE( "Tests with the same name are not allowed", "[Tricky]" )
|
||||
{
|
||||
|
||||
// Uncomment these tests to produce an error at test registration time
|
||||
/*
|
||||
TEST_CASE( "Tests with the same name are not allowed", "[Tricky]" )
|
||||
{
|
||||
}
|
||||
*/
|
||||
|
||||
}
|
||||
TEST_CASE( "Tests with the same name are not allowed", "[Tricky]" )
|
||||
{
|
||||
struct Boolable
|
||||
{
|
||||
explicit Boolable( bool value ) : m_value( value ) {}
|
||||
|
||||
}
|
||||
*/
|
||||
operator Catch::SafeBool::type() const {
|
||||
return Catch::SafeBool::makeSafe( m_value );
|
||||
}
|
||||
|
||||
struct Boolable
|
||||
{
|
||||
explicit Boolable( bool value ) : m_value( value ) {}
|
||||
bool m_value;
|
||||
};
|
||||
|
||||
operator Catch::SafeBool::type() const {
|
||||
return Catch::SafeBool::makeSafe( m_value );
|
||||
TEST_CASE( "Objects that evaluated in boolean contexts can be checked", "[Tricky][SafeBool]" )
|
||||
{
|
||||
Boolable True( true );
|
||||
Boolable False( false );
|
||||
|
||||
CHECK( True );
|
||||
CHECK( !False );
|
||||
CHECK_FALSE( False );
|
||||
}
|
||||
|
||||
bool m_value;
|
||||
};
|
||||
|
||||
TEST_CASE( "Objects that evaluated in boolean contexts can be checked", "[Tricky][SafeBool]" )
|
||||
{
|
||||
Boolable True( true );
|
||||
Boolable False( false );
|
||||
|
||||
CHECK( True );
|
||||
CHECK( !False );
|
||||
CHECK_FALSE( False );
|
||||
}
|
||||
|
||||
TEST_CASE( "Assertions then sections", "[Tricky]" )
|
||||
{
|
||||
// This was causing a failure due to the way the console reporter was handling
|
||||
// the current section
|
||||
|
||||
REQUIRE( Catch::isTrue( true ) );
|
||||
|
||||
SECTION( "A section", "" )
|
||||
TEST_CASE( "Assertions then sections", "[Tricky]" )
|
||||
{
|
||||
// This was causing a failure due to the way the console reporter was handling
|
||||
// the current section
|
||||
|
||||
REQUIRE( Catch::isTrue( true ) );
|
||||
|
||||
SECTION( "Another section", "" )
|
||||
{
|
||||
REQUIRE( Catch::isTrue( true ) );
|
||||
}
|
||||
SECTION( "Another other section", "" )
|
||||
SECTION( "A section", "" )
|
||||
{
|
||||
REQUIRE( Catch::isTrue( true ) );
|
||||
|
||||
SECTION( "Another section", "" )
|
||||
{
|
||||
REQUIRE( Catch::isTrue( true ) );
|
||||
}
|
||||
SECTION( "Another other section", "" )
|
||||
{
|
||||
REQUIRE( Catch::isTrue( true ) );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct Awkward
|
||||
{
|
||||
operator int() const { return 7; }
|
||||
};
|
||||
|
||||
TEST_CASE( "non streamable - with conv. op", "[Tricky]" )
|
||||
{
|
||||
Awkward awkward;
|
||||
std::string s = Catch::toString( awkward );
|
||||
REQUIRE( s == "7" );
|
||||
}
|
||||
|
||||
inline void foo() {}
|
||||
|
||||
typedef void (*fooptr_t)();
|
||||
|
||||
TEST_CASE( "Comparing function pointers", "[Tricky][function pointer]" )
|
||||
{
|
||||
// This was giving a warning in VS2010
|
||||
// #179
|
||||
fooptr_t a = foo;
|
||||
|
||||
REQUIRE( a );
|
||||
REQUIRE( a == &foo );
|
||||
}
|
||||
|
||||
class ClassName {};
|
||||
|
||||
TEST_CASE( "pointer to class", "[Tricky]" )
|
||||
{
|
||||
ClassName *p = 0;
|
||||
REQUIRE( p == 0 );
|
||||
}
|
||||
|
||||
#ifdef CATCH_CONFIG_CPP11_NULLPTR
|
||||
|
||||
#include <memory>
|
||||
|
||||
TEST_CASE( "null_ptr", "[Tricky]" )
|
||||
{
|
||||
std::unique_ptr<int> ptr;
|
||||
REQUIRE(ptr.get() == nullptr);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
TEST_CASE( "X/level/0/a", "[Tricky]" ) { SUCCEED(""); }
|
||||
TEST_CASE( "X/level/0/b", "[Tricky][fizz]" ){ SUCCEED(""); }
|
||||
TEST_CASE( "X/level/1/a", "[Tricky]" ) { SUCCEED(""); }
|
||||
TEST_CASE( "X/level/1/b", "[Tricky]" ) { SUCCEED(""); }
|
||||
}
|
||||
|
||||
struct Awkward
|
||||
{
|
||||
operator int() const { return 7; }
|
||||
};
|
||||
|
||||
TEST_CASE( "non streamable - with conv. op", "[Tricky]" )
|
||||
{
|
||||
Awkward awkward;
|
||||
std::string s = Catch::toString( awkward );
|
||||
REQUIRE( s == "7" );
|
||||
}
|
||||
|
||||
inline void foo() {}
|
||||
|
||||
typedef void (*fooptr_t)();
|
||||
|
||||
TEST_CASE( "Comparing function pointers", "[Tricky][function pointer]" )
|
||||
{
|
||||
// This was giving a warning in VS2010
|
||||
// #179
|
||||
fooptr_t a = foo;
|
||||
|
||||
REQUIRE( a );
|
||||
REQUIRE( a == &foo );
|
||||
}
|
||||
|
||||
class ClassName {};
|
||||
|
||||
TEST_CASE( "pointer to class", "[Tricky]" )
|
||||
{
|
||||
ClassName *p = 0;
|
||||
REQUIRE( p == 0 );
|
||||
}
|
||||
|
||||
#ifdef CATCH_CONFIG_CPP11_NULLPTR
|
||||
|
||||
#include <memory>
|
||||
|
||||
TEST_CASE( "null_ptr", "[Tricky]" )
|
||||
{
|
||||
std::unique_ptr<int> ptr;
|
||||
REQUIRE(ptr.get() == nullptr);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
TEST_CASE( "X/level/0/a", "[Tricky]" ) { SUCCEED(""); }
|
||||
TEST_CASE( "X/level/0/b", "[Tricky][fizz]" ){ SUCCEED(""); }
|
||||
TEST_CASE( "X/level/1/a", "[Tricky]" ) { SUCCEED(""); }
|
||||
TEST_CASE( "X/level/1/b", "[Tricky]" ) { SUCCEED(""); }
|
||||
|
110
projects/SelfTest/VisualStudioTests.cpp
Normal file
110
projects/SelfTest/VisualStudioTests.cpp
Normal file
@ -0,0 +1,110 @@
|
||||
/*
|
||||
* Created by Phil on 22/10/2010.
|
||||
* Copyright 2010 Two Blue Cubes Ltd
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
* file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
|
||||
#include "catch.hpp"
|
||||
|
||||
#if defined(INTERNAL_CATCH_VS_MANAGED) || defined(INTERNAL_CATCH_VS_NATIVE)
|
||||
|
||||
namespace VisualStudioTests
|
||||
{
|
||||
class UniqueTestsFixture {
|
||||
private:
|
||||
static int uniqueID;
|
||||
public:
|
||||
UniqueTestsFixture() { }
|
||||
protected:
|
||||
int getID() {
|
||||
return ++uniqueID;
|
||||
}
|
||||
};
|
||||
|
||||
int UniqueTestsFixture::uniqueID = 0;
|
||||
TEST_CASE("M00", "[m_off]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(!show);
|
||||
}
|
||||
|
||||
CATCH_CONFIG_SHOW_SUCCESS(true)
|
||||
TEST_CASE("M01", "[m_on]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(show);
|
||||
}
|
||||
|
||||
TEST_CASE("M02", "[m_off]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(!show);
|
||||
}
|
||||
|
||||
TEST_CASE_METHOD(UniqueTestsFixture, "M10", "[m_off]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(!show);
|
||||
getID();
|
||||
}
|
||||
|
||||
CATCH_CONFIG_WARN_MISSING_ASSERTIONS(true)
|
||||
CATCH_CONFIG_SHOW_SUCCESS(true)
|
||||
TEST_CASE_METHOD(UniqueTestsFixture, "M11", "[m_on]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(show);
|
||||
getID();
|
||||
}
|
||||
|
||||
CATCH_CONFIG_WARN_MISSING_ASSERTIONS(true)
|
||||
CATCH_CONFIG_SHOW_SUCCESS(true)
|
||||
TEST_CASE_METHOD(UniqueTestsFixture, "M99", "[m_on]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(show);
|
||||
WARN("Warning message");
|
||||
getID();
|
||||
}
|
||||
|
||||
TEST_CASE_METHOD(UniqueTestsFixture, "M12", "[m_off]")
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(!show);
|
||||
getID();
|
||||
}
|
||||
|
||||
class ConfigTest
|
||||
{
|
||||
public:
|
||||
void run1()
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(!show);
|
||||
}
|
||||
void run2()
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(show);
|
||||
}
|
||||
void run3()
|
||||
{
|
||||
bool show = Catch::getCurrentContext().getConfig()->includeSuccessfulResults();
|
||||
REQUIRE(!show);
|
||||
}
|
||||
};
|
||||
METHOD_AS_TEST_CASE(ConfigTest::run1,"M20", "[m_off]");
|
||||
|
||||
CATCH_CONFIG_SHOW_SUCCESS(true)
|
||||
METHOD_AS_TEST_CASE(ConfigTest::run2,"M21", "[m_on]");
|
||||
|
||||
METHOD_AS_TEST_CASE(ConfigTest::run3,"M22", "[m_off]");
|
||||
|
||||
CATCH_MAP_CATEGORY_TO_TAG(vstestsCheckOutputOff, "[m_off]");
|
||||
CATCH_CONFIG_SHOW_SUCCESS(true)
|
||||
CATCH_MAP_CATEGORY_TO_TAG(vstestsCheckOutputOn, "[m_on]");
|
||||
CATCH_MAP_CATEGORY_TO_TAG(vstestsCheckOutputOff2, "[m_off]");
|
||||
}
|
||||
#endif
|
@ -4,8 +4,6 @@ SOURCES = ApproxTests.cpp \
|
||||
ExceptionTests.cpp \
|
||||
GeneratorTests.cpp \
|
||||
MessageTests.cpp \
|
||||
MessageInstantiationTests1.cpp \
|
||||
MessageInstantiationTests2.cpp \
|
||||
MiscTests.cpp \
|
||||
TestMain.cpp \
|
||||
TrickyTests.cpp \
|
||||
|
@ -16,13 +16,19 @@ Global
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Win32 = Debug|Win32
|
||||
DebugMbcs|Win32 = DebugMbcs|Win32
|
||||
Release|Win32 = Release|Win32
|
||||
ReleaseMbcs|Win32 = ReleaseMbcs|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.DebugMbcs|Win32.ActiveCfg = DebugMbcs|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.DebugMbcs|Win32.Build.0 = DebugMbcs|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.Release|Win32.Build.0 = Release|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.ReleaseMbcs|Win32.ActiveCfg = ReleaseMbcs|Win32
|
||||
{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}.ReleaseMbcs|Win32.Build.0 = ReleaseMbcs|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
@ -1,17 +1,25 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="DebugMbcs|Win32">
|
||||
<Configuration>DebugMbcs</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMbcs|Win32">
|
||||
<Configuration>ReleaseMbcs</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<TargetName>DefaultTest</TargetName>
|
||||
<TargetName>$(ProjectName)</TargetName>
|
||||
<ProjectTypes>{3AC096D0-A1C2-E12C-1390-A8335801FDAB};{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}</ProjectTypes>
|
||||
<ProjectGUID>{7CC06A6B-763E-42B3-AF6C-8F1E340372A1}</ProjectGUID>
|
||||
<Keyword>ManagedCProj</Keyword>
|
||||
@ -23,24 +31,42 @@
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CLRSupport>Safe</CLRSupport>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CLRSupport>Safe</CLRSupport>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\10.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup>
|
||||
<PostBuildEventCommand>if exist app.config copy app.config "$(OutDir)app.config"</PostBuildEventCommand>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">true</LinkIncremental>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
@ -58,6 +84,22 @@
|
||||
</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<AdditionalIncludeDirectories>..\..\..\include</AdditionalIncludeDirectories>
|
||||
<CompileAsManaged>true</CompileAsManaged>
|
||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AdditionalDependencies>
|
||||
</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
@ -72,6 +114,20 @@
|
||||
</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<CompileAsManaged>true</CompileAsManaged>
|
||||
<AdditionalIncludeDirectories>../../../include</AdditionalIncludeDirectories>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AdditionalDependencies>
|
||||
</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="Microsoft.VisualStudio.QualityTools.UnitTestFramework" />
|
||||
<Reference Include="System" />
|
||||
@ -90,13 +146,18 @@
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\MessageTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\MiscTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\RunAllTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\SectionTrackerTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\TestMain.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\TrickyTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\VariadicMacrosTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\VisualStudioTests.cpp" />
|
||||
<ClCompile Include="AssemblyInfo.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
@ -63,6 +63,15 @@
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\TestMain.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\RunAllTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\VisualStudioTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="stdafx.h">
|
||||
|
@ -6,13 +6,19 @@ EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Win32 = Debug|Win32
|
||||
DebugMbcs|Win32 = DebugMbcs|Win32
|
||||
Release|Win32 = Release|Win32
|
||||
ReleaseMbcs|Win32 = ReleaseMbcs|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.DebugMbcs|Win32.ActiveCfg = DebugMbcs|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.DebugMbcs|Win32.Build.0 = DebugMbcs|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.Release|Win32.Build.0 = Release|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.ReleaseMbcs|Win32.ActiveCfg = ReleaseMbcs|Win32
|
||||
{9757CB21-B840-49A6-B057-9F322E543DD6}.ReleaseMbcs|Win32.Build.0 = ReleaseMbcs|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
@ -1,17 +1,25 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="DebugMbcs|Win32">
|
||||
<Configuration>DebugMbcs</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMbcs|Win32">
|
||||
<Configuration>ReleaseMbcs</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<TargetName>DefaultTest</TargetName>
|
||||
<TargetName>$(ProjectName)</TargetName>
|
||||
<ProjectTypes>{3AC096D0-A1C2-E12C-1390-A8335801FDAB};{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}</ProjectTypes>
|
||||
<ProjectGUID>{9757CB21-B840-49A6-B057-9F322E543DD6}</ProjectGUID>
|
||||
<Keyword>ManagedCProj</Keyword>
|
||||
@ -24,30 +32,54 @@
|
||||
<CLRSupport>Safe</CLRSupport>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<PlatformToolset>v110</PlatformToolset>
|
||||
<CLRSupport>Safe</CLRSupport>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<PlatformToolset>v110</PlatformToolset>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<PlatformToolset>v110</PlatformToolset>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(LocalAppData)\Microsoft\VisualStudio\11.0\Microsoft.Cpp.$(Platform).user.props')" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup>
|
||||
<PostBuildEventCommand>if exist app.config copy app.config "$(OutDir)app.config"</PostBuildEventCommand>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
@ -66,6 +98,25 @@
|
||||
<Command>taskkill /F /IM vstest.executionengine.x86.exe /FI "MEMUSAGE gt 1"</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<AdditionalIncludeDirectories>../../../include</AdditionalIncludeDirectories>
|
||||
<CompileAsManaged>true</CompileAsManaged>
|
||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AdditionalDependencies>
|
||||
</AdditionalDependencies>
|
||||
</Link>
|
||||
<PreBuildEvent>
|
||||
<Command>taskkill /F /IM vstest.executionengine.x86.exe /FI "MEMUSAGE gt 1"</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
@ -79,6 +130,20 @@
|
||||
<AdditionalDependencies />
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<AdditionalIncludeDirectories>../../../include</AdditionalIncludeDirectories>
|
||||
<CompileAsManaged>true</CompileAsManaged>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AdditionalDependencies>
|
||||
</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="Microsoft.VisualStudio.QualityTools.UnitTestFramework">
|
||||
<HintPath>..\..\..\..\..\Program Files (x86)\Microsoft Visual Studio 11.0\Common7\IDE\PublicAssemblies\Microsoft.VisualStudio.QualityTools.UnitTestFramework.dll</HintPath>
|
||||
@ -100,13 +165,18 @@
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\MessageTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\MiscTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\RunAllTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\SectionTrackerTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\TestMain.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\TrickyTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\VariadicMacrosTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\VisualStudioTests.cpp" />
|
||||
<ClCompile Include="AssemblyInfo.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
@ -63,6 +63,15 @@
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\TestMain.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\RunAllTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\VisualStudioTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="stdafx.h">
|
||||
|
@ -6,13 +6,19 @@ EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Win32 = Debug|Win32
|
||||
DebugMbcs|Win32 = DebugMbcs|Win32
|
||||
Release|Win32 = Release|Win32
|
||||
ReleaseMbcs|Win32 = ReleaseMbcs|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.DebugMbcs|Win32.ActiveCfg = DebugMbcs|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.DebugMbcs|Win32.Build.0 = DebugMbcs|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.Release|Win32.Build.0 = Release|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.ReleaseMbcs|Win32.ActiveCfg = ReleaseMbcs|Win32
|
||||
{977CE524-3FC7-4281-9C1B-77C210F24A9B}.ReleaseMbcs|Win32.Build.0 = ReleaseMbcs|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
@ -1,10 +1,18 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="DebugMbcs|Win32">
|
||||
<Configuration>DebugMbcs</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMbcs|Win32">
|
||||
<Configuration>ReleaseMbcs</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
@ -23,6 +31,20 @@
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<UseOfMfc>false</UseOfMfc>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v110</PlatformToolset>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
<UseOfMfc>false</UseOfMfc>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v110</PlatformToolset>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
<UseOfMfc>false</UseOfMfc>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
@ -37,6 +59,12 @@
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
@ -44,6 +72,12 @@
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
@ -62,6 +96,36 @@
|
||||
<AdditionalLibraryDirectories>$(VCInstallDir)UnitTest\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<AdditionalIncludeDirectories>../../../include;$(VCInstallDir)UnitTest\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<UseFullPaths>true</UseFullPaths>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AdditionalLibraryDirectories>$(VCInstallDir)UnitTest\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<AdditionalIncludeDirectories>../../../include;$(VCInstallDir)UnitTest\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<UseFullPaths>true</UseFullPaths>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AdditionalLibraryDirectories>$(VCInstallDir)UnitTest\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
@ -97,11 +161,16 @@
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\MessageTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\MiscTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\RunAllTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\SectionTrackerTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\TestMain.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\TrickyTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\VariadicMacrosTests.cpp" />
|
||||
<ClCompile Include="..\..\SelfTest\VisualStudioTests.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='DebugMbcs|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='ReleaseMbcs|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
|
@ -50,12 +50,6 @@
|
||||
<ClCompile Include="..\..\SelfTest\GeneratorTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests1.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\MessageTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
@ -68,5 +62,20 @@
|
||||
<ClCompile Include="..\..\SelfTest\TrickyTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\RunAllTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\TestMain.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\VisualStudioTests.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests1.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\SelfTest\MessageInstantiationTests2.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
716
scripts/approvalVSTests.py
Normal file
716
scripts/approvalVSTests.py
Normal file
@ -0,0 +1,716 @@
|
||||
#!/c/Python27/python
|
||||
|
||||
import os
|
||||
import sys
|
||||
import subprocess
|
||||
import re
|
||||
|
||||
import xml.etree.cElementTree as etree
|
||||
|
||||
from scriptCommon import catchPath
|
||||
#from rawfile import writeRawFile
|
||||
#from rawfile import parseRawFileIntoTree
|
||||
from catch_test_run import TestRunApprovedHandler
|
||||
from catch_test_run import TestRunData
|
||||
from catch_test_run import TestRunResultHandler
|
||||
from catch_test_case import TestCaseResultParser
|
||||
from catch_test_case import TestCaseData
|
||||
|
||||
rootPath = os.path.join(os.path.join(os.path.join( catchPath, 'projects'), 'SelfTest'), 'Baselines' )
|
||||
|
||||
if len(sys.argv) == 2:
|
||||
cmdPath = sys.argv[1]
|
||||
else:
|
||||
if sys.platform == 'win32':
|
||||
cmdPath = os.path.join( catchPath, 'projects\\VS2010\\TestCatch\\Release\\TestCatch.exe' )
|
||||
dllPath = os.path.join( catchPath, 'projects\\VS2010\\ManagedTestCatch\\Release\\ManagedTestCatch.dll' )
|
||||
else:
|
||||
cmdPath = os.path.join( catchPath, 'projects/XCode4/CatchSelfTest/DerivedData/CatchSelfTest/Build/Products/Debug/CatchSelfTest' )
|
||||
|
||||
print cmdPath
|
||||
|
||||
overallResult = 0
|
||||
|
||||
def approve( baseName, args ):
|
||||
global overallResult
|
||||
args[0:0] = [cmdPath]
|
||||
baselinesPath = os.path.join( rootPath, '{0}.approved.txt'.format( baseName ) )
|
||||
baselinesSortedPath = os.path.join( rootPath, '{0}.sorted.approved.txt'.format( baseName ) )
|
||||
rawResultsPath = os.path.join( rootPath, '_{0}.tmp'.format( baseName ) )
|
||||
if os.path.exists( baselinesPath ):
|
||||
approvedFileHandler = TestRunApprovedHandler(baselinesPath)
|
||||
baselinesPathNew = os.path.join( rootPath, '{0}.approved.new.txt'.format( baseName ) )
|
||||
approvedFileHandler.writeRawFile(baselinesPathNew)
|
||||
approvedFileHandler.writeSortedRawFile(baselinesSortedPath)
|
||||
else:
|
||||
raise Exception("Base file does not exist: '" + baselinesPath + "'")
|
||||
|
||||
if not(os.path.exists( args[0] )):
|
||||
raise Exception("Executable does not exist: '" + args[0] + "'")
|
||||
|
||||
f = open( rawResultsPath, 'w' )
|
||||
subprocess.call( args, stdout=f, stderr=f )
|
||||
f.close()
|
||||
|
||||
if os.path.exists( rawResultsPath ):
|
||||
resultFileHandler = TestRunResultHandler(rawResultsPath)
|
||||
rawPathNew = os.path.join( rootPath, '{0}.rewrite.txt'.format( baseName ) )
|
||||
#print "F:",rawPathNew,",",approvedFileHandler.current.outputLine
|
||||
resultFileHandler.writeRawFile(rawPathNew)
|
||||
rawPathNewSorted = os.path.join( rootPath, '{0}.sorted.unapproved.txt'.format( baseName ) )
|
||||
resultFileHandler.writeSortedUnapprovedFile(rawPathNewSorted, approvedFileHandler.current.outputLine)
|
||||
else:
|
||||
raise Exception("Results file does not exist: '" + rawResultsPath + "'")
|
||||
|
||||
#os.remove( rawResultsPath )
|
||||
print
|
||||
print baseName + ":"
|
||||
if os.path.exists( baselinesSortedPath ) and os.path.exists( rawPathNewSorted ):
|
||||
diffResult = subprocess.call([ "diff", "--ignore-all-space", baselinesSortedPath, rawPathNewSorted ] )
|
||||
if diffResult == 0:
|
||||
#os.remove( filteredResultsPath )
|
||||
if not(sys.platform == 'win32'):
|
||||
print " \033[92mResults matched"
|
||||
else:
|
||||
print " Results matched"
|
||||
else:
|
||||
if not(sys.platform == 'win32'):
|
||||
print " \n****************************\n \033[91mResults differed"
|
||||
else:
|
||||
print " \n****************************\n Results differed"
|
||||
if diffResult > overallResult:
|
||||
overallResult = diffResult
|
||||
if not(sys.platform == 'win32'):
|
||||
print "\033[0m"
|
||||
|
||||
def approveJunit( baseName, args ):
|
||||
global overallResult
|
||||
args[0:0] = [cmdPath]
|
||||
baselinesPath = os.path.join( rootPath, '{0}.approved.txt'.format( baseName ) )
|
||||
baselinesSortedPath = os.path.join( rootPath, '{0}.sorted.approved.txt'.format( baseName ) )
|
||||
#baselinesFixedPath = os.path.join( rootPath, '{0}.rewrite.approved.txt'.format( baseName ) )
|
||||
rawResultsPath = os.path.join( rootPath, '_{0}.tmp'.format( baseName ) )
|
||||
if os.path.exists( baselinesPath ):
|
||||
xml = ""
|
||||
f = open( baselinesPath, 'r' )
|
||||
for line in f:
|
||||
xml += line
|
||||
xml = xml.replace("<line number>", "<line number>")
|
||||
xml = xml.replace("<hex digits>", "<hex digits>")
|
||||
#f2 = open( baselinesFixedPath, 'wb' )
|
||||
#f2.write(xml)
|
||||
#f2.close()
|
||||
|
||||
# ClassTests.cpp:<line number>
|
||||
otherApprovedTestParser = re.compile( r'(.*\..pp).*:<(.*).*>' )
|
||||
testRun = TestRunData()
|
||||
testcase = None
|
||||
root = etree.fromstring(xml)
|
||||
for testsuites in root:
|
||||
if testsuites.tag == "testsuite":
|
||||
testRun = TestRunData()
|
||||
testRun.appname = testsuites.get("name")
|
||||
testRun.errors = testsuites.get("errors")
|
||||
testRun.failures = testsuites.get("failures")
|
||||
testRun.tests = testsuites.get("tests")
|
||||
for tc in testsuites:
|
||||
if tc.tag == "testcase":
|
||||
cls = tc.get("classname")
|
||||
#print "C:",cls,tc
|
||||
if len(cls):
|
||||
testcase = testRun.addClassTestCase(cls, tc.get("name"))
|
||||
else:
|
||||
testcase = testRun.addTestCase(tc.get("name"))
|
||||
for prop in tc:
|
||||
if prop.tag == "failure":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
filename = ""
|
||||
lineNumber = ""
|
||||
output = []
|
||||
for l in lines:
|
||||
m = otherApprovedTestParser.match(l)
|
||||
if m:
|
||||
filename = m.group(1)
|
||||
lineNumber = m.group(2)
|
||||
else:
|
||||
output.append(l)
|
||||
testcase.addFailure(filename, lineNumber, output, prop.get("message"), prop.get("type"))
|
||||
elif prop.tag == "error":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
filename = ""
|
||||
lineNumber = ""
|
||||
output = []
|
||||
for l in lines:
|
||||
m = otherApprovedTestParser.match(l)
|
||||
if m:
|
||||
filename = m.group(1)
|
||||
lineNumber = m.group(2)
|
||||
else:
|
||||
output.append(l)
|
||||
testcase.addError(filename, lineNumber, output, prop.get("message"), prop.get("type"))
|
||||
elif prop.tag == "system-out":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
testcase.addSysout(lines)
|
||||
elif prop.tag == "system-err":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
testcase.addSyserr(lines)
|
||||
elif tc.tag == "system-out":
|
||||
text = tc.text.strip()
|
||||
lines = text.splitlines()
|
||||
testRun.addSysout(lines)
|
||||
elif tc.tag == "system-err":
|
||||
text = tc.text.strip()
|
||||
lines = text.splitlines()
|
||||
testRun.addSyserr(lines)
|
||||
else:
|
||||
print tc.tag
|
||||
|
||||
lines = testRun.generateSortedUnapprovedJunit()
|
||||
|
||||
rawWriteFile = open( baselinesSortedPath, 'wb' )
|
||||
for line in lines:
|
||||
#print "L:",line
|
||||
rawWriteFile.write(line + "\n")
|
||||
rawWriteFile.close()
|
||||
|
||||
if not(os.path.exists( args[0] )):
|
||||
raise Exception("Executable does not exist: '" + args[0] + "'")
|
||||
|
||||
f = open( rawResultsPath, 'w' )
|
||||
subprocess.call( args, stdout=f, stderr=f )
|
||||
f.close()
|
||||
|
||||
rawSortedPath = os.path.join( rootPath, '{0}.sorted.unapproved.txt'.format( baseName ) )
|
||||
if os.path.exists( rawResultsPath ):
|
||||
xml = ""
|
||||
f = open( rawResultsPath, 'r' )
|
||||
for line in f:
|
||||
xml += line
|
||||
#xml = xml.replace("<line number>", "<line number>")
|
||||
#xml = xml.replace("<hex digits>", "<hex digits>")
|
||||
|
||||
# ClassTests.cpp:<line number>
|
||||
otherResultsTestParser = re.compile( r'(.*\\)(.*\..pp).*\((.*).*\)' )
|
||||
testRun = TestRunData()
|
||||
testcase = None
|
||||
root = etree.fromstring(xml)
|
||||
for testsuites in root:
|
||||
if testsuites.tag == "testsuite":
|
||||
testRun = TestRunData()
|
||||
testRun.appname = testsuites.get("name")
|
||||
testRun.errors = testsuites.get("errors")
|
||||
testRun.failures = testsuites.get("failures")
|
||||
testRun.tests = testsuites.get("tests")
|
||||
for tc in testsuites:
|
||||
if tc.tag == "testcase":
|
||||
cls = tc.get("classname")
|
||||
#print "C:",cls,tc
|
||||
if len(cls):
|
||||
if cls.startswith("::"):
|
||||
cls = cls[2:]
|
||||
testcase = testRun.addClassTestCase(cls, tc.get("name"))
|
||||
else:
|
||||
testcase = testRun.addTestCase(tc.get("name"))
|
||||
for prop in tc:
|
||||
if prop.tag == "failure":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
filename = ""
|
||||
lineNumber = ""
|
||||
output = []
|
||||
for l in lines:
|
||||
m = otherResultsTestParser.match(l)
|
||||
if m:
|
||||
filename = m.group(2)
|
||||
lineNumber = "line number"
|
||||
else:
|
||||
output.append(l)
|
||||
testcase.addFailure(filename, lineNumber, output, prop.get("message"), prop.get("type"))
|
||||
elif prop.tag == "error":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
filename = ""
|
||||
lineNumber = ""
|
||||
output = []
|
||||
for l in lines:
|
||||
m = otherResultsTestParser.match(l)
|
||||
if m:
|
||||
filename = m.group(2)
|
||||
lineNumber = "line number"
|
||||
else:
|
||||
output.append(l)
|
||||
testcase.addError(filename, lineNumber, output, prop.get("message"), prop.get("type"))
|
||||
elif prop.tag == "system-out":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
testcase.addSysout(lines)
|
||||
elif prop.tag == "system-err":
|
||||
text = prop.text.strip()
|
||||
lines = text.splitlines()
|
||||
testcase.addSyserr(lines)
|
||||
elif tc.tag == "system-out":
|
||||
text = tc.text.strip()
|
||||
lines = text.splitlines()
|
||||
testRun.addSysout(lines)
|
||||
elif tc.tag == "system-err":
|
||||
text = tc.text.strip()
|
||||
lines = text.splitlines()
|
||||
testRun.addSyserr(lines)
|
||||
else:
|
||||
print tc.tag
|
||||
|
||||
lines = testRun.generateSortedUnapprovedJunit()
|
||||
|
||||
rawWriteFile = open( rawSortedPath, 'wb' )
|
||||
for line in lines:
|
||||
#print "L:",line
|
||||
rawWriteFile.write(line + "\n")
|
||||
rawWriteFile.close()
|
||||
|
||||
def addSubSection(testcase, section, exp):
|
||||
r = exp.find("OverallResults")
|
||||
if r != None:
|
||||
ores = []
|
||||
ores.append(r.get("successes"))
|
||||
ores.append(r.get("failures"))
|
||||
if section == None:
|
||||
section = testcase.addSection(exp.get("name"), exp.get("description"), ores)
|
||||
else:
|
||||
section = testcase.addSubSection(section, exp.get("name"), exp.get("description"), ores)
|
||||
e1 = False
|
||||
for tmp in exp:
|
||||
if tmp.tag == "OverallResults":
|
||||
pass
|
||||
elif tmp.tag == "Exception":
|
||||
filename = tmp.get("filename")
|
||||
text = tmp.text
|
||||
ls = text.splitlines()
|
||||
testcase.addSubException(section, filename, ls)
|
||||
elif tmp.tag == "Section":
|
||||
addSubSection(testcase, section, tmp)
|
||||
elif tmp.tag == "Failure":
|
||||
text = tmp.text
|
||||
ls = text.splitlines()
|
||||
testcase.addSubFailure(section, ls)
|
||||
elif tmp.tag == "Expression":
|
||||
#print "Exp:",tmp
|
||||
e1 = True
|
||||
result = tmp.get("success")
|
||||
filename = tmp.get("filename")
|
||||
subSection = testcase.addSubExpression(section,result,filename)
|
||||
subExp = []
|
||||
for cond in tmp:
|
||||
if cond.tag == "Original":
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Expanded" and len(subExp) == 1:
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Exception" and len(subExp) == 2:
|
||||
subExp.append(cond.get("filename"))
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
else:
|
||||
print "SX:",cond.tag
|
||||
if len(subExp) >= 2:
|
||||
testcase.addExpressionDetails(subSection, subExp)
|
||||
else:
|
||||
print "Z:",tmp.tag
|
||||
#if e1:
|
||||
# print "Section:",section
|
||||
|
||||
def addResultsSubSection(otherResultsTestParser, testcase, section, exp):
|
||||
r = exp.find("OverallResults")
|
||||
if r != None:
|
||||
ores = []
|
||||
ores.append(r.get("successes"))
|
||||
ores.append(r.get("failures"))
|
||||
if section == None:
|
||||
section = testcase.addSection(exp.get("name"), exp.get("description"), ores)
|
||||
else:
|
||||
section = testcase.addSubSection(section, exp.get("name"), exp.get("description"), ores)
|
||||
e1 = False
|
||||
for tmp in exp:
|
||||
if tmp.tag == "OverallResults":
|
||||
pass
|
||||
elif tmp.tag == "Exception":
|
||||
filename = tmp.get("filename")
|
||||
m = otherResultsTestParser.match(filename)
|
||||
if m:
|
||||
filename = "/Users/philnash/Dev/OSS/Catch/projects/SelfTest/" + m.group(2)
|
||||
text = tmp.text
|
||||
ls = text.splitlines()
|
||||
testcase.addSubException(section, filename, ls)
|
||||
elif tmp.tag == "Section":
|
||||
addResultsSubSection(otherResultsTestParser, testcase, section, tmp)
|
||||
elif tmp.tag == "Failure":
|
||||
text = tmp.text
|
||||
ls = text.splitlines()
|
||||
testcase.addSubFailure(section, ls)
|
||||
elif tmp.tag == "Expression":
|
||||
#print "Exp:",tmp
|
||||
e1 = True
|
||||
result = tmp.get("success")
|
||||
filename = tmp.get("filename")
|
||||
m = otherResultsTestParser.match(filename)
|
||||
if m:
|
||||
filename = "/Users/philnash/Dev/OSS/Catch/projects/SelfTest/" + m.group(2)
|
||||
subSection = testcase.addSubExpression(section,result,filename)
|
||||
subExp = []
|
||||
for cond in tmp:
|
||||
if cond.tag == "Original":
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Expanded" and len(subExp) == 1:
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Exception" and len(subExp) == 2:
|
||||
filename = cond.get("filename")
|
||||
m = otherResultsTestParser.match(filename)
|
||||
if m:
|
||||
filename = "/Users/philnash/Dev/OSS/Catch/projects/SelfTest/" + m.group(2)
|
||||
subExp.append(filename)
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
else:
|
||||
print "SX:",cond.tag
|
||||
if len(subExp) >= 2:
|
||||
testcase.addExpressionDetails(subSection, subExp)
|
||||
else:
|
||||
print "Z:",tmp.tag
|
||||
#if e1:
|
||||
# print "Section:",section
|
||||
|
||||
def approveXml( baseName, args ):
|
||||
global overallResult
|
||||
args[0:0] = [cmdPath]
|
||||
baselinesPath = os.path.join( rootPath, '{0}.approved.txt'.format( baseName ) )
|
||||
baselinesSortedPath = os.path.join( rootPath, '{0}.sorted.approved.txt'.format( baseName ) )
|
||||
#baselinesFixedPath = os.path.join( rootPath, '{0}.rewrite.approved.txt'.format( baseName ) )
|
||||
rawResultsPath = os.path.join( rootPath, '_{0}.tmp'.format( baseName ) )
|
||||
if os.path.exists( baselinesPath ):
|
||||
xml = ""
|
||||
f = open( baselinesPath, 'r' )
|
||||
for line in f:
|
||||
xml += line
|
||||
xml = xml.replace("<hex digits>", "<hex digits>")
|
||||
|
||||
#otherApprovedTestParser = re.compile( r'(.*\..pp).*:<(.*).*>' )
|
||||
testRun = TestRunData()
|
||||
testcase = None
|
||||
root = etree.fromstring(xml)
|
||||
testRun.appname = root.get("name")
|
||||
for ts in root:
|
||||
#print ts.tag
|
||||
for tc in ts:
|
||||
if tc.tag == "TestCase":
|
||||
testcase = testRun.addTestCase(tc.get("name"))
|
||||
for exp in tc:
|
||||
if exp.tag == "Expression":
|
||||
result = exp.get("success")
|
||||
filename = exp.get("filename")
|
||||
section = testcase.addExpression(result,filename)
|
||||
subExp = []
|
||||
for cond in exp:
|
||||
if cond.tag == "Original":
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Expanded" and len(subExp) == 1:
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Exception" and len(subExp) == 2:
|
||||
subExp.append(cond.get("filename"))
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
else:
|
||||
print "X:",cond.tag
|
||||
if len(subExp) >= 2:
|
||||
testcase.addExpressionDetails(section, subExp)
|
||||
elif exp.tag == "Exception":
|
||||
filename = exp.get("filename")
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addException(filename,ls)
|
||||
elif exp.tag == "Section":
|
||||
addSubSection(testcase, None, exp)
|
||||
elif exp.tag == "Info":
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addInfo(ls)
|
||||
elif exp.tag == "Warning":
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addWarning(ls)
|
||||
elif exp.tag == "Failure":
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addSimpleFailure(ls)
|
||||
elif exp.tag == "OverallResult":
|
||||
testcase.addOverallResult(exp.get("success"))
|
||||
else:
|
||||
print "E:",exp.tag
|
||||
elif tc.tag == "OverallResults":
|
||||
testRun.tests = tc.get("successes")
|
||||
testRun.failures = tc.get("failures")
|
||||
else:
|
||||
print "U:",tc.tag
|
||||
|
||||
lines = testRun.generateSortedUnapprovedXml()
|
||||
|
||||
rawWriteFile = open( baselinesSortedPath, 'wb' )
|
||||
for line in lines:
|
||||
#print "L:",line
|
||||
rawWriteFile.write(line + "\n")
|
||||
rawWriteFile.close()
|
||||
|
||||
if not(os.path.exists( args[0] )):
|
||||
raise Exception("Executable does not exist: '" + args[0] + "'")
|
||||
|
||||
f = open( rawResultsPath, 'w' )
|
||||
subprocess.call( args, stdout=f, stderr=f )
|
||||
f.close()
|
||||
|
||||
rawSortedPath = os.path.join( rootPath, '{0}.sorted.unapproved.txt'.format( baseName ) )
|
||||
if os.path.exists( rawResultsPath ):
|
||||
xml = ""
|
||||
f = open( rawResultsPath, 'r' )
|
||||
for line in f:
|
||||
xml += line
|
||||
#xml = xml.replace("<hex digits>", "<hex digits>")
|
||||
|
||||
otherResultsTestParser = re.compile( r'(.*\\)(.*\..pp)' )
|
||||
hexParser = re.compile( r'(.*)\b(0[xX][0-9a-fA-F]+)\b(.*)' )
|
||||
testRun = TestRunData()
|
||||
testcase = None
|
||||
root = etree.fromstring(xml)
|
||||
testRun.appname = root.get("name")
|
||||
if testRun.appname == "TestCatch.exe":
|
||||
testRun.appname = "CatchSelfTest"
|
||||
for ts in root:
|
||||
#print ts.tag
|
||||
for tc in ts:
|
||||
if tc.tag == "TestCase":
|
||||
testcase = testRun.addTestCase(tc.get("name"))
|
||||
for exp in tc:
|
||||
if exp.tag == "Expression":
|
||||
result = exp.get("success")
|
||||
filename = exp.get("filename")
|
||||
m = otherResultsTestParser.match(filename)
|
||||
if m:
|
||||
filename = "/Users/philnash/Dev/OSS/Catch/projects/SelfTest/" + m.group(2)
|
||||
section = testcase.addExpression(result,filename)
|
||||
subExp = []
|
||||
for cond in exp:
|
||||
if cond.tag == "Original":
|
||||
text = cond.text
|
||||
tmp = text.splitlines()
|
||||
ls = []
|
||||
for li in tmp:
|
||||
m = hexParser.match(li)
|
||||
if m:
|
||||
while m:
|
||||
#print li, m.group(1), m.group(3)
|
||||
li = m.group(1) + "0x<hex digits>" + m.group(3)
|
||||
m = hexParser.match(li)
|
||||
ls.append(li)
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Expanded" and len(subExp) == 1:
|
||||
text = cond.text
|
||||
tmp = text.splitlines()
|
||||
ls = []
|
||||
for li in tmp:
|
||||
m = hexParser.match(li)
|
||||
if m:
|
||||
while m:
|
||||
#print li, m.group(1), m.group(3)
|
||||
li = m.group(1) + "0x<hex digits>" + m.group(3)
|
||||
m = hexParser.match(li)
|
||||
ls.append(li)
|
||||
subExp.append(ls)
|
||||
elif cond.tag == "Exception" and len(subExp) == 2:
|
||||
filename = cond.get("filename")
|
||||
m = otherResultsTestParser.match(filename)
|
||||
if m:
|
||||
filename = "/Users/philnash/Dev/OSS/Catch/projects/SelfTest/" + m.group(2)
|
||||
subExp.append(filename)
|
||||
text = cond.text
|
||||
ls = text.splitlines()
|
||||
subExp.append(ls)
|
||||
else:
|
||||
print "X:",cond.tag
|
||||
if len(subExp) >= 2:
|
||||
testcase.addExpressionDetails(section, subExp)
|
||||
elif exp.tag == "Exception":
|
||||
filename = exp.get("filename")
|
||||
m = otherResultsTestParser.match(filename)
|
||||
if m:
|
||||
filename = "/Users/philnash/Dev/OSS/Catch/projects/SelfTest/" + m.group(2)
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addException(filename,ls)
|
||||
elif exp.tag == "Section":
|
||||
addResultsSubSection(otherResultsTestParser, testcase, None, exp)
|
||||
elif exp.tag == "Info":
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addInfo(ls)
|
||||
elif exp.tag == "Warning":
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addWarning(ls)
|
||||
elif exp.tag == "Failure":
|
||||
text = exp.text
|
||||
ls = text.splitlines()
|
||||
section = testcase.addSimpleFailure(ls)
|
||||
elif exp.tag == "OverallResult":
|
||||
testcase.addOverallResult(exp.get("success"))
|
||||
else:
|
||||
print "E:",exp.tag
|
||||
elif tc.tag == "OverallResults":
|
||||
testRun.tests = tc.get("successes")
|
||||
testRun.failures = tc.get("failures")
|
||||
else:
|
||||
print "U:",tc.tag
|
||||
|
||||
lines = testRun.generateSortedUnapprovedXml()
|
||||
|
||||
rawWriteFile = open( rawSortedPath, 'wb' )
|
||||
for line in lines:
|
||||
#print "L:",line
|
||||
rawWriteFile.write(line + "\n")
|
||||
rawWriteFile.close()
|
||||
|
||||
def parseTrxFile(trxFile):
|
||||
print "TRX file:" ,trxFile
|
||||
if os.path.exists( trxFile ):
|
||||
xml = ""
|
||||
f = open( trxFile, 'r' )
|
||||
for line in f:
|
||||
xml += line
|
||||
|
||||
#otherResultsTestParser = re.compile( r'(.*\\)(.*\..pp)' )
|
||||
#hexParser = re.compile( r'(.*)\b(0[xX][0-9a-fA-F]+)\b(.*)' )
|
||||
testRun = TestRunData()
|
||||
testRun.appname = "CatchSelfTest"
|
||||
root = etree.fromstring(xml)
|
||||
if testRun.appname == "TestCatch.exe":
|
||||
testRun.appname = "CatchSelfTest"
|
||||
qname=re.compile("{(?P<ns>.*)}(?P<element>.*)")
|
||||
ids = []
|
||||
for ts in root:
|
||||
m = qname.match(ts.tag)
|
||||
if m:
|
||||
tag = m.group(2)
|
||||
print tag
|
||||
if tag != None:
|
||||
if tag == "TestDefinitions":
|
||||
for tc in ts:
|
||||
m = qname.match(tc.tag)
|
||||
if m:
|
||||
tag = m.group(2)
|
||||
if tag != None and tag == "UnitTest":
|
||||
name = tc.get("name")
|
||||
id = tc.get("id")
|
||||
for item in tc:
|
||||
m = qname.match(item.tag)
|
||||
if m:
|
||||
tag = m.group(2)
|
||||
if tag != None and tag == "Description":
|
||||
desc = item.text
|
||||
#print desc, id
|
||||
ids.append([id,desc])
|
||||
elif tag == "Results":
|
||||
#print ids
|
||||
ids = dict(ids)
|
||||
#print ids["87ec526a-e414-1a3f-ba0f-e210b204bb42"]
|
||||
resultParser = TestCaseResultParser()
|
||||
for tc in ts:
|
||||
m = qname.match(tc.tag)
|
||||
if m:
|
||||
tag = m.group(2)
|
||||
if tag != None and tag == "UnitTestResult":
|
||||
outcome = tc.get("outcome")
|
||||
id = tc.get("testId")
|
||||
if len(id) > 0:
|
||||
for item in tc:
|
||||
m = qname.match(item.tag)
|
||||
if m:
|
||||
tag = m.group(2)
|
||||
if tag != None and tag == "Output":
|
||||
for sub in item:
|
||||
m = qname.match(sub.tag)
|
||||
if m:
|
||||
tag = m.group(2)
|
||||
if tag != None and tag == "StdOut":
|
||||
desc = sub.text
|
||||
lines = desc.splitlines()
|
||||
if (len(lines) > 2 and
|
||||
lines[0].startswith("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~") and
|
||||
lines[1].startswith("Using Catch v") ):
|
||||
lines = lines[2:-1]
|
||||
#print "*******",desc
|
||||
#print lines
|
||||
for line in lines:
|
||||
testcase = resultParser.parseResultLine(line)
|
||||
if isinstance(testcase, TestCaseData):
|
||||
testRun.testcases.append(testcase)
|
||||
lines = testRun.generateSortedUnapprovedLines(0)
|
||||
|
||||
rawSortedPath = os.path.join( rootPath, 'mstest.trx.sorted.unapproved.txt' )
|
||||
rawWriteFile = open( rawSortedPath, 'wb' )
|
||||
for line in lines:
|
||||
#print "L:",line
|
||||
rawWriteFile.write(line + "\n")
|
||||
rawWriteFile.close()
|
||||
|
||||
|
||||
def approveMsTest( baseName ):
|
||||
rawResultsPath = os.path.join( rootPath, '_{0}.tmp'.format( baseName ) )
|
||||
if not(os.path.exists( dllPath )):
|
||||
raise Exception("Managed DLL does not exist: '" + dllPath + "'")
|
||||
|
||||
args = []
|
||||
args.append("MSTest.exe")
|
||||
args.append("/testcontainer:" + dllPath)
|
||||
#f = open( rawResultsPath, 'w' )
|
||||
#subprocess.call( args, stdout=f, stderr=f )
|
||||
#f.close()
|
||||
|
||||
#if os.path.exists( rawResultsPath ):
|
||||
# f = open( rawResultsPath, 'r' )
|
||||
# for line in f:
|
||||
line = "Results file: c:\Projects\Catch\TestResults\NoyesMa_SACHDEW7 2013-12-09 11_43_57.trx"
|
||||
|
||||
if line.startswith("Results file:"):
|
||||
trxFile = line[13:].strip()
|
||||
parseTrxFile(trxFile)
|
||||
|
||||
# Standard console reporter
|
||||
#approve( "console.std", ["~_"] )
|
||||
# console reporter, include passes, warn about No Assertions
|
||||
#approve( "console.sw", ["~_", "-s", "-w", "NoAssertions"] )
|
||||
# console reporter, include passes, warn about No Assertions, limit failures to first 4
|
||||
#approve( "console.swa4", ["~_", "-s", "-w", "NoAssertions", "-x", "4"] )
|
||||
# junit reporter, include passes, warn about No Assertions
|
||||
#approveJunit( "junit.sw", ["~_", "-s", "-w", "NoAssertions", "-r", "junit"] )
|
||||
# xml reporter, include passes, warn about No Assertions
|
||||
#approveXml( "xml.sw", ["~_", "-s", "-w", "NoAssertions", "-r", "xml"] )
|
||||
#mstest runner, xml output
|
||||
approveMsTest( "mstest.sw")
|
||||
|
||||
if overallResult <> 0:
|
||||
print "run approve.py to approve new baselines"
|
||||
exit( overallResult)
|
398
scripts/catch_conditions.py
Normal file
398
scripts/catch_conditions.py
Normal file
@ -0,0 +1,398 @@
|
||||
import re
|
||||
|
||||
class RandomOutput:
|
||||
|
||||
def __init__(self):
|
||||
output = []
|
||||
|
||||
class TestConditionData:
|
||||
NONE = 0
|
||||
CONDITION = 1
|
||||
EXPANSION = 2
|
||||
MESSAGES = 3
|
||||
|
||||
hexParser = re.compile( r'(.*)\b(0[xX][0-9a-fA-F]+)\b(.*)' )
|
||||
|
||||
def __init__(self):
|
||||
self.state = self.NONE
|
||||
self.filenamePrefix = ""
|
||||
self.filename = ""
|
||||
self.lineNumber = ""
|
||||
self.reason = ""
|
||||
self.condition = ""
|
||||
self.expansionPrefix = ""
|
||||
self.expansion = []
|
||||
self.messagePrefix = ""
|
||||
self.messages = []
|
||||
self.output = []
|
||||
self.noAssertions = ""
|
||||
|
||||
def __eq__(self, other):
|
||||
return (self.filenamePrefix == other.filenamePrefix and
|
||||
self.filename == other.filename and self.lineNumber == other.lineNumber and
|
||||
self.reason == other.reason and self.condition == other.condition and
|
||||
self.expansion == other.expansion and self.messagePrefix == other.messagePrefix and
|
||||
self.output == other.output and self.noAssertions == other.noAssertions)
|
||||
|
||||
|
||||
def empty(self):
|
||||
if self.state == self.NONE:
|
||||
return True
|
||||
return False
|
||||
|
||||
def __repr__(self):
|
||||
result = ("[" + self.reason + ", " + self.filename + ", " + self.lineNumber + ", " + self.condition +
|
||||
", " + self.expansionPrefix + ", [ ")
|
||||
suffix = ""
|
||||
for msg in self.expansion:
|
||||
result += suffix
|
||||
result += repr(msg)
|
||||
suffix = ", "
|
||||
result += "], " + self.messagePrefix + ", [ "
|
||||
suffix = ""
|
||||
for msg in self.messages:
|
||||
result += suffix
|
||||
result += repr(msg)
|
||||
suffix = ", "
|
||||
result += " ], [ "
|
||||
suffix = ""
|
||||
for msg in self.output:
|
||||
result += suffix
|
||||
result += repr(msg)
|
||||
suffix = ", "
|
||||
result += " ] ]"
|
||||
return result
|
||||
|
||||
def parseCondition(self,line):
|
||||
if len(line):
|
||||
if self.state == self.CONDITION and line.startswith(" "):
|
||||
self.condition = line.strip()
|
||||
elif self.state == self.CONDITION:
|
||||
if len(self.reason) == 0 and line.startswith("PASSED:"):
|
||||
self.reason = line.strip()
|
||||
elif line.startswith("warning:") or line.startswith("with message"):
|
||||
self.messagePrefix = line.strip()
|
||||
self.state = self.MESSAGES
|
||||
elif not(line.startswith(" ")):
|
||||
self.expansionPrefix = line.strip()
|
||||
self.state = self.EXPANSION
|
||||
else:
|
||||
raise Exception("Unknown condition parse line: '" + line + "'")
|
||||
elif self.state == self.EXPANSION:
|
||||
if line.startswith("with message"):
|
||||
self.messagePrefix = line.strip()
|
||||
self.state = self.MESSAGES
|
||||
elif line.startswith(" "):
|
||||
#print "***LINE: ", line
|
||||
self.expansion.append(line[2:].rstrip())
|
||||
elif line.startswith("... message truncated due"):
|
||||
#print "***MSG: ", line
|
||||
self.messagePrefix = line.strip()
|
||||
else:
|
||||
#print "***OUTPUT: ", line
|
||||
self.output.append(line.strip())
|
||||
elif self.state == self.MESSAGES:
|
||||
if line.startswith(" "):
|
||||
#print "***MESSAGE: ", line
|
||||
self.messages.append(line.strip())
|
||||
else:
|
||||
#print "***OUTPUT: ", line
|
||||
self.output.append(line.strip())
|
||||
else:
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
|
||||
if len(self.output) == 10:
|
||||
if (self.output[0] == "Message from section one" and self.output[1] == "Message from section two" and
|
||||
self.output[2] == "Some information" and self.output[3] == "An error" and
|
||||
self.output[4] == "Message from section one" and self.output[5] == "Message from section two" and
|
||||
self.output[6] == "Some information" and self.output[7] == "An error" and
|
||||
self.output[8] == "hello" and self.output[9] == "hello" ):
|
||||
obj = RandomOutput()
|
||||
obj.output = self.output
|
||||
self.output = []
|
||||
raise obj
|
||||
|
||||
elif len(self.output) == 2:
|
||||
if (self.output[0] == "hello" and self.output[1] == "hello" ):
|
||||
obj = RandomOutput()
|
||||
obj.output = self.output
|
||||
self.output = []
|
||||
raise obj
|
||||
|
||||
def generateApprovedLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty condition..." + repr(self))
|
||||
lines = []
|
||||
extraLine = False
|
||||
if len(self.filename):
|
||||
line = self.filename + ":<" + self.lineNumber + ">:"
|
||||
reasonOnSameLine = False
|
||||
if self.reason == "FAILED":
|
||||
line += " " + "FAILED:"
|
||||
reasonOnSameLine = True
|
||||
lines.append(line)
|
||||
if not(reasonOnSameLine) and len(self.reason):
|
||||
lines.append(self.reason)
|
||||
if len(self.condition):
|
||||
lines.append(" " + self.condition)
|
||||
if len(self.expansionPrefix):
|
||||
lines.append(self.expansionPrefix)
|
||||
extraLine = True
|
||||
if len(self.expansion):
|
||||
for line in self.expansion:
|
||||
m = self.hexParser.match(line)
|
||||
if m:
|
||||
while m:
|
||||
line = m.group(1) + "0x<hex digits>" + m.group(3)
|
||||
m = self.hexParser.match(line)
|
||||
lines.append(" " + line)
|
||||
if len(self.messagePrefix):
|
||||
lines.append(self.messagePrefix)
|
||||
extraLine = True
|
||||
if len(self.messages):
|
||||
for msg in self.messages:
|
||||
lines.append(" " + msg)
|
||||
lines.append("")
|
||||
if len(self.noAssertions) > 0:
|
||||
if extraLine:
|
||||
lines.append("")
|
||||
lines.append(self.noAssertions)
|
||||
lines.append("")
|
||||
if len(self.output):
|
||||
for msg in self.output:
|
||||
lines.append(msg)
|
||||
return lines
|
||||
|
||||
def generateResultLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty condition..." + repr(self))
|
||||
lines = []
|
||||
extraLine = False
|
||||
if len(self.filename):
|
||||
if len(self.filenamePrefix):
|
||||
line = self.filenamePrefix + self.filename + "(" + self.lineNumber + "):"
|
||||
else:
|
||||
line = self.filename + "(" + self.lineNumber + "):"
|
||||
reasonOnSameLine = False
|
||||
if self.reason == "FAILED":
|
||||
line += " " + "FAILED:"
|
||||
reasonOnSameLine = True
|
||||
if (len(self.messagePrefix) > 0 and self.messagePrefix == "warning:" or
|
||||
self.reason == "PASSED:" or self.expansionPrefix.startswith("FAILED - but was ok") ):
|
||||
line += " "
|
||||
lines.append(line)
|
||||
if not(reasonOnSameLine) and len(self.reason):
|
||||
lines.append(self.reason)
|
||||
if len(self.condition):
|
||||
lines.append(" " + self.condition)
|
||||
if len(self.expansionPrefix):
|
||||
lines.append(self.expansionPrefix)
|
||||
extraLine = True
|
||||
if len(self.expansion):
|
||||
for line in self.expansion:
|
||||
lines.append(" " + line)
|
||||
if len(self.messagePrefix):
|
||||
lines.append(self.messagePrefix)
|
||||
extraLine = True
|
||||
if len(self.messages):
|
||||
for msg in self.messages:
|
||||
lines.append(" " + msg)
|
||||
lines.append("")
|
||||
if len(self.noAssertions) > 0:
|
||||
if extraLine:
|
||||
lines.append("")
|
||||
lines.append(self.noAssertions)
|
||||
lines.append("")
|
||||
if len(self.output):
|
||||
for msg in self.output:
|
||||
lines.append(msg)
|
||||
return lines
|
||||
|
||||
def generateUnapprovedLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty condition..." + repr(self))
|
||||
lines = []
|
||||
extraLine = False
|
||||
if len(self.filename):
|
||||
line = self.filename + ":<" + "line number" + ">:"
|
||||
reasonOnSameLine = False
|
||||
if self.reason == "FAILED":
|
||||
line += " " + "FAILED:"
|
||||
reasonOnSameLine = True
|
||||
lines.append(line)
|
||||
if not(reasonOnSameLine) and len(self.reason):
|
||||
lines.append(self.reason)
|
||||
if len(self.condition):
|
||||
lines.append(" " + self.condition)
|
||||
if len(self.expansionPrefix):
|
||||
lines.append(self.expansionPrefix)
|
||||
extraLine = True
|
||||
if len(self.expansion):
|
||||
for line in self.expansion:
|
||||
m = self.hexParser.match(line)
|
||||
if m:
|
||||
while m:
|
||||
line = m.group(1) + "0x<hex digits>" + m.group(3)
|
||||
m = self.hexParser.match(line)
|
||||
lines.append(" " + line)
|
||||
if len(self.messagePrefix):
|
||||
lines.append(self.messagePrefix)
|
||||
extraLine = True
|
||||
if len(self.messages):
|
||||
for msg in self.messages:
|
||||
lines.append(" " + msg)
|
||||
lines.append("")
|
||||
if len(self.noAssertions) > 0:
|
||||
if extraLine:
|
||||
lines.append("")
|
||||
lines.append(self.noAssertions)
|
||||
lines.append("")
|
||||
if len(self.output):
|
||||
for msg in self.output:
|
||||
lines.append(msg)
|
||||
return lines
|
||||
|
||||
def addFailure(self, filename, lineNumber, output, message, type):
|
||||
self.reason = "failure"
|
||||
self.filename = filename
|
||||
self.lineNumber = lineNumber
|
||||
self.condition = type
|
||||
if message != None:
|
||||
self.expansion.append(message)
|
||||
self.output = output
|
||||
|
||||
def addError(self, filename, lineNumber, output, message, type):
|
||||
self.reason = "error"
|
||||
self.filename = filename
|
||||
self.lineNumber = lineNumber
|
||||
self.condition = type
|
||||
if message != None:
|
||||
self.expansion.append(message)
|
||||
self.output = output
|
||||
|
||||
def generateUnapprovedJunit(self):
|
||||
lines = []
|
||||
msg = ""
|
||||
for m in self.expansion:
|
||||
msg += m
|
||||
msg = msg.replace("\"", """)
|
||||
msg = msg.replace("<", "<")
|
||||
msg = msg.replace("<hex digits>", "<hex digits>")
|
||||
#msg = msg.replace(">", ">")
|
||||
|
||||
#print "R:",self.reason,msg,self.condition
|
||||
if len(self.reason) > 0:
|
||||
l = " <" + self.reason
|
||||
if len(msg) > 0:
|
||||
m = self.hexParser.match(msg)
|
||||
if m:
|
||||
while m:
|
||||
msg = m.group(1) + "0x<hex digits>" + m.group(3)
|
||||
m = self.hexParser.match(msg)
|
||||
l += " message=\"" + msg + "\""
|
||||
if self.condition != None:
|
||||
l += " type=\"" + self.condition + "\""
|
||||
l += ">"
|
||||
lines.append(l)
|
||||
if len(self.output) > 0:
|
||||
for o in self.output:
|
||||
lines.append(o)
|
||||
if len(self.filename) > 0:
|
||||
lines.append(self.filename + ":<" + self.lineNumber + ">")
|
||||
lines.append(" </" + self.reason + ">")
|
||||
return lines
|
||||
|
||||
class TestConditionApprovedParser:
|
||||
failedApprovedTestParser = re.compile( r'(.*\..pp).*:<(.*).*>:(.*FAILED)' )
|
||||
otherApprovedTestParser = re.compile( r'(.*\..pp).*:<(.*).*>:' )
|
||||
|
||||
def __init__(self):
|
||||
self.current = TestConditionData()
|
||||
|
||||
def parseApprovedLine(self,line):
|
||||
result = None
|
||||
if line.startswith("==============================================================================="):
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
|
||||
elif line.startswith("-------------------------------------------------------------------------------"):
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
|
||||
else:
|
||||
if line.startswith("No assertions in"):
|
||||
self.current.noAssertions = line.strip()
|
||||
self.current.state = self.current.MESSAGES
|
||||
else:
|
||||
m = self.failedApprovedTestParser.match(line)
|
||||
if m:
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
self.current.filename = m.group(1).strip()
|
||||
self.current.lineNumber = m.group(2).strip()
|
||||
self.current.reason = m.group(3).strip()
|
||||
self.current.state = self.current.CONDITION
|
||||
else:
|
||||
m = self.otherApprovedTestParser.match(line)
|
||||
if m:
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
self.current.filename = m.group(1).strip()
|
||||
self.current.lineNumber = m.group(2).strip()
|
||||
self.current.state = self.current.CONDITION
|
||||
elif not(self.current.empty()):
|
||||
self.current.parseCondition(line)
|
||||
return result
|
||||
|
||||
class TestConditionResultParser:
|
||||
failedResultsTestParser = re.compile( r'(.*\\)(.*\..pp).*\((.*).*\):(.*FAILED)' )
|
||||
otherResultsTestParser = re.compile( r'(.*\\)(.*\..pp).*\((.*).*\):' )
|
||||
|
||||
def __init__(self):
|
||||
self.current = TestConditionData()
|
||||
|
||||
def parseResultLine(self,line):
|
||||
result = None
|
||||
if line.startswith("==============================================================================="):
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
|
||||
elif line.startswith("-------------------------------------------------------------------------------"):
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
|
||||
else:
|
||||
if line.startswith("No assertions in"):
|
||||
self.current.noAssertions = line.strip()
|
||||
self.current.state = self.current.MESSAGES
|
||||
else:
|
||||
m = self.failedResultsTestParser.match(line)
|
||||
if m:
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
self.current.filenamePrefix = m.group(1).strip()
|
||||
self.current.filename = m.group(2).strip()
|
||||
self.current.lineNumber = m.group(3).strip()
|
||||
self.current.reason = m.group(4).strip()
|
||||
self.current.state = self.current.CONDITION
|
||||
else:
|
||||
m = self.otherResultsTestParser.match(line)
|
||||
if m:
|
||||
if not(self.current.empty()):
|
||||
result = self.current
|
||||
self.current = TestConditionData()
|
||||
self.current.filenamePrefix = m.group(1).strip()
|
||||
self.current.filename = m.group(2).strip()
|
||||
self.current.lineNumber = m.group(3).strip()
|
||||
self.current.state = self.current.CONDITION
|
||||
elif not(self.current.empty()):
|
||||
self.current.parseCondition(line)
|
||||
return result
|
||||
|
584
scripts/catch_test_case.py
Normal file
584
scripts/catch_test_case.py
Normal file
@ -0,0 +1,584 @@
|
||||
import re
|
||||
|
||||
from catch_conditions import TestConditionData
|
||||
from catch_conditions import TestConditionApprovedParser
|
||||
from catch_conditions import TestConditionResultParser
|
||||
|
||||
class EndOfClassName:
|
||||
@staticmethod
|
||||
def parseRawLine(line):
|
||||
if line.startswith("..............................................................................."):
|
||||
return ParseResult.END_OF_CLASS_NAME
|
||||
return ParseResult.NONE
|
||||
|
||||
class TestCaseData:
|
||||
|
||||
def __init__(self):
|
||||
self.name = ""
|
||||
self.nameParts = []
|
||||
self.classname = "global"
|
||||
self.sections = []
|
||||
self.filenamePrefix = ""
|
||||
self.filename = ""
|
||||
self.lineNumber = ""
|
||||
self.conditions = []
|
||||
self.sysout = []
|
||||
self.syserr = []
|
||||
self.result = ""
|
||||
|
||||
def __eq__(self, other):
|
||||
return self.__dict__ == other.__dict__
|
||||
|
||||
def __repr__(self):
|
||||
result = "[" + self.name + ", [ "
|
||||
suffix = ""
|
||||
for section in self.sections:
|
||||
result += suffix
|
||||
result += repr(section)
|
||||
suffix = ", "
|
||||
result + " ] "
|
||||
result += self.filename + ", " + self.lineNumber + " [ "
|
||||
suffix = ""
|
||||
for cond in self.conditions:
|
||||
result += suffix
|
||||
result += repr(cond)
|
||||
suffix = ", "
|
||||
result + " ] ]"
|
||||
return result
|
||||
|
||||
def empty(self):
|
||||
if len(self.name):
|
||||
return False
|
||||
return True
|
||||
|
||||
def generateApprovedLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty test case..." + repr(self))
|
||||
lines = []
|
||||
if len(self.name):
|
||||
lines.append("-------------------------------------------------------------------------------")
|
||||
for n in self.nameParts:
|
||||
lines.append(n)
|
||||
if len(self.sections) > 0:
|
||||
for section in self.sections:
|
||||
lines.append(" " + section)
|
||||
lines.append("-------------------------------------------------------------------------------")
|
||||
if len(self.filename):
|
||||
lines.append(self.filename + ":<" + self.lineNumber + ">")
|
||||
lines.append("...............................................................................")
|
||||
lines.append("")
|
||||
for cond in self.conditions:
|
||||
lines += cond.generateApprovedLines()
|
||||
return lines
|
||||
|
||||
def generateResultLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty test case..." + repr(self))
|
||||
lines = []
|
||||
if len(self.name):
|
||||
lines.append("-------------------------------------------------------------------------------")
|
||||
for n in self.nameParts:
|
||||
lines.append(n)
|
||||
if len(self.sections) > 0:
|
||||
for section in self.sections:
|
||||
lines.append(" " + section)
|
||||
lines.append("-------------------------------------------------------------------------------")
|
||||
if len(self.filename):
|
||||
lines.append(self.filenamePrefix + self.filename + "(" + self.lineNumber + ")")
|
||||
lines.append("...............................................................................")
|
||||
lines.append("")
|
||||
for cond in self.conditions:
|
||||
lines += cond.generateResultLines()
|
||||
return lines
|
||||
|
||||
def generateUnapprovedLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty test case..." + repr(self))
|
||||
lines = []
|
||||
if len(self.name):
|
||||
lines.append("-------------------------------------------------------------------------------")
|
||||
for n in self.nameParts:
|
||||
lines.append(n)
|
||||
if len(self.sections) > 0:
|
||||
for section in self.sections:
|
||||
lines.append(" " + section)
|
||||
lines.append("-------------------------------------------------------------------------------")
|
||||
if len(self.filename):
|
||||
lines.append(self.filename + ":<" + "line number" + ">")
|
||||
lines.append("...............................................................................")
|
||||
lines.append("")
|
||||
for cond in self.conditions:
|
||||
lines += cond.generateUnapprovedLines()
|
||||
return lines
|
||||
|
||||
def generateUnapprovedJunit(self):
|
||||
lines = []
|
||||
|
||||
condLines = []
|
||||
for cond in self.conditions:
|
||||
condLines += cond.generateUnapprovedJunit()
|
||||
|
||||
if len(self.name):
|
||||
l = " <testcase classname=\"" + self.classname + "\" name=\"" + self.name + "\" time=\"{duration}\""
|
||||
if len(condLines) > 0 or len(self.sysout) > 0 or len(self.syserr) > 0:
|
||||
l += ">"
|
||||
else:
|
||||
l += "/>"
|
||||
lines.append(l)
|
||||
#if len(self.sections) > 0:
|
||||
# for section in self.sections:
|
||||
# lines.append(" " + section)
|
||||
#if len(self.filename):
|
||||
# lines.append(self.filename + ":<" + "line number" + ">")
|
||||
# lines.append("...............................................................................")
|
||||
lines += condLines
|
||||
if len(self.sysout) > 0:
|
||||
lines.append(" <system-out>")
|
||||
for l in self.sysout:
|
||||
lines.append(l)
|
||||
lines.append(" </system-out>")
|
||||
if len(self.syserr) > 0:
|
||||
lines.append(" <system-err>")
|
||||
for l in self.syserr:
|
||||
lines.append(l)
|
||||
lines.append(" </system-err>")
|
||||
if len(condLines) > 0 or len(self.sysout) > 0 or len(self.syserr) > 0:
|
||||
lines.append(" </testcase>")
|
||||
return lines
|
||||
|
||||
def generateRecursiveSection(self, prefix, section):
|
||||
lines = []
|
||||
#print "S:",section
|
||||
if section[0] == "S":
|
||||
l = " " + prefix + "<Section name=\"" + section[1] + "\""
|
||||
if section[2] != None:
|
||||
li = section[2]
|
||||
li = li.replace("&","&")
|
||||
li = li.replace("<","<")
|
||||
li = li.replace("<hex digits>","<hex digits>")
|
||||
li = li.replace("\"",""")
|
||||
l += " description=\"" + li + "\""
|
||||
l += ">"
|
||||
lines.append(l)
|
||||
if len(section) > 4:
|
||||
index = 4
|
||||
while index < len(section):
|
||||
tmp = section[index]
|
||||
if len(tmp) > 0:
|
||||
if tmp[0] == "E":
|
||||
l = " " + prefix + "<Expression success=\"" + tmp[1] + "\""
|
||||
if tmp[2] != None:
|
||||
l += " filename=\"" + tmp[2] + "\""
|
||||
l += " >"
|
||||
lines.append(l)
|
||||
if len(tmp) > 3:
|
||||
cond = tmp[3]
|
||||
if len(cond[0]) > 0:
|
||||
lines.append(" " + prefix + "<Original>")
|
||||
for li in cond[0]:
|
||||
if len(li.strip()) > 0:
|
||||
li = li.replace("<","<")
|
||||
li = li.replace("<hex digits>","<hex digits>")
|
||||
li = li.replace("\"",""")
|
||||
lines.append(li)
|
||||
lines.append(" " + prefix + "</Original>")
|
||||
if len(cond[1]) > 0:
|
||||
lines.append(" " + prefix + "<Expanded>")
|
||||
for li in cond[1]:
|
||||
if len(li.strip()) > 0:
|
||||
li = li.replace("<","<")
|
||||
li = li.replace("<hex digits>","<hex digits>")
|
||||
li = li.replace("\"",""")
|
||||
lines.append(li)
|
||||
lines.append(" " + prefix + "</Expanded>")
|
||||
if len(cond) > 2:
|
||||
filename = cond[2]
|
||||
lines.append(" " + prefix + "<Exception filename=\"" + filename + "\" >")
|
||||
if len(cond) > 3:
|
||||
tmp = cond[3]
|
||||
for li in tmp:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
lines.append(" " + prefix + "</Exception>")
|
||||
elif len(tmp) > 4:
|
||||
print "RE:",tmp[4]
|
||||
|
||||
l = " " + prefix + "</Expression>"
|
||||
lines.append(l)
|
||||
elif tmp[0] == "X":
|
||||
l = " " + prefix + "<Exception filename=\"" + tmp[1] + "\" >"
|
||||
lines.append(l)
|
||||
for li in tmp[2]:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
l = " " + prefix + "</Exception>"
|
||||
lines.append(l)
|
||||
elif tmp[0] == "F":
|
||||
l = " " + prefix + "<Failure>"
|
||||
lines.append(l)
|
||||
for li in tmp[1]:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
l = " " + prefix + "</Failure>"
|
||||
lines.append(l)
|
||||
elif tmp[0] == "S":
|
||||
lines += self.generateRecursiveSection(prefix + " ", tmp)
|
||||
else:
|
||||
print "RS2:",tmp[0]
|
||||
else:
|
||||
print "RS:",section[index]
|
||||
index += 1
|
||||
|
||||
lines.append(" " + prefix + "<OverallResults successes=\"" + section[3][0] + "\" failures=\"" + section[3][1] + "\"/>")
|
||||
l = " " + prefix + "</Section>"
|
||||
lines.append(l)
|
||||
return lines
|
||||
|
||||
def generateSection(self, prefix, sections):
|
||||
lines = []
|
||||
for section in sections:
|
||||
#print "S:",section
|
||||
if section[0] == "S":
|
||||
lines += self.generateRecursiveSection(prefix, section)
|
||||
elif section[0] == "E":
|
||||
l = " " + prefix + "<Expression success=\"" + section[1] + "\""
|
||||
if section[2] != None:
|
||||
l += " filename=\"" + section[2] + "\""
|
||||
l += " >"
|
||||
lines.append(l)
|
||||
if len(section) > 3:
|
||||
cond = section[3]
|
||||
if len(cond[0]) > 0:
|
||||
lines.append(" " + prefix + "<Original>")
|
||||
for li in cond[0]:
|
||||
if len(li.strip()) > 0:
|
||||
li = li.replace("&","&")
|
||||
li = li.replace("<","<")
|
||||
li = li.replace("<hex digits>","<hex digits>")
|
||||
li = li.replace("\"",""")
|
||||
lines.append(li)
|
||||
lines.append(" " + prefix + "</Original>")
|
||||
if len(cond[1]) > 0:
|
||||
lines.append(" " + prefix + "<Expanded>")
|
||||
for li in cond[1]:
|
||||
if len(li.strip()) > 0:
|
||||
li = li.replace("<","<")
|
||||
li = li.replace("<hex digits>","<hex digits>")
|
||||
li = li.replace("\"",""")
|
||||
lines.append(li)
|
||||
lines.append(" " + prefix + "</Expanded>")
|
||||
if len(cond) > 2:
|
||||
filename = cond[2]
|
||||
lines.append(" " + prefix + "<Exception filename=\"" + filename + "\" >")
|
||||
if len(cond) > 3:
|
||||
tmp = cond[3]
|
||||
for li in tmp:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
lines.append(" " + prefix + "</Exception>")
|
||||
elif len(section) > 4:
|
||||
print "RE:",section[4]
|
||||
|
||||
l = " " + prefix + "</Expression>"
|
||||
lines.append(l)
|
||||
elif section[0] == "X":
|
||||
l = " " + prefix + "<Exception filename=\"" + section[1] + "\" >"
|
||||
lines.append(l)
|
||||
for li in section[2]:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
l = " " + prefix + "</Exception>"
|
||||
lines.append(l)
|
||||
elif section[0] == "I":
|
||||
l = " " + prefix + "<Info>"
|
||||
lines.append(l)
|
||||
for li in section[1]:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
l = " " + prefix + "</Info>"
|
||||
lines.append(l)
|
||||
elif section[0] == "W":
|
||||
l = " " + prefix + "<Warning>"
|
||||
lines.append(l)
|
||||
for li in section[1]:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
l = " " + prefix + "</Warning>"
|
||||
lines.append(l)
|
||||
elif section[0] == "F":
|
||||
l = " " + prefix + "<Failure>"
|
||||
lines.append(l)
|
||||
for li in section[1]:
|
||||
if len(li.strip()) > 0:
|
||||
lines.append(li)
|
||||
l = " " + prefix + "</Failure>"
|
||||
lines.append(l)
|
||||
return lines
|
||||
|
||||
def generateUnapprovedXml(self):
|
||||
lines = []
|
||||
|
||||
if len(self.name):
|
||||
l = " <TestCase name=\"" + self.name + "\">"
|
||||
lines.append(l)
|
||||
|
||||
if len(self.sections) > 0:
|
||||
prefix = " "
|
||||
lines += self.generateSection(prefix, self.sections)
|
||||
|
||||
if len(self.result) > 0:
|
||||
lines.append(" <OverallResult success=\"" + self.result + "\"/>")
|
||||
|
||||
if len(self.name):
|
||||
l = " </TestCase>"
|
||||
lines.append(l)
|
||||
return lines
|
||||
|
||||
def addFailure(self, filename, lineNumber, output, message, type):
|
||||
self.filename = filename
|
||||
self.lineNumber = lineNumber
|
||||
condition = TestConditionData()
|
||||
condition.addFailure(filename, lineNumber, output, message, type)
|
||||
self.conditions.append(condition)
|
||||
|
||||
def addError(self, filename, lineNumber, output, message, type):
|
||||
self.filename = filename
|
||||
self.lineNumber = lineNumber
|
||||
condition = TestConditionData()
|
||||
condition.addError(filename, lineNumber, output, message, type)
|
||||
self.conditions.append(condition)
|
||||
|
||||
def addSysout(self, output):
|
||||
self.sysout = output
|
||||
|
||||
def addSyserr(self, output):
|
||||
self.syserr = output
|
||||
|
||||
def addOverallResult(self,r):
|
||||
self.result = r
|
||||
|
||||
def addSection(self,name,desc, results):
|
||||
section = []
|
||||
section.append("S")
|
||||
section.append(name)
|
||||
section.append(desc)
|
||||
section.append(results)
|
||||
self.sections.append(section)
|
||||
return section
|
||||
|
||||
def addExpression(self,result,filename):
|
||||
section = []
|
||||
section.append("E")
|
||||
section.append(result)
|
||||
section.append(filename)
|
||||
self.sections.append(section)
|
||||
return section
|
||||
|
||||
def addException(self,filename,text):
|
||||
section = []
|
||||
section.append("X")
|
||||
section.append(filename)
|
||||
section.append(text)
|
||||
#print section
|
||||
self.sections.append(section)
|
||||
return section
|
||||
|
||||
def addInfo(self,text):
|
||||
section = []
|
||||
section.append("I")
|
||||
section.append(text)
|
||||
self.sections.append(section)
|
||||
return section
|
||||
|
||||
def addWarning(self,text):
|
||||
section = []
|
||||
section.append("W")
|
||||
section.append(text)
|
||||
self.sections.append(section)
|
||||
return section
|
||||
|
||||
def addSimpleFailure(self,text):
|
||||
section = []
|
||||
section.append("F")
|
||||
section.append(text)
|
||||
self.sections.append(section)
|
||||
return section
|
||||
|
||||
def addExpressionDetails(self, section, subExp):
|
||||
section.append(subExp)
|
||||
|
||||
def addSubException(self, section, filename, text):
|
||||
tmp = []
|
||||
tmp.append("X")
|
||||
tmp.append(filename)
|
||||
tmp.append(text)
|
||||
section.append(tmp)
|
||||
|
||||
def addSubFailure(self, section, text):
|
||||
tmp = []
|
||||
tmp.append("F")
|
||||
tmp.append(text)
|
||||
section.append(tmp)
|
||||
|
||||
def addSubExpression(self,section,result,filename):
|
||||
tmp = []
|
||||
tmp.append("E")
|
||||
tmp.append(result)
|
||||
tmp.append(filename)
|
||||
section.append(tmp)
|
||||
#print "Section:",section
|
||||
return tmp
|
||||
|
||||
def addSubSection(self,section,name,desc,results):
|
||||
tmp = []
|
||||
tmp.append("S")
|
||||
tmp.append(name)
|
||||
tmp.append(desc)
|
||||
tmp.append(results)
|
||||
section.append(tmp)
|
||||
#print "Section:",section
|
||||
return tmp
|
||||
|
||||
class TestCaseApprovedParser:
|
||||
NONE = 0
|
||||
TEST_CASE_NAME_EXPECTED = 1
|
||||
TEST_CASE_NAME = 2
|
||||
TEST_CLASS_EXPECTED = 3
|
||||
END_OF_CLASS_NAME_EXPECTED = 4
|
||||
TEST_CONDITION_EXPECTED = 5
|
||||
|
||||
testFilenameParser = re.compile( r'(.*\..pp).*:<(.*).*>' )
|
||||
|
||||
def __init__(self):
|
||||
self.state = self.NONE
|
||||
self.current = TestCaseData()
|
||||
self.conditionParser = TestConditionApprovedParser()
|
||||
|
||||
def parseApprovedLine(self,line):
|
||||
result = None
|
||||
if self.state == self.NONE:
|
||||
if line.startswith("-------------------------------------------------------------------------------"):
|
||||
self.state = self.TEST_CASE_NAME_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CASE_NAME_EXPECTED:
|
||||
if len(line):
|
||||
self.current.name = line.strip()
|
||||
self.current.nameParts.append(line.strip())
|
||||
self.state = self.TEST_CASE_NAME
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CASE_NAME:
|
||||
if line.startswith("-------------------------------------------------------------------------------"):
|
||||
self.state = self.TEST_CLASS_EXPECTED
|
||||
elif line.startswith(" "):
|
||||
#print "***SECTION: ",line
|
||||
self.current.sections.append(line[2:])
|
||||
elif len(line):
|
||||
if len(self.current.name) > 0:
|
||||
self.current.name += line.strip()
|
||||
else:
|
||||
self.current.name = line.strip()
|
||||
self.current.nameParts.append(line.strip())
|
||||
elif self.state == self.TEST_CLASS_EXPECTED:
|
||||
m = self.testFilenameParser.match(line)
|
||||
if m:
|
||||
self.current.filename = m.group(1).strip()
|
||||
self.current.lineNumber = m.group(2).strip()
|
||||
self.state = self.END_OF_CLASS_NAME_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.END_OF_CLASS_NAME_EXPECTED:
|
||||
if line.startswith("..............................................................................."):
|
||||
self.state = self.TEST_CONDITION_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CONDITION_EXPECTED:
|
||||
#print "**** LINE " + line
|
||||
condition = self.conditionParser.parseApprovedLine(line)
|
||||
if isinstance(condition, TestConditionData):
|
||||
#print "**** CASE " + repr(condition)
|
||||
self.current.conditions.append(condition)
|
||||
if line.startswith("-------------------------------------------------------------------------------"):
|
||||
result = self.current
|
||||
self.current = TestCaseData()
|
||||
self.state = self.TEST_CASE_NAME_EXPECTED
|
||||
elif line.startswith("==============================================================================="):
|
||||
result = self.current
|
||||
self.current = TestCaseData()
|
||||
self.state = self.NONE
|
||||
|
||||
return result
|
||||
|
||||
class TestCaseResultParser:
|
||||
NONE = 0
|
||||
TEST_CASE_NAME_EXPECTED = 1
|
||||
TEST_CASE_NAME = 2
|
||||
TEST_CLASS_EXPECTED = 3
|
||||
END_OF_CLASS_NAME_EXPECTED = 4
|
||||
TEST_CONDITION_EXPECTED = 5
|
||||
|
||||
testFilenameParser = re.compile( r'(.*\\)(.*\..pp).*\((.*).*\)' )
|
||||
|
||||
def __init__(self):
|
||||
self.state = self.NONE
|
||||
self.current = TestCaseData()
|
||||
self.conditionParser = TestConditionResultParser()
|
||||
|
||||
def parseResultLine(self,line):
|
||||
result = None
|
||||
if self.state == self.NONE:
|
||||
if line.startswith("-------------------------------------------------------------------------------"):
|
||||
self.state = self.TEST_CASE_NAME_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CASE_NAME_EXPECTED:
|
||||
if len(line):
|
||||
self.current.name = line.strip()
|
||||
self.current.nameParts.append(line.strip())
|
||||
self.state = self.TEST_CASE_NAME
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CASE_NAME:
|
||||
if line.startswith("-------------------------------------------------------------------------------"):
|
||||
self.state = self.TEST_CLASS_EXPECTED
|
||||
elif line.startswith(" "):
|
||||
#print "***SECTION: ",line
|
||||
self.current.sections.append(line[2:])
|
||||
elif len(line):
|
||||
if len(self.current.name) > 0:
|
||||
self.current.name += line.strip()
|
||||
else:
|
||||
self.current.name = line.strip()
|
||||
self.current.nameParts.append(line.strip())
|
||||
elif self.state == self.TEST_CLASS_EXPECTED:
|
||||
m = self.testFilenameParser.match(line)
|
||||
if m:
|
||||
self.current.filenamePrefix = m.group(1).strip()
|
||||
self.current.filename = m.group(2).strip()
|
||||
self.current.lineNumber = m.group(3).strip()
|
||||
self.state = self.END_OF_CLASS_NAME_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.END_OF_CLASS_NAME_EXPECTED:
|
||||
if line.startswith("..............................................................................."):
|
||||
self.state = self.TEST_CONDITION_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CONDITION_EXPECTED:
|
||||
#print "**** LINE " + line
|
||||
condition = self.conditionParser.parseResultLine(line)
|
||||
if isinstance(condition, TestConditionData):
|
||||
#print "**** CASE " + repr(condition)
|
||||
self.current.conditions.append(condition)
|
||||
if line.startswith("-------------------------------------------------------------------------------"):
|
||||
result = self.current
|
||||
self.current = TestCaseData()
|
||||
self.state = self.TEST_CASE_NAME_EXPECTED
|
||||
elif line.startswith("==============================================================================="):
|
||||
result = self.current
|
||||
self.current = TestCaseData()
|
||||
self.state = self.NONE
|
||||
|
||||
return result
|
||||
|
430
scripts/catch_test_run.py
Normal file
430
scripts/catch_test_run.py
Normal file
@ -0,0 +1,430 @@
|
||||
import re
|
||||
import os
|
||||
|
||||
from catch_test_case import TestCaseApprovedParser
|
||||
from catch_test_case import TestCaseResultParser
|
||||
from catch_test_case import TestCaseData
|
||||
from catch_conditions import RandomOutput
|
||||
|
||||
class TestRunData:
|
||||
|
||||
def __init__(self):
|
||||
self.appname = ""
|
||||
self.version = ""
|
||||
self.testcases = []
|
||||
self.results = ""
|
||||
self.output = []
|
||||
self.outputLine = 0
|
||||
self.writtenOutput = False
|
||||
self.sysout = []
|
||||
self.syserr = []
|
||||
self.errors = ""
|
||||
self.failures = ""
|
||||
self.tests = ""
|
||||
|
||||
def __eq__(self, other):
|
||||
return self.__dict__ == other.__dict__
|
||||
|
||||
def __repr__(self):
|
||||
result = "[" + self.appname + ", " + self.version + " [ "
|
||||
suffix = ""
|
||||
for case in self.testcases:
|
||||
result += suffix
|
||||
result += repr(case)
|
||||
suffix = ", "
|
||||
result += " ]"
|
||||
result += self.results
|
||||
result += " ]"
|
||||
return result
|
||||
|
||||
def empty(self):
|
||||
if len(self.appname):
|
||||
return False
|
||||
return True
|
||||
|
||||
def generateApprovedLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty test run..." + repr(self))
|
||||
lines = []
|
||||
self.writtenOutput = False
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and self.outputLine == 0:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
if len(self.appname):
|
||||
lines.append("")
|
||||
lines.append("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
|
||||
lines.append(self.appname + " is a " + self.version + " host application.")
|
||||
lines.append("Run with -? for options")
|
||||
lines.append("")
|
||||
for case in self.testcases:
|
||||
lines += case.generateApprovedLines()
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and len(lines) >= self.outputLine:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
lines.append("===============================================================================")
|
||||
lines.append(self.results)
|
||||
lines.append("")
|
||||
|
||||
return lines
|
||||
|
||||
def generateSortedApprovedLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty test run..." + repr(self))
|
||||
lines = []
|
||||
self.writtenOutput = False
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and self.outputLine == 0:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
if len(self.appname):
|
||||
lines.append("")
|
||||
lines.append("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
|
||||
lines.append(self.appname + " is a " + self.version + " host application.")
|
||||
lines.append("Run with -? for options")
|
||||
lines.append("")
|
||||
sortedTestcases = sorted(self.testcases, key=lambda x: x.name, reverse=False)
|
||||
for case in sortedTestcases:
|
||||
lines += case.generateApprovedLines()
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and len(lines) >= self.outputLine:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
lines.append("===============================================================================")
|
||||
lines.append(self.results)
|
||||
lines.append("")
|
||||
|
||||
return lines
|
||||
|
||||
def generateResultLines(self):
|
||||
if self.empty():
|
||||
raise Exception("Empty test run..." + repr(self))
|
||||
lines = []
|
||||
self.writtenOutput = False
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and self.outputLine == 0:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
if len(self.appname):
|
||||
lines.append("")
|
||||
lines.append("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
|
||||
lines.append(self.appname + " is a " + self.version + " host application.")
|
||||
lines.append("Run with -? for options")
|
||||
lines.append("")
|
||||
for case in self.testcases:
|
||||
lines += case.generateResultLines()
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and len(lines) >= self.outputLine:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
lines.append("===============================================================================")
|
||||
lines.append(self.results)
|
||||
lines.append("")
|
||||
|
||||
return lines
|
||||
|
||||
def generateUnapprovedLines(self, outputLine):
|
||||
if self.empty():
|
||||
raise Exception("Empty test run..." + repr(self))
|
||||
lines = []
|
||||
self.writtenOutput = False
|
||||
#print "U:",outputLine,",",self.output
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and outputLine == 0:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
if len(self.appname):
|
||||
lines.append("")
|
||||
lines.append("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
|
||||
lines.append("CatchSelfTest" + " is a " + "<version>" + " host application.")
|
||||
lines.append("Run with -? for options")
|
||||
lines.append("")
|
||||
for case in self.testcases:
|
||||
lines += case.generateUnapprovedLines()
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and len(lines) >= outputLine:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
lines.append("===============================================================================")
|
||||
lines.append(self.results)
|
||||
lines.append("")
|
||||
|
||||
return lines
|
||||
|
||||
def generateSortedUnapprovedLines(self, outputLine):
|
||||
if self.empty():
|
||||
raise Exception("Empty test run..." + repr(self))
|
||||
lines = []
|
||||
self.writtenOutput = False
|
||||
#print "U:",outputLine,",",self.output
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and outputLine == 0:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
if len(self.appname):
|
||||
lines.append("")
|
||||
lines.append("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
|
||||
lines.append("CatchSelfTest" + " is a " + "<version>" + " host application.")
|
||||
lines.append("Run with -? for options")
|
||||
lines.append("")
|
||||
sortedTestcases = sorted(self.testcases, key=lambda x: x.name, reverse=False)
|
||||
for case in sortedTestcases:
|
||||
lines += case.generateUnapprovedLines()
|
||||
if not(self.writtenOutput) and len(self.output) > 0 and len(lines) >= outputLine:
|
||||
lines += self.output
|
||||
self.writtenOutput = True
|
||||
lines.append("===============================================================================")
|
||||
lines.append(self.results)
|
||||
lines.append("")
|
||||
|
||||
return lines
|
||||
|
||||
def generateSortedUnapprovedJunit(self):
|
||||
lines = []
|
||||
#print "U:",outputLine,",",self.output
|
||||
lines.append("<testsuites>")
|
||||
l = " <testsuite name=\""
|
||||
l += self.appname
|
||||
l += "\" errors=\""
|
||||
l += self.errors
|
||||
l += "\" failures=\""
|
||||
l += self.failures
|
||||
l += "\" tests=\""
|
||||
l += self.tests
|
||||
l += "\" hostname=\"tbd\" time=\"{duration}\" timestamp=\"tbd\">"
|
||||
lines.append(l)
|
||||
sortedTestcases = sorted(self.testcases, key=lambda x: x.classname, reverse=False)
|
||||
sortedTestcases = sorted(sortedTestcases, key=lambda x: x.name, reverse=False)
|
||||
#sortedTestcases = self.testcases
|
||||
for case in sortedTestcases:
|
||||
lines += case.generateUnapprovedJunit()
|
||||
|
||||
if len(self.sysout) > 0:
|
||||
lines.append(" <system-out>")
|
||||
for l in self.sysout:
|
||||
lines.append(l)
|
||||
lines.append(" </system-out>")
|
||||
if len(self.syserr) > 0:
|
||||
lines.append(" <system-err>")
|
||||
for l in self.syserr:
|
||||
lines.append(l)
|
||||
lines.append(" </system-err>")
|
||||
|
||||
lines.append(" </testsuite>")
|
||||
lines.append("</testsuites>")
|
||||
return lines
|
||||
|
||||
def generateSortedUnapprovedXml(self):
|
||||
lines = []
|
||||
#print "U:",outputLine,",",self.output
|
||||
lines.append("<Catch name=\"" + self.appname + "\">")
|
||||
lines.append(" <Group name=\"~_\">")
|
||||
|
||||
sortedTestcases = sorted(self.testcases, key=lambda x: x.classname, reverse=False)
|
||||
sortedTestcases = sorted(sortedTestcases, key=lambda x: x.name, reverse=False)
|
||||
#sortedTestcases = self.testcases
|
||||
for case in sortedTestcases:
|
||||
lines += case.generateUnapprovedXml()
|
||||
|
||||
l = "<OverallResults successes=\""
|
||||
# successes="663" failures="109"
|
||||
l += self.tests
|
||||
l += "\" failures=\""
|
||||
l += self.failures
|
||||
l += "\"/>"
|
||||
lines.append(" " + l)
|
||||
lines.append(" </Group>")
|
||||
lines.append(" " + l)
|
||||
lines.append("</Catch>")
|
||||
return lines
|
||||
|
||||
def addTestCase(self, name):
|
||||
testcase = TestCaseData()
|
||||
testcase.name = name
|
||||
testcase.nameParts.append(name)
|
||||
self.testcases.append(testcase)
|
||||
return testcase
|
||||
|
||||
def addClassTestCase(self, cls, name):
|
||||
testcase = TestCaseData()
|
||||
testcase.classname = cls
|
||||
testcase.name = name
|
||||
testcase.nameParts.append(name)
|
||||
self.testcases.append(testcase)
|
||||
return testcase
|
||||
|
||||
def addSysout(self, output):
|
||||
self.sysout = output
|
||||
|
||||
def addSyserr(self, output):
|
||||
self.syserr = output
|
||||
|
||||
class TestRunApprovedParser:
|
||||
NONE = 0
|
||||
VERSION_EXPECTED = 1
|
||||
TEST_CASE_EXPECTED = 2
|
||||
END_RUN_INFO = 3
|
||||
|
||||
versionParser = re.compile( r'(.*)is a (<version>*).*' )
|
||||
|
||||
def __init__(self):
|
||||
self.state = self.NONE
|
||||
self.current = TestRunData()
|
||||
self.testcaseParser = TestCaseApprovedParser()
|
||||
self.lineNumber = 0
|
||||
|
||||
def parseApprovedLine(self,line):
|
||||
result = None
|
||||
if self.state == self.NONE:
|
||||
if line.startswith("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"):
|
||||
self.state = self.VERSION_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.VERSION_EXPECTED:
|
||||
m = self.versionParser.match(line)
|
||||
if m:
|
||||
self.current.appname = m.group(1).strip()
|
||||
self.current.version = m.group(2).strip()
|
||||
self.state = self.TEST_CASE_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CASE_EXPECTED:
|
||||
if line == "Run with -? for options":
|
||||
pass
|
||||
else:
|
||||
testcase = None
|
||||
try:
|
||||
testcase = self.testcaseParser.parseApprovedLine(line)
|
||||
except RandomOutput as e:
|
||||
#print "E:", self.lineNumber, ", ",e.output
|
||||
self.current.output = e.output
|
||||
self.current.outputLine = self.lineNumber - 10
|
||||
|
||||
if isinstance(testcase, TestCaseData):
|
||||
self.current.testcases.append(testcase)
|
||||
if line.startswith("==============================================================================="):
|
||||
self.state = self.END_RUN_INFO
|
||||
elif self.state == self.END_RUN_INFO:
|
||||
if len(line):
|
||||
self.current.results = line.strip()
|
||||
result = self.current
|
||||
|
||||
self.lineNumber += 1
|
||||
return result
|
||||
|
||||
class TestRunApprovedHandler:
|
||||
|
||||
def __init__(self, filePath):
|
||||
rawFile = open( filePath, 'r' )
|
||||
parser = TestRunApprovedParser()
|
||||
lineNumber = 0
|
||||
self.current = None
|
||||
for line in rawFile:
|
||||
line = line.rstrip()
|
||||
#print "L:", lineNumber, "'",line,"'"
|
||||
result = parser.parseApprovedLine(line)
|
||||
if isinstance(result, TestRunData):
|
||||
self.current = result
|
||||
lineNumber += 1
|
||||
if not(isinstance(self.current, TestRunData) ):
|
||||
raise Exception("File could not be parsed: '" + filePath + "'")
|
||||
|
||||
def writeRawFile(self,filePath):
|
||||
rawWriteFile = open( filePath, 'wb' )
|
||||
lines = self.current.generateApprovedLines()
|
||||
for line in lines:
|
||||
rawWriteFile.write(line + "\n")
|
||||
|
||||
def writeSortedRawFile(self,filePath):
|
||||
rawWriteFile = open( filePath, 'wb' )
|
||||
lines = self.current.generateSortedApprovedLines()
|
||||
for line in lines:
|
||||
rawWriteFile.write(line + "\n")
|
||||
|
||||
class TestRunResultParser:
|
||||
NONE = 0
|
||||
VERSION_EXPECTED = 1
|
||||
TEST_CASE_EXPECTED = 2
|
||||
END_RUN_INFO = 3
|
||||
|
||||
versionParser = re.compile( r'(.*)is a (Catch v[0-9]*.[0-9]* b[0-9]*).*' )
|
||||
|
||||
def __init__(self):
|
||||
self.state = self.NONE
|
||||
self.current = TestRunData()
|
||||
self.testcaseParser = TestCaseResultParser()
|
||||
self.lineNumber = 0
|
||||
|
||||
def parseResultLine(self,line):
|
||||
result = None
|
||||
if self.state == self.NONE:
|
||||
if line.startswith("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"):
|
||||
self.state = self.VERSION_EXPECTED
|
||||
elif len(line):
|
||||
self.current.output.append(line.strip())
|
||||
if len(self.current.output) == 10:
|
||||
if (self.current.output[0] == "Message from section one" and self.current.output[1] == "Message from section two" and
|
||||
self.current.output[2] == "Some information" and self.current.output[3] == "An error" and
|
||||
self.current.output[4] == "Message from section one" and self.current.output[5] == "Message from section two" and
|
||||
self.current.output[6] == "Some information" and self.current.output[7] == "An error" and
|
||||
self.current.output[8] == "hello" and self.current.output[9] == "hello" ):
|
||||
|
||||
self.current.outputLine = self.lineNumber - 9
|
||||
|
||||
elif self.state == self.VERSION_EXPECTED:
|
||||
m = self.versionParser.match(line)
|
||||
if m:
|
||||
self.current.appname = m.group(1).strip()
|
||||
self.current.version = m.group(2).strip()
|
||||
self.state = self.TEST_CASE_EXPECTED
|
||||
elif len(line):
|
||||
raise Exception("Unknown parse line: '" + line + "'")
|
||||
elif self.state == self.TEST_CASE_EXPECTED:
|
||||
if line == "Run with -? for options":
|
||||
pass
|
||||
else:
|
||||
testcase = None
|
||||
try:
|
||||
testcase = self.testcaseParser.parseResultLine(line)
|
||||
except RandomOutput as e:
|
||||
#print "E:", self.lineNumber, ", ",e.output
|
||||
self.current.output = e.output
|
||||
self.current.outputLine = self.lineNumber - 10
|
||||
|
||||
if isinstance(testcase, TestCaseData):
|
||||
self.current.testcases.append(testcase)
|
||||
if line.startswith("==============================================================================="):
|
||||
self.state = self.END_RUN_INFO
|
||||
elif self.state == self.END_RUN_INFO:
|
||||
if len(line):
|
||||
self.current.results = line.strip()
|
||||
result = self.current
|
||||
|
||||
self.lineNumber += 1
|
||||
return result
|
||||
|
||||
class TestRunResultHandler:
|
||||
|
||||
def __init__(self, filePath):
|
||||
rawFile = open( filePath, 'r' )
|
||||
parser = TestRunResultParser()
|
||||
lineNumber = 0
|
||||
self.current = None
|
||||
for line in rawFile:
|
||||
line = line.rstrip()
|
||||
#print "L:", lineNumber, "'",line,"'"
|
||||
result = parser.parseResultLine(line)
|
||||
if isinstance(result, TestRunData):
|
||||
self.current = result
|
||||
lineNumber += 1
|
||||
if not(isinstance(self.current, TestRunData) ):
|
||||
raise Exception("File could not be parsed: '" + filePath + "'")
|
||||
|
||||
def writeRawFile(self,filePath):
|
||||
rawWriteFile = open( filePath, 'wb' )
|
||||
lines = self.current.generateResultLines()
|
||||
for line in lines:
|
||||
rawWriteFile.write(line + os.linesep)
|
||||
|
||||
def writeUnapprovedFile(self,filePath,outputLine):
|
||||
rawWriteFile = open( filePath, 'wb' )
|
||||
lines = self.current.generateUnapprovedLines(outputLine)
|
||||
for line in lines:
|
||||
rawWriteFile.write(line + "\n")
|
||||
def writeSortedUnapprovedFile(self,filePath,outputLine):
|
||||
rawWriteFile = open( filePath, 'wb' )
|
||||
lines = self.current.generateSortedUnapprovedLines(outputLine)
|
||||
for line in lines:
|
||||
rawWriteFile.write(line + "\n")
|
698
scripts/test_conditions.py
Normal file
698
scripts/test_conditions.py
Normal file
@ -0,0 +1,698 @@
|
||||
import unittest
|
||||
import catch_conditions
|
||||
|
||||
from catch_conditions import TestConditionApprovedParser
|
||||
from catch_conditions import TestConditionResultParser
|
||||
from catch_conditions import TestConditionData
|
||||
from catch_conditions import RandomOutput
|
||||
|
||||
class ConditionTest(unittest.TestCase):
|
||||
|
||||
def testConditionEquality(self):
|
||||
c1 = TestConditionData()
|
||||
c2 = TestConditionData()
|
||||
c1.state = TestConditionData.CONDITION
|
||||
c2.state = TestConditionData.EXPANSION
|
||||
c1.filenamePrefix = "..\\..\\Test"
|
||||
c2.filenamePrefix = "..\\..\\Test"
|
||||
self.assertTrue(c1 == c2)
|
||||
c2.filenamePrefix = "..\\..\\Junk"
|
||||
self.assertFalse(c1 == c2)
|
||||
self.assertTrue(c1 != c2)
|
||||
|
||||
def testEndOfTestRunIsFound(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
line = "==============================================================================="
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(obj.current.empty())
|
||||
|
||||
def testEndOfTestCaseIsFound(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
line = "-------------------------------------------------------------------------------"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(obj.current.empty())
|
||||
|
||||
def testFailedConditionIsFound(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
line = "ClassTests.cpp:<line number>: FAILED:"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue( not(obj.current.empty()) )
|
||||
|
||||
def testOtherConditionIsFound(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
line = "ClassTests.cpp:<line number>:"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue( not(obj.current.empty()) )
|
||||
|
||||
def testFailedConditionSetsReason(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
line = "ClassTests.cpp:<line number>: FAILED:"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(obj.current.reason == "FAILED")
|
||||
self.assertTrue(obj.current.filename == "ClassTests.cpp")
|
||||
self.assertTrue(obj.current.lineNumber == "line number")
|
||||
|
||||
def testOtherConditionSetsFileNameAndLine(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
line = "MessageTests.cpp:<line number>:"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(obj.current.filename == "MessageTests.cpp")
|
||||
self.assertTrue(obj.current.lineNumber == "line number")
|
||||
|
||||
def testFailedConditionSetsCondition(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = ["ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
""]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
|
||||
self.assertTrue(obj.current.condition == "REQUIRE( s == \"world\" )")
|
||||
newLines = obj.current.generateApprovedLines()
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testExpansionConditionReturnsExpansion(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = ["ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:" ]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
|
||||
def testExpansionSetsExpansion(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" 1 == 2",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
#print lines
|
||||
self.assertTrue(isinstance(result, TestConditionData))
|
||||
self.assertTrue(len(result.expansion) == 1)
|
||||
self.assertTrue(result.expansion[0] == "1 == 2")
|
||||
newLines = result.generateApprovedLines()
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testTwoConditions(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.int_seven == 6 )",
|
||||
"with expansion:",
|
||||
" 7 == 6",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.int_seven == 8 )",
|
||||
"with expansion:",
|
||||
" 7 == 8",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testSuccessConditions(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "ApproxTests.cpp:<line number>:",
|
||||
"PASSED:",
|
||||
" REQUIRE( d == Approx( 1.23 ) )",
|
||||
"with expansion:",
|
||||
" 1.23 == Approx( 1.23 )",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print result
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testConditionsWithoutExpansion(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( false != false )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( true != true )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( !true )",
|
||||
"with expansion:",
|
||||
" false",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testExceptionsExplicit(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "ExceptionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK_THROWS_AS( thisThrows() )",
|
||||
"due to unexpected exception with message:",
|
||||
" expected exception",
|
||||
"",
|
||||
"ExceptionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK_THROWS_AS( thisDoesntThrow() )",
|
||||
"because no exception was thrown where one was expected:",
|
||||
"",
|
||||
"ExceptionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK_NOTHROW( thisThrows() )",
|
||||
"due to unexpected exception with message:",
|
||||
" expected exception",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testExceptionsImplicit(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "ExceptionTests.cpp:<line number>: FAILED:",
|
||||
"due to unexpected exception with message:",
|
||||
" unexpected exception",
|
||||
"",
|
||||
"ExceptionTests.cpp:<line number>: FAILED:",
|
||||
" {Unknown expression after the reported line}",
|
||||
"due to unexpected exception with message:",
|
||||
" unexpected exception",
|
||||
"",
|
||||
"ExceptionTests.cpp:<line number>: FAILED:",
|
||||
"due to unexpected exception with message:",
|
||||
" 3.14",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testWarning(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MessageTests.cpp:<line number>:",
|
||||
"warning:",
|
||||
" this is a warning",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMessages1(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MessageTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( a == 1 )",
|
||||
"with expansion:",
|
||||
" 2 == 1",
|
||||
"with messages:",
|
||||
" this message should be logged",
|
||||
" so should this",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMessagesExplicitFail(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MessageTests.cpp:<line number>: FAILED:",
|
||||
"explicitly with message:",
|
||||
" This is a failure",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMessagesOutput(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MessageTests.cpp:<line number>: FAILED:",
|
||||
"explicitly with message:",
|
||||
" Message from section two",
|
||||
"",
|
||||
"Message from section one",
|
||||
"Message from section two",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMultiMessages(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MessageTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( i < 10 )",
|
||||
"with expansion:",
|
||||
" 10 < 10",
|
||||
"with messages:",
|
||||
" current counter 10",
|
||||
" i := 10",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMiscMessages(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MiscTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( ( fib[i] % 2 ) == 0 )",
|
||||
"with expansion:",
|
||||
" 1 == 0",
|
||||
"with message:",
|
||||
" Testing if fib[0] (1) is even",
|
||||
"",
|
||||
"MiscTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( ( fib[i] % 2 ) == 0 )",
|
||||
"with expansion:",
|
||||
" 1 == 0",
|
||||
"with message:",
|
||||
" Testing if fib[1] (1) is even",
|
||||
"",
|
||||
"MiscTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( ( fib[i] % 2 ) == 0 )",
|
||||
"with expansion:",
|
||||
" 1 == 0",
|
||||
"with message:",
|
||||
" Testing if fib[3] (3) is even",
|
||||
"",
|
||||
"MiscTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( ( fib[i] % 2 ) == 0 )",
|
||||
"with expansion:",
|
||||
" 1 == 0",
|
||||
"with message:",
|
||||
" Testing if fib[4] (5) is even",
|
||||
"",
|
||||
"MiscTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( ( fib[i] % 2 ) == 0 )",
|
||||
"with expansion:",
|
||||
" 1 == 0",
|
||||
"with message:",
|
||||
" Testing if fib[6] (13) is even",
|
||||
"",
|
||||
"MiscTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( ( fib[i] % 2 ) == 0 )",
|
||||
"with expansion:",
|
||||
" 1 == 0",
|
||||
"with message:",
|
||||
" Testing if fib[7] (21) is even",
|
||||
"",
|
||||
"Some information",
|
||||
"An error",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testRandomOutput(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MiscTests.cpp:<line number>: FAILED:",
|
||||
"explicitly with message:",
|
||||
" to infinity and beyond",
|
||||
"",
|
||||
"Message from section one",
|
||||
"Message from section two",
|
||||
"Some information",
|
||||
"An error",
|
||||
"Message from section one",
|
||||
"Message from section two",
|
||||
"Some information",
|
||||
"An error",
|
||||
"hello",
|
||||
"hello",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
try:
|
||||
result = obj.parseApprovedLine(line)
|
||||
except RandomOutput as e:
|
||||
randomOutput = e.output
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
self.assertTrue( len(randomOutput) == 10)
|
||||
newLines += randomOutput
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMultiLineWarning(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "TrickyTests.cpp:<line number>:",
|
||||
"warning:",
|
||||
" Uncomment the code in this test to check that it gives a sensible compiler",
|
||||
" error",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMultiMessagesAfterCondition(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MiscTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( false )",
|
||||
"with messages:",
|
||||
" hi",
|
||||
" i := 7",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
randomOutput = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testNoAssertions(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "",
|
||||
"No assertions in test case './succeeding/exceptions/implicit'",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
randomOutput = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testNoAssertionsWithOutput(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "",
|
||||
"No assertions in section 'one'",
|
||||
"",
|
||||
"Message from section two",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
randomOutput = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testFailedButOk(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MessageTests.cpp:<line number>:",
|
||||
"FAILED - but was ok:",
|
||||
" CHECK_NOFAIL( 1 == 2 )",
|
||||
"",
|
||||
"",
|
||||
"No assertions in test case './succeeding/nofail'",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
randomOutput = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMultiLineExpansion(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "MiscTests.cpp:<line number>:",
|
||||
"PASSED:",
|
||||
" CHECK_THAT( testStringForMatching() AllOf( Catch::Contains( \"string\" ), Catch::Contains( \"abc\" ) ) )",
|
||||
"with expansion:",
|
||||
" \"this string contains 'abc' as a substring\" ( contains: \"string\" and",
|
||||
" contains: \"abc\" )",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
randomOutput = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMultiLineExpansionWithWrap(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "TestMain.cpp:<line number>:",
|
||||
"PASSED:",
|
||||
" CHECK( text.toString() == \" one two\n three\n four\" )",
|
||||
"with expansion:",
|
||||
" \" one two",
|
||||
" three",
|
||||
" four\"",
|
||||
" ==",
|
||||
" \" one two",
|
||||
" three",
|
||||
" four\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
randomOutput = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testMultiLineExpansionWithTruncation(self):
|
||||
obj = TestConditionApprovedParser()
|
||||
lines = [ "TestMain.cpp:<line number>:",
|
||||
"PASSED:",
|
||||
" CHECK_THAT( t.toString() EndsWith( \"... message truncated due to excessive size\" ) )",
|
||||
"with expansion:",
|
||||
" \"***************************************************************************-",
|
||||
" ***-",
|
||||
" ****************************************************************************-",
|
||||
" **-",
|
||||
"... message truncated due to excessive size",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testBasicResultsParser(self):
|
||||
obj = TestConditionResultParser()
|
||||
lines = [ "..\..\..\SelfTest\ClassTests.cpp(28): FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseResultLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateResultLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testBasicResultsWarning(self):
|
||||
obj = TestConditionResultParser()
|
||||
lines = [ "..\..\..\SelfTest\MessageTests.cpp(17): ",
|
||||
"warning:",
|
||||
" this is a warning",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseResultLine(line)
|
||||
if isinstance(result, TestConditionData):
|
||||
#print result
|
||||
newLines += result.generateResultLines()
|
||||
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
#print lines
|
||||
#print newLines
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
341
scripts/test_test_case.py
Normal file
341
scripts/test_test_case.py
Normal file
@ -0,0 +1,341 @@
|
||||
import unittest
|
||||
|
||||
from catch_test_case import TestCaseApprovedParser
|
||||
from catch_test_case import TestCaseResultParser
|
||||
from catch_test_case import TestCaseData
|
||||
from catch_conditions import TestConditionData
|
||||
|
||||
class TestCaseTest(unittest.TestCase):
|
||||
|
||||
def testTestCaseEquality(self):
|
||||
c1 = TestConditionData()
|
||||
c2 = TestConditionData()
|
||||
c1.filenamePrefix = "..\\..\\Test"
|
||||
c2.filenamePrefix = "..\\..\\Junk"
|
||||
t1 = TestCaseData()
|
||||
t2 = TestCaseData()
|
||||
t1.name = "Test 1"
|
||||
t2.name = "Test 1"
|
||||
t1.conditions.append(c1)
|
||||
t1.conditions.append(c2)
|
||||
t2.conditions.append(c1)
|
||||
t2.conditions.append(c2)
|
||||
self.assertTrue(t1 == t2)
|
||||
|
||||
c3 = TestConditionData()
|
||||
c3.filenamePrefix = "..\\..\\Fail"
|
||||
t2.conditions.append(c3)
|
||||
self.assertFalse(t1 == t2)
|
||||
|
||||
t1.conditions.append(c3)
|
||||
self.assertTrue(t1 == t2)
|
||||
|
||||
t2.name = "Test 2"
|
||||
self.assertFalse(t1 == t2)
|
||||
|
||||
def testEndOfTestCaseIsFound(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
line = "-------------------------------------------------------------------------------"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(obj.current.empty())
|
||||
|
||||
def testTestCaseNameIsFound(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------" ]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(obj.current.name == "./failing/TestClass/failingCase")
|
||||
self.assertTrue( not(obj.current.empty()) )
|
||||
|
||||
def testTestCaseClassIsFound(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"..............................................................................." ]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(obj.current.filename == "ClassTests.cpp")
|
||||
self.assertTrue(obj.current.lineNumber == "line number")
|
||||
|
||||
def testPartialConditionRequiresMoreData(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"ClassTests.cpp:<line number>: FAILED:" ]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(len(obj.current.conditions) == 0)
|
||||
|
||||
def testTestCaseConditionIsFound(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\""]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(not(obj.conditionParser.current.empty()))
|
||||
self.assertTrue(obj.conditionParser.current.reason == "FAILED")
|
||||
|
||||
def testTestCaseConditionIsInsertedIntoList(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
|
||||
self.assertTrue(isinstance(result, TestCaseData))
|
||||
self.assertTrue(len(result.conditions) > 0)
|
||||
self.assertTrue(result.conditions[0].filename == "ClassTests.cpp" )
|
||||
self.assertTrue(result.conditions[0].lineNumber == "line number" )
|
||||
self.assertTrue(result.conditions[0].reason == "FAILED" )
|
||||
newLines = result.generateApprovedLines()
|
||||
newLines.append("-------------------------------------------------------------------------------")
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testTwoTestCases(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/Fixture/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( m_a == 2 )",
|
||||
"with expansion:",
|
||||
" 1 == 2",
|
||||
"",
|
||||
"==============================================================================="
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestCaseData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("===============================================================================")
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testTestCaseMultiConditionMatches(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/conditions/equality",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ConditionTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.int_seven == 6 )",
|
||||
"with expansion:",
|
||||
" 7 == 6",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.int_seven == 8 )",
|
||||
"with expansion:",
|
||||
" 7 == 8",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.int_seven == 0 )",
|
||||
"with expansion:",
|
||||
" 7 == 0",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.float_nine_point_one == Approx( 9.11f ) )",
|
||||
"with expansion:",
|
||||
" 9.1 == Approx( 9.11 )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.float_nine_point_one == Approx( 9.0f ) )",
|
||||
"with expansion:",
|
||||
" 9.1 == Approx( 9 )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.float_nine_point_one == Approx( 1 ) )",
|
||||
"with expansion:",
|
||||
" 9.1 == Approx( 1 )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.float_nine_point_one == Approx( 0 ) )",
|
||||
"with expansion:",
|
||||
" 9.1 == Approx( 0 )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.double_pi == Approx( 3.1415 ) )",
|
||||
"with expansion:",
|
||||
" 3.1415926535 == Approx( 3.1415 )",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.str_hello == \"goodbye\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"goodbye\"",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.str_hello == \"hell\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"hell\"",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.str_hello == \"hello1\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"hello1\"",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( data.str_hello.size() == 6 )",
|
||||
"with expansion:",
|
||||
" 5 == 6",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>: FAILED:",
|
||||
" CHECK( x == Approx( 1.301 ) )",
|
||||
"with expansion:",
|
||||
" 1.3 == Approx( 1.301 )",
|
||||
"",
|
||||
"==============================================================================="
|
||||
]
|
||||
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
|
||||
self.assertTrue(isinstance(result, TestCaseData))
|
||||
newLines = result.generateApprovedLines()
|
||||
newLines.append("===============================================================================")
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testOneSection(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/message/sections",
|
||||
" one",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"MessageTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"MessageTests.cpp:<line number>: FAILED:",
|
||||
"explicitly with message:",
|
||||
" Message from section one",
|
||||
"",
|
||||
"==============================================================================="
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestCaseData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("===============================================================================")
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testOneSection(self):
|
||||
obj = TestCaseApprovedParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"Comparisons between unsigned ints and negative signed ints match c++ standard",
|
||||
"behaviour",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ConditionTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>:",
|
||||
"PASSED:",
|
||||
" CHECK( ( -1 > 2u ) )",
|
||||
"with expansion:",
|
||||
" true",
|
||||
"",
|
||||
"ConditionTests.cpp:<line number>:",
|
||||
"PASSED:",
|
||||
" CHECK( -1 > 2u )",
|
||||
"with expansion:",
|
||||
" -1 > 2",
|
||||
"",
|
||||
"==============================================================================="
|
||||
]
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestCaseData):
|
||||
newLines += result.generateApprovedLines()
|
||||
|
||||
newLines.append("===============================================================================")
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testCaseBasicResults(self):
|
||||
obj = TestCaseResultParser()
|
||||
lines = [ "-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"..\..\..\SelfTest\ClassTests.cpp(34)",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"..\..\..\SelfTest\ClassTests.cpp(28): FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"==============================================================================="
|
||||
]
|
||||
|
||||
newLines = []
|
||||
for line in lines:
|
||||
result = obj.parseResultLine(line)
|
||||
if isinstance(result, TestCaseData):
|
||||
newLines += result.generateResultLines()
|
||||
|
||||
newLines.append("===============================================================================")
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
334
scripts/test_test_run.py
Normal file
334
scripts/test_test_run.py
Normal file
@ -0,0 +1,334 @@
|
||||
import unittest
|
||||
import catch_test_case
|
||||
|
||||
from catch_test_run import TestRunData
|
||||
from catch_test_run import TestRunApprovedParser
|
||||
from catch_test_run import TestRunResultParser
|
||||
from catch_test_case import TestCaseData
|
||||
from catch_conditions import TestConditionData
|
||||
|
||||
class TestCaseTest(unittest.TestCase):
|
||||
|
||||
def testTestRunEquality(self):
|
||||
c1 = TestConditionData()
|
||||
c2 = TestConditionData()
|
||||
c1.filenamePrefix = "..\\..\\Test"
|
||||
c2.filenamePrefix = "..\\..\\Junk"
|
||||
t1 = TestCaseData()
|
||||
t2 = TestCaseData()
|
||||
t1.name = "Test 1"
|
||||
t2.name = "Test 1"
|
||||
t1.conditions.append(c1)
|
||||
t1.conditions.append(c2)
|
||||
t2.conditions.append(c1)
|
||||
t2.conditions.append(c2)
|
||||
r1 = TestRunData()
|
||||
r2 = TestRunData()
|
||||
r1.appname = "One"
|
||||
r2.appname = "One"
|
||||
self.assertTrue(r1 == r2)
|
||||
|
||||
r1.testcases.append(t1)
|
||||
self.assertFalse(r1 == r2)
|
||||
|
||||
r2.testcases.append(t2)
|
||||
self.assertTrue(r1 == r2)
|
||||
|
||||
c3 = TestConditionData()
|
||||
c3.filenamePrefix = "..\\..\\Fail"
|
||||
t2.conditions.append(c3)
|
||||
self.assertFalse(r1 == r2)
|
||||
|
||||
def testStartOfTestRunIsFound(self):
|
||||
obj = TestRunApprovedParser()
|
||||
line = "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"
|
||||
result = obj.parseApprovedLine(line)
|
||||
self.assertTrue(result == None)
|
||||
|
||||
def testTestRunVersionIsSet(self):
|
||||
obj = TestRunApprovedParser()
|
||||
lines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options" ]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
#print obj
|
||||
self.assertTrue(result == None)
|
||||
self.assertTrue(obj.current.appname == "CatchSelfTest")
|
||||
self.assertTrue(obj.current.version == "<version>")
|
||||
|
||||
def testTestRunParsesTestCase(self):
|
||||
obj = TestRunApprovedParser()
|
||||
lines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:"
|
||||
" \"hello\" == \"world\""]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
#print obj
|
||||
self.assertTrue(obj.testcaseParser.conditionParser.current.filename == "ClassTests.cpp" )
|
||||
self.assertTrue(obj.testcaseParser.conditionParser.current.lineNumber == "line number" )
|
||||
self.assertTrue(obj.testcaseParser.conditionParser.current.reason == "FAILED" )
|
||||
|
||||
def testTestRunAddsTestCase(self):
|
||||
obj = TestRunApprovedParser()
|
||||
lines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:"
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------"
|
||||
]
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
#print obj
|
||||
self.assertTrue( result == None )
|
||||
self.assertTrue( len(obj.current.testcases) == 1 )
|
||||
self.assertTrue(obj.current.testcases[0].filename == "ClassTests.cpp" )
|
||||
self.assertTrue(obj.current.testcases[0].lineNumber == "line number" )
|
||||
self.assertTrue( len(obj.current.testcases[0].conditions) == 1 )
|
||||
self.assertTrue(obj.current.testcases[0].conditions[0].filename == "ClassTests.cpp" )
|
||||
self.assertTrue(obj.current.testcases[0].conditions[0].lineNumber == "line number" )
|
||||
self.assertTrue(obj.current.testcases[0].conditions[0].reason == "FAILED" )
|
||||
|
||||
def testTestRunParsesTwoTestCases(self):
|
||||
obj = TestRunApprovedParser()
|
||||
lines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/Fixture/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( m_a == 2 )",
|
||||
"with expansion:",
|
||||
" 1 == 2",
|
||||
"",
|
||||
"===============================================================================",
|
||||
"122 test cases - 35 failed (753 assertions - 90 failed)",
|
||||
""
|
||||
]
|
||||
testRun = None
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestRunData):
|
||||
testRun = result
|
||||
|
||||
self.assertTrue( isinstance(testRun, TestRunData) )
|
||||
newLines = testRun.generateApprovedLines()
|
||||
#for line in newLines:
|
||||
# print "L:",line
|
||||
#print len(lines),",",len(newLines)
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testTestRunWithRandomOutput(self):
|
||||
obj = TestRunApprovedParser()
|
||||
lines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"MiscTests.cpp:<line number>: FAILED:",
|
||||
"explicitly with message:",
|
||||
" to infinity and beyond",
|
||||
"",
|
||||
"Message from section one",
|
||||
"Message from section two",
|
||||
"Some information",
|
||||
"An error",
|
||||
"Message from section one",
|
||||
"Message from section two",
|
||||
"Some information",
|
||||
"An error",
|
||||
"hello",
|
||||
"hello",
|
||||
"===============================================================================",
|
||||
"122 test cases - 35 failed (753 assertions - 90 failed)",
|
||||
""
|
||||
]
|
||||
testRun = None
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestRunData):
|
||||
testRun = result
|
||||
|
||||
self.assertTrue( isinstance(testRun, TestRunData) )
|
||||
#print "O:",result.outputLine
|
||||
self.assertTrue( testRun.outputLine == 14 )
|
||||
newLines = testRun.generateApprovedLines()
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testRunBasicResult(self):
|
||||
obj = TestRunResultParser()
|
||||
lines = [ "Message from section one",
|
||||
"Message from section two",
|
||||
"Some information",
|
||||
"An error",
|
||||
"Message from section one",
|
||||
"Message from section two",
|
||||
"Some information",
|
||||
"An error",
|
||||
"hello",
|
||||
"hello",
|
||||
"",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"TestCatch.exe is a Catch v1.0 b13 host application.",
|
||||
"Run with -? for options",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"..\..\..\SelfTest\ClassTests.cpp(34)",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"..\..\..\SelfTest\ClassTests.cpp(28): FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"===============================================================================",
|
||||
"122 test cases - 35 failed (753 assertions - 90 failed)",
|
||||
""
|
||||
]
|
||||
|
||||
testRun = None
|
||||
for line in lines:
|
||||
result = obj.parseResultLine(line)
|
||||
if isinstance(result, TestRunData):
|
||||
testRun = result
|
||||
|
||||
self.assertTrue( isinstance(testRun, TestRunData) )
|
||||
#print "O:",testRun.outputLine
|
||||
self.assertTrue( testRun.outputLine == 0 )
|
||||
newLines = testRun.generateResultLines()
|
||||
#for line in newLines:
|
||||
# print line
|
||||
self.assertTrue( len(lines) == len(newLines) )
|
||||
self.assertTrue( lines == newLines )
|
||||
|
||||
def testTestRunSorted(self):
|
||||
obj = TestRunApprovedParser()
|
||||
lines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/Fixture/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( m_a == 2 )",
|
||||
"with expansion:",
|
||||
" 1 == 2",
|
||||
"",
|
||||
"===============================================================================",
|
||||
"122 test cases - 35 failed (753 assertions - 90 failed)",
|
||||
""
|
||||
]
|
||||
testRun = None
|
||||
for line in lines:
|
||||
result = obj.parseApprovedLine(line)
|
||||
if isinstance(result, TestRunData):
|
||||
testRun = result
|
||||
|
||||
self.assertTrue( isinstance(testRun, TestRunData) )
|
||||
newLines = testRun.generateSortedApprovedLines()
|
||||
#for line in newLines:
|
||||
# print "L:",line
|
||||
#print len(lines),",",len(newLines)
|
||||
expectedLines = [ "",
|
||||
"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~",
|
||||
"CatchSelfTest is a <version> host application.",
|
||||
"Run with -? for options",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/Fixture/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( m_a == 2 )",
|
||||
"with expansion:",
|
||||
" 1 == 2",
|
||||
"",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"./failing/TestClass/failingCase",
|
||||
"-------------------------------------------------------------------------------",
|
||||
"ClassTests.cpp:<line number>",
|
||||
"...............................................................................",
|
||||
"",
|
||||
"ClassTests.cpp:<line number>: FAILED:",
|
||||
" REQUIRE( s == \"world\" )",
|
||||
"with expansion:",
|
||||
" \"hello\" == \"world\"",
|
||||
"",
|
||||
"===============================================================================",
|
||||
"122 test cases - 35 failed (753 assertions - 90 failed)",
|
||||
""
|
||||
]
|
||||
self.assertTrue( len(expectedLines) == len(newLines) )
|
||||
self.assertTrue( expectedLines == newLines )
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
Loading…
Reference in New Issue
Block a user