diff options
| author | René Scharfe <l.s.r@web.de> | 2024-07-30 16:08:19 +0200 |
|---|---|---|
| committer | Junio C Hamano <gitster@pobox.com> | 2024-07-30 13:32:43 -0700 |
| commit | 96c6304c1866d8dd2f17208e906749f999df0911 (patch) | |
| tree | 64f13cd19f337208f7b67e4bb2c105012bf0d21f /t/unit-tests | |
| parent | 1f452d6c6835e41d25e163616d8ee75aa91b5b17 (diff) | |
| download | git-96c6304c1866d8dd2f17208e906749f999df0911.tar.gz | |
unit-tests: add if_test
The macro TEST only allows defining a test that consists of a single
expression. Add a new macro, if_test, which provides a way to define
unit tests that are made up of one or more statements.
if_test allows defining self-contained tests en bloc, a bit like
test_expect_success does for regular tests. It acts like a conditional;
the test body is executed if test_skip_all() had not been called before.
Signed-off-by: René Scharfe <l.s.r@web.de>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
Diffstat (limited to 't/unit-tests')
| -rw-r--r-- | t/unit-tests/test-lib.c | 29 | ||||
| -rw-r--r-- | t/unit-tests/test-lib.h | 20 |
2 files changed, 49 insertions, 0 deletions
diff --git a/t/unit-tests/test-lib.c b/t/unit-tests/test-lib.c index 989dc758e6..fa1f95965c 100644 --- a/t/unit-tests/test-lib.c +++ b/t/unit-tests/test-lib.c @@ -16,6 +16,8 @@ static struct { unsigned running :1; unsigned skip_all :1; unsigned todo :1; + char location[100]; + char description[100]; } ctx = { .lazy_plan = 1, .result = RESULT_NONE, @@ -125,6 +127,8 @@ void test_plan(int count) int test_done(void) { + if (ctx.running && ctx.location[0] && ctx.description[0]) + test__run_end(1, ctx.location, "%s", ctx.description); assert(!ctx.running); if (ctx.lazy_plan) @@ -167,13 +171,38 @@ void test_skip_all(const char *format, ...) va_end(ap); } +void test__run_describe(const char *location, const char *format, ...) +{ + va_list ap; + int len; + + assert(ctx.running); + assert(!ctx.location[0]); + assert(!ctx.description[0]); + + xsnprintf(ctx.location, sizeof(ctx.location), "%s", + make_relative(location)); + + va_start(ap, format); + len = vsnprintf(ctx.description, sizeof(ctx.description), format, ap); + va_end(ap); + if (len < 0) + die("unable to format message: %s", format); + if (len >= sizeof(ctx.description)) + BUG("ctx.description too small to format %s", format); +} + int test__run_begin(void) { + if (ctx.running && ctx.location[0] && ctx.description[0]) + test__run_end(1, ctx.location, "%s", ctx.description); assert(!ctx.running); ctx.count++; ctx.result = RESULT_NONE; ctx.running = 1; + ctx.location[0] = '\0'; + ctx.description[0] = '\0'; return ctx.skip_all; } diff --git a/t/unit-tests/test-lib.h b/t/unit-tests/test-lib.h index 2de6d715d5..f15dceb29e 100644 --- a/t/unit-tests/test-lib.h +++ b/t/unit-tests/test-lib.h @@ -15,6 +15,23 @@ TEST_LOCATION(), __VA_ARGS__) /* + * Run a test unless test_skip_all() has been called. Acts like a + * conditional; the test body is expected as a statement or block after + * the closing parenthesis. The description for each test should be + * unique. E.g.: + * + * if_test ("something else %d %d", arg1, arg2) { + * prepare(); + * test_something_else(arg1, arg2); + * cleanup(); + * } + */ +#define if_test(...) \ + if (test__run_begin() ? \ + (test__run_end(0, TEST_LOCATION(), __VA_ARGS__), 0) : \ + (test__run_describe(TEST_LOCATION(), __VA_ARGS__), 1)) + +/* * Print a test plan, should be called before any tests. If the number * of tests is not known in advance test_done() will automatically * print a plan at the end of the test program. @@ -153,6 +170,9 @@ union test__tmp { extern union test__tmp test__tmp[2]; +__attribute__((format (printf, 2, 3))) +void test__run_describe(const char *, const char *, ...); + int test__run_begin(void); __attribute__((format (printf, 3, 4))) int test__run_end(int, const char *, const char *, ...); |
