[Cppunit-cvs] cppunit2/src/cpput SConscript, 1.11, 1.12 testcase.cpp, 1.16, 1.17 testinfo.cpp, 1.22
Brought to you by:
blep
From: Baptiste L. <bl...@us...> - 2008-07-13 08:19:24
|
Update of /cvsroot/cppunit/cppunit2/src/cpput In directory sc8-pr-cvs4.sourceforge.net:/tmp/cvs-serv16552/src/cpput Modified Files: SConscript testcase.cpp testinfo.cpp Log Message: - Added core framework for resource handling to test case, resource registry and test info. Not integrated with the test runner and no unit tests yet. Index: SConscript =================================================================== RCS file: /cvsroot/cppunit/cppunit2/src/cpput/SConscript,v retrieving revision 1.11 retrieving revision 1.12 diff -C2 -d -r1.11 -r1.12 *** SConscript 2 Sep 2006 11:24:53 -0000 1.11 --- SConscript 13 Jul 2008 08:19:20 -0000 1.12 *************** *** 9,12 **** --- 9,13 ---- message.cpp registry.cpp + resource.cpp testcase.cpp testinfo.cpp Index: testinfo.cpp =================================================================== RCS file: /cvsroot/cppunit/cppunit2/src/cpput/testinfo.cpp,v retrieving revision 1.22 retrieving revision 1.23 diff -C2 -d -r1.22 -r1.23 *** testinfo.cpp 14 Aug 2007 17:30:52 -0000 1.22 --- testinfo.cpp 13 Jul 2008 08:19:20 -0000 1.23 *************** *** 1,3 **** --- 1,4 ---- #include <cpput/testinfo.h> + #include <cpput/resource.h> #include <cpptl/stringtools.h> #include <cpptl/thread.h> *************** *** 299,302 **** --- 300,352 ---- testStatus_ = TestStatus( TestStatus::passed ); assertionType_ = abortingAssertion; + resources_.clear(); + } + + + void + TestInfo::addResource( const AcquiredResourceHandlePtr &resource ) + { + resources_.insert( Resources::value_type( resource->name(), resource ) ); + } + + void + TestInfo::discardTestResources() + { + Resources resources; + resources.swap( resources_ ); // releases resource once exiting this function + + // tear down each resource + Resources::iterator itEnd = resources.end(); + for ( Resources::iterator it = resources.begin(); it != itEnd; ++it ) + { + AcquiredResourceHandlePtr &resource = it->second; + try + { + // Assertions are allowed in tearDown Ignore them as they have + // already been handled. + resource->tearDown(); + } + catch ( const AbortingAssertionException & ) + { + } + catch ( const SkipTestException & ) + { + } + } + } + + + Resource & + TestInfo::getResource( const ResourceName &name ) + { + Resources::iterator it = resources_.find( name ); + if ( it == resources_.end() ) + { + // @todo check that resource name is correctly reported in failure message + testStatus_.setStatus( TestStatus::failed ); + throw UndeclaredResourceException( name.c_str() ); + } + AcquiredResourceHandlePtr &resource = it->second; + return resource->resource(); } *************** *** 442,445 **** --- 492,500 ---- // ////////////////////////////////////////////////////////////////// + Resource &getResource( const ResourceName &name ) + { + return TestInfo::threadInstance().getResource( name ); + } + void log( const Json::Value &log ) Index: testcase.cpp =================================================================== RCS file: /cvsroot/cppunit/cppunit2/src/cpput/testcase.cpp,v retrieving revision 1.16 retrieving revision 1.17 diff -C2 -d -r1.16 -r1.17 *** testcase.cpp 15 Aug 2007 11:20:57 -0000 1.16 --- testcase.cpp 13 Jul 2008 08:19:20 -0000 1.17 *************** *** 1,7 **** #include <cpput/testcase.h> #include <cpput/assertcommon.h> #include <cpptl/functor.h> #include <cpput/message.h> ! #include <cpput/exceptionguard.h> #include <cpput/testvisitor.h> --- 1,8 ---- #include <cpput/testcase.h> #include <cpput/assertcommon.h> + #include <cpput/exceptionguard.h> #include <cpptl/functor.h> #include <cpput/message.h> ! #include <cpput/resource.h> #include <cpput/testvisitor.h> *************** *** 42,58 **** } bool AbstractTestCase::runTest( const ExceptionGuard &guardsChain ) { ! TestInfo::threadInstance().startNewTest(); ! bool initialized = guardsChain.protect( CppTL::memfn0( this, ! &AbstractTestCase::setUp ) ); ! if ( initialized ) { ! guardsChain.protect( CppTL::memfn0( this, &AbstractTestCase::run ) ); ! guardsChain.protect( CppTL::memfn0( this, &AbstractTestCase::tearDown) ); } return !TestInfo::threadInstance().testStatus().hasFailed(); } --- 43,75 ---- } + bool AbstractTestCase::runTest( const ExceptionGuard &guardsChain ) { ! TestInfo &testInfo = TestInfo::threadInstance(); ! testInfo.startNewTest(); ! // Protect resource acquisition in the of a resource constructor ! // throw an exception. ! bool allResourceAcquired = false; ! bool resourceAcquired = guardsChain.protect( ! CppTL::bind( ! CppTL::memfn1( this, &AbstractTestCase::acquireTestResources ), ! CppTL::ref( allResourceAcquired ) ) ); ! if ( resourceAcquired ) { ! bool initialized = guardsChain.protect( ! CppTL::memfn0( this, &AbstractTestCase::setUp ) ); ! ! if ( initialized ) ! { ! guardsChain.protect( CppTL::memfn0( this, &AbstractTestCase::run ) ); ! guardsChain.protect( CppTL::memfn0( this, &AbstractTestCase::tearDown) ); ! } } + // Tear down and releases resources "allocated" for the test. + testInfo.discardTestResources(); + return !TestInfo::threadInstance().testStatus().hasFailed(); } *************** *** 71,74 **** --- 88,151 ---- + void + AbstractTestCase::requireResource( const std::string &resourceName ) + { + resourceNames_.insert( resourceName ); + } + + + void + AbstractTestCase::prepareResourceAcquisition() + { + requiredResources_.clear(); + requiredResources_.reserve( resourceNames_.size() ); + + // For each required resource, we obtain a lazy reference on the resource. + // This does not instantiate the resource but indicates future usage of the + // resource. This is used to allow destruction of the resource as soon as + // all tests requiring it have been executed. + ResourceHandlerRegistry ®istry = ResourceHandlerRegistry::instance(); + ResourceNames::iterator itEnd = resourceNames_.end(); + for ( ResourceNames::iterator it = resourceNames_.begin(); + it != itEnd; + ++it ) + { + const ResourceName &resourceName = *it; + ResourceLazyPtr resource = registry.getResource( resourceName ); + requiredResources_.push_back( resource ); + } + } + + + void + AbstractTestCase::acquireTestResources( bool &allResourceAcquired ) + { + // Notes that the resources are acquired in the order they are stored in the map, + // that is, in the order of the resource name. + // This is important to ensure that multiple resources acquisition is always done + // in the same order to avoid dead-lock when resources are acquired concurrently. + TestInfo &testInfo = TestInfo::threadInstance(); + RequiredResources::iterator itEnd = requiredResources_.end(); + for ( RequiredResources::iterator it = requiredResources_.begin(); + it != itEnd; + ++it ) + { + ResourceLazyPtr &resourceRef = *it; + // Obtains a reference on an actual instance of the resource. + // The resource is instantiated if required. + // Notes: resource constructor may throw an exception. + AcquiredResourceHandlePtr resource = resourceRef.acquire(); + if ( !resource ) + { + allResourceAcquired = false; + return; // No resource handler defined for the resource + } + testInfo.addResource( resource ); + resource->setUp(); + } + allResourceAcquired = true; + } + + // Class TestCase |