Sane C++ Libraries
C++ Platform Abstraction Libraries
Loading...
Searching...
No Matches
Testing.h
1// Copyright (c) Stefano Cristiano
2// SPDX-License-Identifier: MIT
3#pragma once
4#include "../Foundation/Result.h"
5#include "../Foundation/StringPath.h"
6#include "../Foundation/StringSpan.h"
7
8namespace SC
9{
10struct TestCase;
13
16
22{
23 struct IOutput
24 {
25 virtual ~IOutput() = default;
26
27 virtual void flush() = 0;
28 virtual void printLine(StringSpan text) = 0;
29 virtual void print(StringSpan text) = 0;
30 virtual void print(StringSpan text, StringSpan p0) = 0;
31 virtual void print(StringSpan text, StringSpan p0, StringSpan p1) = 0;
32 virtual void print(StringSpan text, size_t p0) = 0;
33 virtual void print(StringSpan text, size_t p0, size_t p1) = 0;
34 };
35
36 template <typename ConsoleType>
37 struct Output final : public TestReport::IOutput
38 {
39 ConsoleType& console;
40 Output(ConsoleType& console) : console(console) {}
41
42 virtual void flush() override { console.flush(); }
43 virtual void printLine(StringSpan text) override { console.printLine(text); }
44 virtual void print(StringSpan text) override { console.print(text); }
45 virtual void print(StringSpan text, StringSpan p0) override { console.print(text, p0); }
46 virtual void print(StringSpan text, StringSpan p0, StringSpan p1) override { console.print(text, p0, p1); }
47 virtual void print(StringSpan text, size_t p0) override { console.print(text, p0); }
48 virtual void print(StringSpan text, size_t p0, size_t p1) override { console.print(text, p0, p1); }
49 };
50 IOutput& console;
51
55
56 // Options
59 bool quietMode = false;
60
65 TestReport(IOutput& console, int argc, const char** argv);
67
70 [[nodiscard]] int getTestReturnCode() const;
71
72 template <typename Statistics>
73 void runGlobalMemoryReport(Statistics stats, bool reportFailure = true)
74 {
75 TestReport::MemoryStatistics memStats;
76 memStats.numAllocate = stats.numAllocate;
77 memStats.numReallocate = stats.numReallocate;
78 memStats.numRelease = stats.numRelease;
79 internalRunGlobalMemoryReport(memStats, reportFailure);
80 }
81
82 private:
83 struct MemoryStatistics
84 {
85 size_t numAllocate = 0;
86 size_t numReallocate = 0;
87 size_t numRelease = 0;
88 };
89
91 void internalRunGlobalMemoryReport(MemoryStatistics stats, bool reportFailure);
92
93 [[nodiscard]] bool isTestEnabled(StringSpan testName) const;
94 [[nodiscard]] bool isSectionEnabled(StringSpan sectionName) const;
95
96 void testCaseFinished(TestCase& testCase);
97 void printSectionResult(TestCase& testCase);
98
99 friend struct TestCase;
100 uint32_t numTestsSucceeded = 0;
101 uint32_t numTestsFailed = 0;
102 StringSpan currentSection;
103 StringSpan firstFailedTest;
104 StringSpan testToRun;
105 StringSpan sectionToRun;
106};
107
114{
119 ~TestCase();
120
126 bool recordExpectation(StringSpan expression, bool status, StringSpan detailedError = StringSpan());
127
132 bool recordExpectation(StringSpan expression, Result status);
133
134 enum class Execute
135 {
136 Default,
138 };
139
144 [[nodiscard]] bool test_section(StringSpan sectionName, Execute execution = Execute::Default);
145
147 private:
148 friend struct TestReport;
149 const StringSpan testName;
150
151 uint32_t numTestsSucceeded;
152 uint32_t numTestsFailed;
153 uint32_t numSectionTestsFailed;
154 bool printedSection;
155};
156
157// clang-format off
159#define SC_TEST_EXPECT(e) recordExpectation(StringSpan(#e), (e)) ? (void)0 : (TestCase::report.debugBreakOnFailedTest ? SC_COMPILER_DEBUG_BREAK : (void)0)
160// clang-format on
161
163} // namespace SC
unsigned int uint32_t
Platform independent (4) bytes unsigned int.
Definition PrimitiveTypes.h:38
An ascii string used as boolean result. SC_TRY macro forwards errors to caller.
Definition Result.h:12
Pre-sized char array holding enough space to represent a file system path.
Definition StringPath.h:42
An read-only view over a string (to avoid including Strings library when parsing is not needed).
Definition StringSpan.h:37
A test case that can be split into multiple sections.
Definition Testing.h:114
bool recordExpectation(StringSpan expression, Result status)
Records an expectation for a given expression.
Execute
Definition Testing.h:135
@ OnlyExplicit
Test is executed only if explicitly requested with –test-section.
@ Default
Test is executed if all tests are enabled or if this specific one matches –test-section.
TestCase(TestReport &report, StringSpan testName)
Adds this TestCase to a TestReport with a name.
TestReport & report
The TestReport object passed in the constructor.
Definition Testing.h:146
bool recordExpectation(StringSpan expression, bool status, StringSpan detailedError=StringSpan())
Records an expectation for a given expression.
bool test_section(StringSpan sectionName, Execute execution=Execute::Default)
Starts a new test section.
Definition Testing.h:24
Definition Testing.h:38
Collects multiple TestCase and reports their results.
Definition Testing.h:22
StringPath applicationRootDirectory
Path to application (on macOS is different from executable path)
Definition Testing.h:54
StringPath executableFile
Path to current executable.
Definition Testing.h:53
int getTestReturnCode() const
Gets return code for this process.
bool quietMode
If true will not print recaps at start or end of the test.
Definition Testing.h:59
bool abortOnFirstFailedTest
If true will abort after first failed test.
Definition Testing.h:57
StringPath libraryRootDirectory
Path to sources directory for library.
Definition Testing.h:52
bool debugBreakOnFailedTest
If true will issue a debugger halt when a test fails.
Definition Testing.h:58
TestReport(IOutput &console, int argc, const char **argv)
Build from a console and executable arguments.