43 #ifndef BOOST_TEST_NO_LIB
44 # define BOOST_TEST_NO_LIB
46 #define BOOST_TEST_NO_MAIN
47 #if defined(__FreeBSD_cc_version) && !defined(__FreeBSD_version)
48 # define __FreeBSD_version __FreeBSD_cc_version
52 #include <boost/preprocessor/cat.hpp>
53 #include <boost/preprocessor/tuple/elem.hpp>
54 #include <boost/preprocessor/tuple/eat.hpp>
62 #ifdef NCBI_COMPILER_MSVC
63 # pragma warning(push)
65 # pragma warning(disable: 4265)
67 # pragma warning(disable: 4191)
72 #if __cplusplus > 201703L
73 # include <boost/version.hpp>
74 # if BOOST_VERSION < 107300
76 ostream&
operator<<(ostream& os,
const wchar_t* ws)
78 return os << ncbi::CUtf8::AsUTF8(ws);
83 #include <boost/test/included/unit_test.hpp>
84 #include <boost/test/results_collector.hpp>
85 #include <boost/test/results_reporter.hpp>
86 #include <boost/test/unit_test_log.hpp>
87 #include <boost/test/unit_test_log_formatter.hpp>
88 #include <boost/test/output/plain_report_formatter.hpp>
89 #include <boost/test/output/xml_report_formatter.hpp>
90 #include <boost/test/output/compiler_log_formatter.hpp>
91 #include <boost/test/output/xml_log_formatter.hpp>
92 #include <boost/test/utils/xml_printer.hpp>
93 #include <boost/test/detail/global_typedef.hpp>
94 #include <boost/test/debug.hpp>
96 #if BOOST_VERSION >= 105900
97 # include <boost/test/tree/observer.hpp>
98 # include <boost/test/unit_test_parameters.hpp>
99 # define IGNORE_STATUS , true
101 # include <boost/test/test_observer.hpp>
102 # include <boost/test/detail/unit_test_parameters.hpp>
104 # define TUT_CASE tut_case
105 # define TUT_SUITE tut_suite
106 # define IGNORE_STATUS
109 #if BOOST_VERSION >= 106000
110 # define attr_value utils::attr_value
111 # if BOOST_VERSION >= 106400
113 # define RTCFG(type, new_name, old_name) \
114 but::runtime_config::get<type >(but::runtime_config::btrt_##old_name)
115 # define CONFIGURED_FILTERS RTCFG(std::vector<std::string>, _, run_filters)
117 # define RTCFG(type, new_name, old_name) \
118 but::runtime_config::get<type >(but::runtime_config::new_name)
121 # define RTCFG(type, new_name, old_name) but::runtime_config::old_name()
122 # if BOOST_VERSION >= 105900
123 # define BOOST_TEST_I_TRY BOOST_TEST_IMPL_TRY
124 # define BOOST_TEST_I_CATCH BOOST_TEST_IMPL_CATCH
125 # define BOOST_TEST_I_CATCH0 BOOST_TEST_IMPL_CATCH0
126 # define BOOST_TEST_I_CATCHALL BOOST_TEST_IMPL_CATCHALL
128 # define BOOST_TEST_I_TRY try
129 # define BOOST_TEST_I_CATCH(type, ex) catch (type const& ex)
130 # define BOOST_TEST_I_CATCH0(type) catch (type const&)
131 # define BOOST_TEST_I_CATCHALL() catch (...)
135 #ifndef CONFIGURED_FILTERS
136 #define CONFIGURED_FILTERS \
137 RTCFG(std::vector<std::string>, RUN_FILTERS, test_to_run)
140 #ifdef NCBI_COMPILER_MSVC
141 # pragma warning(pop)
151 #define NCBI_USE_ERRCODE_X Corelib_TestBoost
154 namespace but = boost::unit_test;
159 #ifdef SYSTEM_MUTEX_INITIALIZER
165 #if BOOST_VERSION >= 105900
167 static bool s_IsEnabled(
const but::test_unit& tu) {
168 return tu.is_enabled();
172 static void s_SetEnabled(but::test_unit& tu,
bool enabled) {
173 but::test_unit::run_status rs
174 = enabled ? but::test_unit::RS_ENABLED : but::test_unit::RS_DISABLED;
175 tu.p_default_status.set(rs);
176 tu.p_run_status.set(rs);
186 tu.p_enabled.set(enabled);
195 #define DUMMY_TEST_FUNCTION_NAME DummyTestFunction
260 virtual void log_start(ostream& ostr, but::counter_t test_cases_amount);
262 #if BOOST_VERSION >= 107000
268 virtual void test_unit_finish(ostream& ostr, but::test_unit
const& tu,
unsigned long elapsed);
270 #if BOOST_VERSION >= 105900
271 virtual void log_exception_start(ostream& ostr, but::log_checkpoint_data
const& lcd, boost::execution_exception
const& ex);
272 virtual void log_exception_finish(ostream& ostr);
273 #elif BOOST_VERSION >= 104200
274 virtual void log_exception(ostream& ostr, but::log_checkpoint_data
const& lcd, boost::execution_exception
const& ex);
276 using TBoostLogFormatter::log_exception;
278 virtual void log_exception(ostream& ostr, but::log_checkpoint_data
const& lcd, but::const_string explanation);
280 virtual void log_entry_start(ostream& ostr, but::log_entry_data
const& led, log_entry_types let);
283 using TBoostLogFormatter::log_entry_value;
286 #if BOOST_VERSION >= 105900
287 virtual void entry_context_start(ostream& ostr, but::log_level
l);
288 # if BOOST_VERSION >= 106500
289 virtual void log_entry_context(ostream& os, but::log_level
l, but::const_string v);
290 virtual void entry_context_finish(ostream& os, but::log_level
l);
292 virtual void log_entry_context(ostream& ostr, but::const_string
value);
293 virtual void entry_context_finish (ostream& ostr);
322 virtual void test_unit_finish(but::test_unit
const& tu,
unsigned long elapsed);
330 #if BOOST_VERSION >= 105900
344 virtual void visit (but::test_case
const&
test );
431 virtual void visit (but::test_case
const&
test );
442 void EnsureDep(but::test_unit* tu, but::test_unit* tu_from);
472 virtual void Init (
void);
473 virtual int Run (
void);
651 m_Upper =
new but::output::xml_report_formatter();
655 m_Upper =
new but::output::plain_report_formatter();
669 m_Upper =
new but::output::xml_log_formatter();
673 m_Upper =
new but::output::compiler_log_formatter();
681 m_OrderChanged(
false)
703 for (; idx_left <
m_Children.size(); ++ idx_left) {
709 if (idx_left < idx_right)
729 if (elem == leftElem) {
731 FORMAT(
"Circular dependency found: '"
733 <<
"' must depend on itself."));
746 if (elem == rightElem) {
748 FORMAT(
"Circular dependency found: '"
750 <<
"' must depend on itself."));
766 size_t idx_right = 0;
767 for (; idx_right <
m_Children.size(); ++idx_right) {
786 parents.push_back(parElem);
789 while (parElem !=
NULL);
794 TElemsList::iterator it = find(parents.begin(), parents.end(), parElem);
795 if (it != parents.end()) {
801 while (parElem !=
NULL);
804 if (parElem ==
this) {
806 FORMAT(
"Error in unit tests setup: dependency of '"
809 <<
"' can never be implemented."));
813 while (toElem->
m_Parent != parElem) {
824 but::test_suite* suite =
static_cast<but::test_suite*
>(
m_TestUnit);
826 suite->remove((*it)->m_TestUnit->p_id);
829 suite->add((*it)->m_TestUnit);
834 (*it)->FixUnitsOrder();
838 inline but::test_unit*
863 but::test_suite* nc_suite =
const_cast<but::test_suite*
>(&suite);
887 but::test_case* nc_test =
const_cast<but::test_case*
>(&
test);
939 : m_RunCalled(
false),
945 m_HasTestErrors(
false),
946 m_HasTestTimeouts(
false)
955 but::results_reporter::set_stream(cerr);
973 "Print test framework related command line arguments");
974 #ifndef NCBI_COMPILER_WORKSHOP
976 "Allows to filter which test units to run",
980 "Do not actually run tests, just print list of all available tests.");
999 but::results_reporter::set_level(but::DETAILED_REPORT);
1036 inline but::test_case*
1054 new_name = new_name.substr(pos + 2);
1057 new_name = new_name.substr(5);
1060 new_name = new_name.substr(4);
1080 <<
"' - renamed to '" <<
test_name <<
"'");
1095 but::test_unit*
test = it->first;
1097 but::test_unit* dep_test = *dep_it;
1107 #if BOOST_VERSION >= 105900
1109 auto master_id = but::framework::master_test_suite().p_id;
1110 auto&
state = but::framework::impl::s_frk_state();
1111 state.finalize_default_run_status(master_id, but::test_unit::RS_INVALID);
1112 state.deduce_run_status(master_id);
1115 but::test_unit*
test = it->first;
1120 but::test_unit* dep_test = *dep_it;
1124 test->depends_on(dep_test);
1133 #define IS_FLAG_DEFINED(flag) \
1134 BOOST_PP_TUPLE_ELEM(2, 1, IS_FLAG_DEFINED_I(BOOST_PP_CAT(NCBI_, flag)))
1135 #define IS_VAR_DEFINED(var) \
1136 BOOST_PP_TUPLE_ELEM(2, 1, IS_FLAG_DEFINED_I(var))
1137 #define IS_FLAG_DEFINED_I(flag) \
1138 (BOOST_PP_CAT(IS_FLAG_DEFINED_II_, flag) (), false)
1139 #define IS_FLAG_DEFINED_II_() \
1140 BOOST_PP_NIL, true) BOOST_PP_TUPLE_EAT(2) (BOOST_PP_NIL
1141 #define IS_FLAG_DEFINED_II_1() \
1142 BOOST_PP_NIL, true) BOOST_PP_TUPLE_EAT(2) (BOOST_PP_NIL
1180 "in_house_resources",
1192 "Boost_Test_Included",
1315 if (features_str.empty()) {
1319 list<string> features_list;
1325 ITERATE(list<string>, it, features_list) {
1331 if (!
isalnum((
unsigned char)(*fit))) {
1341 string name(
"FEATURE_");
1344 bool found = (it != features.end());
1371 but::results_collector.test_unit_aborted(*
s_GetTestApp().GetDummyTest());
1383 printf(
"All tests are disabled in current configuration.\n"
1384 " (for autobuild scripts: NCBI_UNITTEST_DISABLED)\n");
1395 printf(
"Tests cannot be executed in current configuration and will be skipped.\n"
1396 " (for autobuild scripts: NCBI_UNITTEST_SKIPPED)\n");
1404 but::framework::master_test_suite().add(
m_DummyTest);
1417 list<string> reg_entries;
1421 ITERATE(list<string>, it, reg_entries) {
1442 reg_entries.clear();
1445 ITERATE(list<string>, it, reg_entries) {
1460 reg_entries.clear();
1463 ITERATE(list<string>, it, reg_entries) {
1469 list<CTempString> koef_lst;
1471 ITERATE(list<CTempString>, it_koef, koef_lst) {
1476 tu->p_timeout.set(
Uint4(tu->p_timeout.get() * koef));
1481 ERR_POST_X(6,
"Bad format of TIMEOUT_MULT string: '" << reg_value <<
"'");
1497 but::test_unit* tu = it->second;
1585 printf(
"Maximum execution time of %s seconds is exceeded",
m_TimeoutStr.c_str());
1586 #if BOOST_VERSION < 105900
1587 throw but::test_being_aborted();
1588 #elif defined(SIGALRM)
1591 throw runtime_error(
"Maximum execution time of " +
m_TimeoutStr +
" seconds is exceeded");
1597 tu->p_timeout.set(new_timeout);
1605 const but::test_results& tr = but::results_collector.results(tu->p_id);
1613 else if (tr.p_aborted)
1615 else if (tr.p_assertions_failed.get() > tr.p_expected_failures.get() ||
1616 tr.p_test_cases_failed.get() + tr.p_test_cases_aborted.get() > 0) {
1621 else if( tr.passed() )
1634 but::test_unit* tu = it->second;
1651 if (!but::results_collector.
results((*it)->p_id).passed())
1666 but::output_format
format =
RTCFG(but::output_format, REPORT_FORMAT,
1670 string is_autobuild =
env.Get(
"NCBI_AUTOMATED_BUILD");
1671 if (! is_autobuild.empty()) {
1676 but::results_reporter::set_level(but::DETAILED_REPORT);
1678 string boost_rep =
env.Get(
"NCBI_BOOST_REPORT_FILE");
1679 if (! boost_rep.empty()) {
1685 ERR_POST(
"Error opening Boost.Test report file '" << boost_rep <<
"'");
1691 but::results_reporter::set_format(
m_Reporter);
1694 but::unit_test_log.set_formatter(
m_Logger);
1700 switch (func_type) {
1702 return "NCBITEST_AUTO_INIT()";
1704 return "NCBITEST_AUTO_FINI()";
1706 return "NCBITEST_INIT_CMDLINE()";
1708 return "NCBITEST_INIT_VARIABLES()";
1710 return "NCBITEST_INIT_TREE()";
1728 catch (exception& e) {
1737 inline but::test_unit*
1743 "Test unit '" + (
string)
test_name +
"' not found.");
1753 but::traverse_test_tree(but::framework::master_test_suite(), collector
IGNORE_STATUS);
1759 but::test_case_counter tcc;
1760 but::traverse_test_tree(but::framework::master_test_suite(), tcc
IGNORE_STATUS);
1761 return (
int)tcc.p_count;
1768 boost::debug::detect_memory_leaks(
false);
1769 boost::debug::break_memory_alloc(0);
1772 but::framework::register_observer(
m_Observer);
1775 for (
int i = 1;
i < argc; ++
i) {
1778 but::results_reporter::set_level(but::DETAILED_REPORT);
1780 for (
int j =
i + 1; j < argc; ++j) {
1781 argv[j - 1] = argv[j];
1814 #if BOOST_VERSION <= 105900
1821 #ifdef NCBI_COMPILER_WORKSHOP
1823 printf(
"Parameter --run_test is not supported in current configuration\n");
1863 return but::results_reporter::get_stream();
1895 unsigned long timeout = tu.p_timeout.get();
1897 if (timeout != 0 && timeout < elapsed / 1000000) {
1898 boost::execution_exception ex(
1899 boost::execution_exception::timeout_error,
"Timeout exceeded"
1901 but::framework::exception_caught(ex);
1904 but::test_results& tr = but::s_rc_impl().m_results_store[tu.p_id];
1906 static_cast<but::readwrite_property<bool>&
>(
1907 static_cast<but::class_property<bool>&
>(tr.p_skipped)).set(
true);
1908 static_cast<but::readwrite_property<but::counter_t>&
>(
1909 static_cast<but::class_property<but::counter_t>&
>(tr.p_assertions_failed)).set(0);
1916 if (ex.code() == boost::execution_exception::timeout_error) {
1918 &but::framework::current_test_case()));
1922 &but::framework::current_test_case()));
1932 #if BOOST_VERSION >= 105900
1935 if (ar == but::AR_FAILED) {
1957 m_Upper->results_report_start(ostr);
1963 m_Upper->results_report_finish(ostr);
1979 ostr <<
'<' << (tu.p_type ==
but::TUT_CASE ?
"TestCase" :
"TestSuite")
1980 <<
" name" << but::attr_value() << tu.p_name.get()
1981 <<
" result" << but::attr_value() << descr;
1985 ostr << std::setw( m_Indent ) << ""
1986 << "Test " << (tu.p_type == but::TUT_CASE ? "case " : "suite " )
1987 << "\"" << tu.p_name << "\" " << descr;
1994 CNcbiBoostReporter::test_unit_report_finish(but::test_unit const& tu, std::ostream& ostr)
1996 if (tu.p_name.get() == kDummyTestCaseName) {
2000 m_Upper->test_unit_report_finish(tu, ostr);
2004 CNcbiBoostReporter::do_confirmation_report(but::test_unit const& tu, std::ostream& ostr)
2006 #if BOOST_VERSION >= 105900
2007 if (tu.p_type == but::TUT_SUITE && tu.p_line_num == 0) {
2008 but::test_results const& tr = but::results_collector.results(tu.p_id);
2011 if (tr.p_test_cases_skipped > 0) {
2012 ostr << "*** Skipped " << tr.p_test_cases_skipped << " test(s)\n";
2013 } else if (tr.p_skipped) {
2014 ostr << "*** Skipped some tests\n";
2017 // Boost.Test 3.x (from Boost 1.59+) treats skipped tests as errors.
2018 // Override that treatment both here (to avoid a claim that errors
2019 // occurred) and in main (to yield a sane exit code regardless of
2021 const_cast<bool&>(tr.p_skipped.get()) = false;
2022 const_cast<but::counter_t&>(tr.p_test_cases_skipped.get()) = 0;
2025 m_Upper->do_confirmation_report(tu, ostr);
2030 CNcbiBoostLogger::log_start(ostream& ostr, but::counter_t test_cases_amount)
2032 m_Upper->log_start(ostr, test_cases_amount);
2036 CNcbiBoostLogger::log_finish(ostream& ostr)
2038 m_Upper->log_finish(ostr);
2040 ostr << "Executed " << s_GetTestApp().GetRanTestsCount() << " test cases";
2041 int to_fix = s_GetTestApp().GetToFixTestsCount();
2043 ostr << " (" << to_fix << " to fix)";
2045 ostr << "." << endl;
2049 #if BOOST_VERSION >= 107000
2051 CNcbiBoostLogger::log_build_info(ostream& ostr, bool log_build_info)
2053 m_Upper->log_build_info(ostr, log_build_info);
2057 CNcbiBoostLogger::log_build_info(ostream& ostr)
2059 m_Upper->log_build_info(ostr);
2064 CNcbiBoostLogger::test_unit_start(ostream& ostr, but::test_unit const& tu)
2066 m_Upper->test_unit_start(ostr, tu);
2070 CNcbiBoostLogger::test_unit_finish(ostream& ostr, but::test_unit const& tu,
2071 unsigned long elapsed)
2073 m_Upper->test_unit_finish(ostr, tu, elapsed);
2077 CNcbiBoostLogger::test_unit_skipped(ostream& ostr, but::test_unit const& tu)
2079 m_Upper->test_unit_skipped(ostr, tu);
2082 #if BOOST_VERSION >= 105900
2084 CNcbiBoostLogger::log_exception_start(ostream& ostr,
2085 but::log_checkpoint_data const& lcd,
2086 boost::execution_exception const& ex)
2088 m_Upper->log_exception_start(ostr, lcd, ex);
2092 CNcbiBoostLogger::log_exception_finish(ostream& ostr)
2094 m_Upper->log_exception_finish(ostr);
2096 #elif BOOST_VERSION >= 104200
2098 CNcbiBoostLogger::log_exception(ostream& ostr, but::log_checkpoint_data const& lcd,
2099 boost::execution_exception const& ex)
2101 m_Upper->log_exception(ostr, lcd, ex);
2105 CNcbiBoostLogger::log_exception(ostream& ostr, but::log_checkpoint_data const& lcd,
2106 but::const_string explanation)
2108 m_Upper->log_exception(ostr, lcd, explanation);
2113 CNcbiBoostLogger::log_entry_start(ostream& ostr, but::log_entry_data const& led, log_entry_types let)
2115 m_Upper->log_entry_start(ostr, led, let);
2119 CNcbiBoostLogger::log_entry_value(ostream& ostr, but::const_string value)
2121 m_Upper->log_entry_value(ostr, value);
2125 CNcbiBoostLogger::log_entry_finish(ostream& ostr)
2127 m_Upper->log_entry_finish(ostr);
2130 #if BOOST_VERSION >= 105900
2131 void CNcbiBoostLogger::entry_context_start(ostream& ostr, but::log_level l)
2133 m_Upper->entry_context_start(ostr, l);
2136 # if BOOST_VERSION >= 106500
2137 void CNcbiBoostLogger::log_entry_context(ostream& ostr,
2139 but::const_string value)
2141 m_Upper->log_entry_context(ostr, l, value);
2144 void CNcbiBoostLogger::entry_context_finish(ostream& ostr, but::log_level l)
2146 m_Upper->entry_context_finish(ostr, l);
2149 void CNcbiBoostLogger::log_entry_context(ostream& ostr, but::const_string value)
2151 m_Upper->log_entry_context(ostr, value);
2154 void CNcbiBoostLogger::entry_context_finish (ostream& ostr)
2156 m_Upper->entry_context_finish(ostr);
2162 RegisterNcbiTestUserFunc(TNcbiTestUserFunction func,
2163 ETestUserFuncType func_type)
2165 s_GetTestApp().AddUserFunction(func, func_type);
2169 NcbiTestDependsOn(but::test_unit* tu, but::test_unit* dep_tu)
2171 s_GetTestApp().AddTestDependsOn(tu, dep_tu);
2175 NcbiTestDisable(but::test_unit* tu)
2177 s_GetTestApp().SetTestDisabled(tu);
2181 NcbiTestSetGlobalDisabled(void)
2183 s_GetTestApp().SetGloballyDisabled();
2187 NcbiTestSetGlobalSkipped(void)
2189 s_GetTestApp().SetGloballySkipped();
2192 CNcbiApplication* NcbiTestGetAppInstance(void)
2194 return &s_GetTestApp();
2197 CNcbiRegistry& NcbiTestGetRWConfig(void)
2199 return s_GetTestApp().GetTestRWConfig();
2203 NcbiTestGetIniParser(void)
2205 return s_GetTestApp().GetIniParser();
2209 NcbiTestGetArgDescrs(void)
2211 return s_GetTestApp().GetArgDescrs();
2215 NcbiTestGetUnit(CTempString test_name)
2217 return s_GetTestApp().GetTestUnit(test_name);
2224 using namespace but;
2226 static int s_NcbiArgc;
2227 static char** s_NcbiArgv;
2231 init_unit_test_suite(int argc, char** argv)
2233 if (s_NcbiArgc > 0) {
2237 return NCBI_NS_NCBI::s_GetTestApp().InitTestFramework(argc, argv);
2241 // Note: including of a cpp file is unfortunate however there is no
2242 // possibility to add it into the Makefile. Both files, test_boost.cpp
2243 // and teamcity_boost.cpp include some boost header files which in turn
2244 // have some implemented functions. Having them in two compilation units
2245 // result in broken linkage.
2247 // Note 2: teamcity_boost.cpp uses BOOST_GLOBAL_FIXTURE() which installs
2248 // teamcity formatters if the tests are executed under teamcity.
2249 #include "teamcity_boost.cpp"
2252 // This main() is based on a unification of code from various Boost versions'
2257 int result_code = boost::exit_success;
2258 bool made_report =
false;
2263 #if BOOST_VERSION >= 106000
2264 std::vector<char*> boost_args(1, argv[0]), ncbi_args;
2265 for (
int i = 0;
i < argc; ++
i) {
2266 NCBI_NS_NCBI::CTempString s(argv[
i]);
2267 if (NCBI_NS_NCBI::NStr::StartsWith(s,
"--")) {
2268 boost_args.push_back(argv[
i]);
2269 }
else if (s.size() == 2 && s[0] ==
'-'
2270 && s[1] >=
'a' && s[1] <=
'z') {
2271 boost_args.push_back(argv[
i]);
2272 if (
i + 1 < argc && argv[
i+1][0] !=
'-') {
2273 boost_args.push_back(argv[++
i]);
2276 ncbi_args.push_back(argv[
i]);
2289 #if BOOST_VERSION >= 105900
2290 if(
RTCFG(
bool, WAIT_FOR_DEBUGGER, wait_for_debugger) ) {
2291 *ostr <<
"Press any key to continue..." << std::endl;
2294 *ostr <<
"Continuing..." << std::endl;
2296 framework::finalize_setup_phase();
2297 output_format list_cont =
RTCFG(output_format, LIST_CONTENT, list_content);
2298 if( list_cont != but::OF_INVALID ) {
2299 if( list_cont == but::OF_DOT ) {
2300 ut_detail::dot_content_reporter reporter( results_reporter::get_stream() );
2301 traverse_test_tree( framework::master_test_suite().p_id, reporter,
true );
2304 ut_detail::hrf_content_reporter reporter( results_reporter::get_stream() );
2305 traverse_test_tree( framework::master_test_suite().p_id, reporter,
true );
2307 return boost::exit_success;
2310 if(
RTCFG(
bool, LIST_LABELS, list_labels) ) {
2311 ut_detail::labels_collector collector;
2312 traverse_test_tree( framework::master_test_suite().p_id, collector,
true );
2313 *ostr <<
"Available labels:\n ";
2314 std::copy( collector.labels().begin(), collector.labels().end(),
2315 std::ostream_iterator<std::string>( *ostr,
"\n " ) );
2317 return boost::exit_success;
2320 if( !runtime_config::test_to_run().is_empty() ) {
2321 test_case_filter filter( runtime_config::test_to_run() );
2322 traverse_test_tree( framework::master_test_suite().p_id, filter );
2326 #if BOOST_VERSION < 106700
2327 results_reporter::make_report();
2332 #
if BOOST_VERSION >= 106000
2333 RTCFG(
bool, RESULT_CODE, result_code)
2335 !runtime_config::no_result_code()
2338 #if BOOST_VERSION >= 105900
2344 but::test_results
const& tr
2345 = but::results_collector.results(
2346 framework::master_test_suite().p_id);
2347 const_cast<bool&
>(tr.p_skipped.get()) =
false;
2348 const_cast<but::counter_t&
>(tr.p_test_cases_skipped.get()) = 0;
2350 result_code = results_collector.results( framework::master_test_suite().p_id ).result_code();
2356 printf(
"There were no test failures, only timeouts.\n"
2357 " (for autobuild scripts: NCBI_UNITTEST_TIMEOUTS_BUT_NO_ERRORS)\n");
2362 #if BOOST_VERSION >= 106000
2364 result_code = ex.m_result_code;
2366 #elif BOOST_VERSION >= 104200
2368 result_code = boost::exit_success;
2372 *ostr <<
"Boost.Test framework internal error: " << ex.what()
2374 result_code = boost::exit_exception_failure;
2377 *ostr <<
"Test setup error: " << ex.what() << std::endl;
2378 result_code = boost::exit_exception_failure;
2381 *ostr <<
"Test framework error: " << ex.what() << std::endl;
2382 result_code = boost::exit_exception_failure;
2385 *ostr <<
"Boost.Test framework internal error: unknown reason"
2387 result_code = boost::exit_exception_failure;
2390 if ( !made_report ) {
2391 results_reporter::make_report();
2394 #if BOOST_VERSION >= 105900
2395 framework::shutdown();
2406 #if defined(NCBI_OS_MSWIN) && defined(_UNICODE)
2409 std::vector<std::string> args_storage(argc);
2410 std::vector<char*> args(argc);
2411 for (
int i = 0;
i < argc; ++
i) {
2412 args_storage[
i] = ncbi::CUtf8::AsUTF8(argv[
i]);
2413 args[
i] =
const_cast<char*
>(args_storage[
i].c_str());
2415 return main(argc, args.data());
void Parse(const char *str)
CExprSymbol * AddSymbol(const char *name, VT value)
const CExprValue & GetResult(void) const
EValue GetType(void) const
Logger for embedding in Boost framework and adding non-standard information to logging given by Boost...
virtual void test_unit_skipped(ostream &ostr, but::test_unit const &tu)
virtual ~CNcbiBoostLogger(void)
bool m_IsXML
If report is XML or not.
virtual void log_entry_value(ostream &ostr, but::const_string value)
virtual void log_exception(ostream &ostr, but::log_checkpoint_data const &lcd, but::const_string explanation)
virtual void log_start(ostream &ostr, but::counter_t test_cases_amount)
virtual void log_build_info(ostream &ostr)
virtual void log_entry_start(ostream &ostr, but::log_entry_data const &led, log_entry_types let)
virtual void test_unit_finish(ostream &ostr, but::test_unit const &tu, unsigned long elapsed)
void SetOutputFormat(but::output_format format)
Setup logger tuned for printing log of specific format.
virtual void test_unit_start(ostream &ostr, but::test_unit const &tu)
AutoPtr< TBoostLogFormatter > m_Upper
Standard logger from Boost for particular report format.
virtual void log_entry_finish(ostream &ostr)
virtual void log_finish(ostream &ostr)
Reporter for embedding in Boost framework and adding non-standard information to detailed report give...
virtual void results_report_finish(ostream &ostr)
void SetOutputFormat(but::output_format format)
Setup reporter tuned for printing report of specific format.
int m_Indent
Current indentation level in plain text report.
virtual ~CNcbiBoostReporter(void)
virtual void test_unit_report_start(but::test_unit const &tu, ostream &ostr)
bool m_IsXML
If report is XML or not.
virtual void do_confirmation_report(but::test_unit const &tu, ostream &ostr)
AutoPtr< TBoostRepFormatter > m_Upper
Standard reporter from Boost for particular report format.
virtual void results_report_start(ostream &ostr)
virtual void test_unit_report_finish(but::test_unit const &tu, ostream &ostr)
Application for all unit tests.
int GetToFixTestsCount(void)
Get number of tests that were failed but are marked to be fixed.
bool m_RunCalled
If Run() was called or not.
void x_EnableAllTests(bool enable)
Enable / disable all tests known to application.
bool HasTestErrors(void)
Check if there were any test errors.
string m_TimeoutStr
String representation for whole test timeout (real value taken from CHECK_TIMEOUT in Makefile).
CExprParser * GetIniParser(void)
Get parser evaluating configuration conditions.
virtual int DryRun(void)
Test run the application.
TStringToUnitMap m_AllTests
List of all test units mapped to their names.
ofstream m_ReportOut
Output stream for Boost.Test report.
list< TNcbiTestUserFunction > TUserFuncsList
CNcbiRegistry & GetTestRWConfig(void)
Get the application's cached configuration parameters, accessible to read-write.
void AddUserFunction(TNcbiTestUserFunction func, ETestUserFuncType func_type)
Add user function.
virtual void Init(void)
Initialize the application.
AutoPtr< CArgDescriptions > m_ArgDescrs
Argument descriptions to be passed to SetArgDescriptions().
AutoPtr< CExprParser > m_IniParser
Parser to evaluate expressions in configuration file.
void x_AddDummyTest(void)
Add empty test necesary for internal purposes.
bool m_HasTestErrors
Flag showing if there were some test errors.
ostream & GetFreeformReportStream(void) const
CNcbiTestsTreeBuilder m_TreeBuilder
Builder of internal accessible from library tests tree.
TUnitsSet m_ToFixTests
List of all tests marked as in need of fixing in the future.
TUnitToManyMap m_TestDeps
List of all dependencies for each test having dependencies.
but::test_suite * InitTestFramework(int argc, char *argv[])
Initialize this application, main test suite and all test framework.
string GetTestResultString(but::test_unit *tu)
Get string representation of result of test execution.
void FiniTestsAfterRun(void)
Finalize test suite after running tests.
ERunMode
Mode of running testing application.
@ fTestList
Only tests list is requested.
@ fInitFailed
Initialization user functions failed.
@ fDisabled
All tests are disabled in configuration file.
void x_InitCommonParserVars(void)
Initialize common for all tests parser variables (OS*, COMPILER* and DLL_BUILD)
void x_SetupBoostReporters(void)
Setup our own reporter for Boost.Test.
void x_CollectAllTests()
Collect names and pointers to all tests existing in master test suite.
bool IsInitFailed(void)
Check if user initialization functions failed.
void InitTestsBeforeRun(void)
Initialize already prepared test suite before running tests.
unsigned int m_CurUnitTimeout
Timeout that was set in currently executing unit before adjustment.
void x_EnsureAllDeps(void)
Ensure that all dependencies stand earlier in tests tree than their dependents.
void x_ActualizeDeps(void)
Set up real Boost.Test dependencies based on ones made by AddTestDependsOn().
void SetTestDisabled(but::test_unit *tu)
Set test as disabled by user.
void CollectTestUnit(but::test_unit *tu)
Save test unit in the collection of all tests.
double m_Timeout
Timeout for the whole test.
int GetRanTestsCount(void)
Get number of actually executed tests.
void AddTestDependsOn(but::test_unit *tu, but::test_unit *dep_tu)
Add dependency for test unit.
void SetTestErrored(but::test_case *tc)
Register the fact of test failure.
double m_TimeMult
Multiplicator for timeouts.
void ReEnableAllTests(void)
Enable all necessary tests after execution but before printing report.
bool HasTestTimeouts(void)
Check if there were any timeouted tests.
bool x_CalcConfigValue(const string &value)
Calculate the value from configuration file.
but::test_case * m_DummyTest
Empty test case added to Boost for internal perposes.
string x_GetTrimmedTestName(const string &test_name)
Apply standard trimmings to test name and return resultant test name which will identify test inside ...
void SetGloballyDisabled(void)
Set flag that all tests globally disabled.
bool IsTestToFix(const but::test_unit *tu)
Check if given test is marked as requiring fixing in the future.
void AdjustTestTimeout(but::test_unit *tu)
Check the correct setting for unit timeout and check overall test timeout.
int x_GetEnabledTestsCount(void)
Get number of tests which Boost will execute.
CNcbiBoostReporter * m_Reporter
Boost reporter - must be pointer because Boost.Test calls free() on it.
void SetTestTimedOut(but::test_case *tc)
Mark test case as failed due to hit of the timeout.
~CNcbiTestApplication(void)
TUnitsSet m_DisabledTests
List of all disabled tests.
but::test_case * GetDummyTest(void)
Get pointer to empty test case added to Boost for internal purposes.
bool x_ReadConfiguration(void)
Enable / disable tests based on application configuration file.
bool x_CallUserFuncs(ETestUserFuncType func_type)
Call all user functions.
void SetGloballySkipped(void)
Set flag that all tests globally skipped.
CArgDescriptions * GetArgDescrs(void)
Get object with argument descriptions.
TRunMode m_RunMode
Mode of running the application.
virtual int Run(void)
Run the application.
CNcbiBoostLogger * m_Logger
Boost logger - must be pointer because Boost.Test calls free() on it.
TUnitsSet m_TimedOutTests
List of all tests which result is a timeout.
CNcbiTestsObserver m_Observer
Observer to make test dependencies and look for unit's timeouts.
CStopWatch m_Timer
Timer measuring elapsed time for the whole test.
CNcbiTestApplication(void)
but::test_unit * GetTestUnit(CTempString test_name)
Get pointer to test case or test suite by its name.
TUserFuncsList m_UserFuncs[eTestUserFuncLast - eTestUserFuncFirst+1]
Lists of all user-defined functions.
bool m_HasTestTimeouts
Flag showing if there were some timeouted tests.
CNcbiTestMemoryCleanupList – Define a list of pointers to free at exit.
~CNcbiTestTreeElement(void)
In destructor class destroys all its children.
TElemsSet m_MustLeft
Elements that should be "on the left" from this element in tests tree (should have less index in the ...
void AddChild(CNcbiTestTreeElement *element)
Add child element.
TElemsSet m_MustRight
Elements that should be "on the right" from this element in tests tree (should have greater index in ...
void x_AddToMustRight(CNcbiTestTreeElement *elem, CNcbiTestTreeElement *rightElem)
but::test_unit * GetTestUnit(void)
Get unit represented by the element.
void x_EnsureChildOrder(CNcbiTestTreeElement *leftElem, CNcbiTestTreeElement *rightElem)
Ensure that leftElem and rightElem (or element pointed by it_right inside m_Children) are in that ver...
vector< CNcbiTestTreeElement * > TElemsList
CNcbiTestTreeElement * m_Parent
Parent element in tests tree.
void x_AddToMustLeft(CNcbiTestTreeElement *elem, CNcbiTestTreeElement *leftElem)
Add leftElem (rightElem) in the list of elements that should be "lefter" ("righter") in the tests tre...
TElemsList m_Children
Children of the element in tests tree.
bool m_OrderChanged
If order of children was changed during checking dependencies.
CNcbiTestTreeElement & operator=(const CNcbiTestTreeElement &)
void EnsureDep(CNcbiTestTreeElement *from)
Ensure good dependency of this element on "from" element.
void FixUnitsOrder(void)
Fix order of unit tests in the subtree rooted in this element.
CNcbiTestTreeElement(but::test_unit *tu)
Element represents one test unit.
CNcbiTestTreeElement(const CNcbiTestTreeElement &)
Prohibit.
set< CNcbiTestTreeElement * > TElemsSet
CNcbiTestTreeElement * GetParent(void)
Get parent element in tests tree.
but::test_unit * m_TestUnit
Unit represented by the element.
Class that can walk through all tree of tests and register them inside CNcbiTestApplication.
virtual bool test_suite_start(but::test_suite const &suite)
virtual void visit(but::test_case const &test)
virtual ~CNcbiTestsCollector(void)
Special observer to embed in Boost.Test framework to initialize test dependencies before they started...
virtual void test_unit_finish(but::test_unit const &tu, unsigned long elapsed)
Method called after execution of each unit.
virtual void exception_caught(boost::execution_exception const &ex)
Method called when some exception was caught during execution of unit.
virtual void test_finish(void)
Method called before execution of all tests.
virtual ~CNcbiTestsObserver(void)
virtual void test_unit_start(but::test_unit const &tu)
Method called before execution of each unit.
virtual void test_unit_aborted(but::test_unit const &tu)
Method called when some check fails during execution of unit.
virtual void assertion_result(bool passed)
Class for traversing all Boost tests tree and building tree structure in our own accessible manner.
virtual void test_suite_finish(but::test_suite const &suite)
CNcbiTestTreeElement * m_CurElem
Element in tests tree representing started but not yet finished test suite, i.e.
CNcbiTestsTreeBuilder(void)
void EnsureDep(but::test_unit *tu, but::test_unit *tu_from)
Ensure good dependency of the tu test unit on tu_from test unit.
CNcbiTestTreeElement * m_RootElem
Root element of the tests tree.
map< but::test_unit *, CNcbiTestTreeElement * > TUnitToElemMap
virtual ~CNcbiTestsTreeBuilder(void)
virtual bool test_suite_start(but::test_suite const &suite)
TUnitToElemMap m_AllUnits
Overall map of relations between test units and their representatives in elements tree.
virtual void visit(but::test_case const &test)
void FixUnitsOrder(void)
Fix order of unit tests in the whole tree of tests.
static void Destroy(CSafeStaticLifeSpan::ELifeLevel level)
Explicitly destroy all on-demand variables up to a specified level.
@ eLifeLevel_AppMain
Destroyed in CNcbiApplication::AppMain, if possible.
CTempString implements a light-weight string on top of a storage buffer whose lifetime management is ...
container_type::iterator iterator
const_iterator end() const
iterator_bool insert(const value_type &val)
const_iterator find(const key_type &key) const
iterator_bool insert(const value_type &val)
const_iterator find(const key_type &key) const
const_iterator end() const
CNcbiOstream & operator<<(CNcbiOstream &out, const CEquivRange &range)
#define test(a, b, c, d, e)
static void DLIST_NAME() init(DLIST_LIST_TYPE *list)
static const char * str(char *buf, int n)
static char test_name[128]
void SetAppFlags(TAppFlags flags)
const CNcbiRegistry & GetConfig(void) const
Get the application's cached configuration parameters (read-only).
int AppMain(int argc, const char *const *argv, const char *const *envp=0, EAppDiagStream diag=eDS_Default, const char *conf=NcbiEmptyCStr, const string &name=NcbiEmptyString)
Main function (entry point) for the NCBI application.
virtual void SetupArgDescriptions(CArgDescriptions *arg_desc)
Setup the command line argument descriptions.
#define ITERATE(Type, Var, Cont)
ITERATE macro to sequence through container elements.
element_type * get(void) const
Get pointer.
CNcbiRegistry & GetRWConfig(void)
Get the application's cached configuration parameters, accessible for read-write for an application's...
#define NON_CONST_ITERATE(Type, Var, Cont)
Non constant version of ITERATE macro.
const CNcbiArguments & GetArguments(void) const
Get the application's cached unprocessed command-line arguments.
element_type * release(void)
Release will release ownership of pointer to caller.
void AddFlag(const string &name, const string &comment, CBoolEnum< EFlagValue > set_value=eFlagHasValueIfSet, TFlags flags=0)
Add description for flag argument.
void SetUsageContext(const string &usage_name, const string &usage_description, bool usage_sort_args=false, SIZE_TYPE usage_width=78)
Set extra info to be used by PrintUsage().
void AddOptionalKey(const string &name, const string &synopsis, const string &comment, EType type, TFlags flags=0)
Add description for optional key without default value.
@ fMandatorySeparator
Require '=' separator.
@ eString
An arbitrary string.
CDiagContext & GetDiagContext(void)
Get diag context instance.
static CRequestContext & GetRequestContext(void)
Shortcut to CDiagContextThreadData::GetThreadData().GetRequestContext()
void SetRequestStatus(int status)
void SetExitCode(int exit_code)
Set exit code.
#define ERR_POST_X(err_subcode, message)
Error posting with default error code and given error subcode.
#define ERR_POST(message)
Error posting with file, line number information but without error codes.
const string & Get(const string &name, bool *found=NULL) const
Get environment value by name.
#define NCBI_THROW(exception_class, err_code, message)
Generic macro to throw an exception, given the exception class, error code and message string.
void Warning(CExceptionArgs_Base &args)
virtual const char * what(void) const noexcept
Standard report (includes full backlog).
#define FORMAT(message)
Format message using iostreams library.
void Info(CExceptionArgs_Base &args)
uint32_t Uint4
4-byte (32-bit) unsigned integer
virtual const string & Get(const string §ion, const string &name, TFlags flags=0) const
Get the parameter value.
virtual void EnumerateEntries(const string §ion, list< string > *entries, TFlags flags=fAllLayers) const
Enumerate parameter names for a specified section.
#define BEGIN_NCBI_SCOPE
Define ncbi namespace.
NCBI_NS_STD::string::size_type SIZE_TYPE
static list< string > & Split(const CTempString str, const CTempString delim, list< string > &arr, TSplitFlags flags=0, vector< SIZE_TYPE > *token_pos=NULL)
Split a string using specified delimiters.
static double StringToDouble(const CTempStringEx str, TStringToNumFlags flags=0)
Convert string to double.
static string IntToString(int value, TNumToStringFlags flags=0, int base=10)
Convert int to string.
static SIZE_TYPE Find(const CTempString str, const CTempString pattern, ECase use_case=eCase, EDirection direction=eForwardSearch, SIZE_TYPE occurrence=0)
Find the pattern in the string.
static bool StartsWith(const CTempString str, const CTempString start, ECase use_case=eCase)
Check if a string starts with a specified prefix value.
static bool SplitInTwo(const CTempString str, const CTempString delim, string &str1, string &str2, TSplitFlags flags=0)
Split a string into two pieces using the specified delimiters.
static int CompareCase(const CTempString s1, SIZE_TYPE pos, SIZE_TYPE n, const char *s2)
Case-sensitive compare of a substring with another string.
@ fAllowTrailingSpaces
Ignore trailing whitespace characters.
@ fConvErr_NoThrow
Do not throw an exception on error.
@ fAllowLeadingSpaces
Ignore leading whitespace characters in converted string.
@ fSplit_Tokenize
All delimiters are merged and trimmed, to get non-empty tokens only.
@ eReverseSearch
Search in a backward direction.
@ eNocase
Case insensitive compare.
@ eCase
Case sensitive compare.
CAutoInitializeStaticFastMutex g_NcbiTestMutex
void(* TNcbiTestUserFunction)(void)
Type of user-defined function which will be automatically registered in test framework.
ETestUserFuncType
Types of functions that user can define.
~CNcbiTestMemoryCleanupList()
std::list< void * > m_List
static CNcbiTestMemoryCleanupList * GetInstance()
#define STATIC_FAST_MUTEX_INITIALIZER
Determine type of system mutex initialization.
double Elapsed(void) const
Return time elapsed since first Start() or last Restart() call (in seconds).
void Stop(void)
Suspend the timer.
unsigned int
A callback function used to compare two keys in a database.
Definition of all error codes used in corelib (xncbi.lib).
constexpr bool empty(list< Ts... >) noexcept
const GenericPointer< typename T::ValueType > T2 value
Static variables safety - create on demand, destroy on application termination.
void SuppressSystemMessageBox(TSuppressSystemMessageBox mode=fSuppress_Default)
Suppress popup messages on execution errors.
Defines the CNcbiApplication and CAppException classes for creating NCBI applications.
Defines access to miscellaneous global configuration settings.
const char * NCBI_GetBuildFeatures(void)
Get list of enabled features and packages, delimited by spaces.
double NCBI_GetCheckTimeoutMult(void)
Get multiplier for timeouts which depends on speed of the machine and tools application is running un...
#define NCBI_PLATFORM_BITS
Defines unified interface to application:
Miscellaneous common-use basic types and functionality.
void copy(Njn::Matrix< S > *matrix_, const Njn::Matrix< T > &matrix0_)
static SLJIT_INLINE sljit_ins l(sljit_gpr r, sljit_s32 d, sljit_gpr x, sljit_gpr b)
#define BOOST_TEST_I_CATCHALL()
const char * kDummyTestCaseName
static char ** s_NcbiArgv
const char * kTestsTimeoutSectionName
int main(int argc, char *argv[])
static const char * s_NcbiFeatures[]
List of features that will be converted to unittest variables (checking testsuite environment variabl...
const char * kTestConfigGlobalValue
map< but::test_unit *, TUnitsSet > TUnitToManyMap
static CNcbiTestApplication * s_TestApp
but::results_reporter::format TBoostRepFormatter
const char * kTestResultDisabled
static bool s_IsEnabled(const but::test_unit &tu)
const char * kTestsToFixSectionName
const char * kTestResultPassed
static CNcbiTestMemoryCleanupList * s_TestMemoryCleanupList
#define BOOST_TEST_I_CATCH0(type)
#define CONFIGURED_FILTERS
#define IS_FLAG_DEFINED(flag)
Helper macro to check if NCBI preprocessor flag was defined empty or equal to 1.
const char * kTestsDisableSectionName
but::unit_test_log_formatter TBoostLogFormatter
#define BOOST_TEST_I_CATCH(type, ex)
const char * kTestResultAborted
#define IS_VAR_DEFINED(var)
const char * kTestResultSkipped
const char * kTestResultToFix
const char * kTestResultFailed
static const char * s_GetUserFuncName(ETestUserFuncType func_type)
#define DUMMY_TEST_FUNCTION_NAME
set< but::test_unit * > TUnitsSet
#define RTCFG(type, new_name, old_name)
test_suite * init_unit_test_suite(int argc, char **argv)
Global initialization function called from Boost framework.
const char * kTestResultTimeout
static void s_SetEnabled(but::test_unit &tu, bool enabled)
map< string, but::test_unit * > TStringToUnitMap
static CNcbiTestApplication & s_GetTestApp(void)
Application for unit tests.
Utility stuff for more convenient using of Boost.Test library.
#define NCBI_BOOST_LOCATION()