Skip to content

Ignore non-JSON stdout preamble in catch_discover_tests (#3162)#3166

Open
ShivaPriyanShanmuga wants to merge 1 commit into
catchorg:develfrom
ShivaPriyanShanmuga:discover-tests-ignore-stdout-preamble
Open

Ignore non-JSON stdout preamble in catch_discover_tests (#3162)#3166
ShivaPriyanShanmuga wants to merge 1 commit into
catchorg:develfrom
ShivaPriyanShanmuga:discover-tests-ignore-stdout-preamble

Conversation

@ShivaPriyanShanmuga

Copy link
Copy Markdown

What

catch_discover_tests() runs the test executable with
--list-tests --reporter json and feeds the entire stdout into CMake's
string(JSON ...). If anything writes to stdout before main runs - most
commonly a third-party library logging from a static initializer - that text
precedes Catch2's JSON and the parser fails with:

string sub-command JSON failed parsing json string: * Line 1, Column 1
Syntax error: value, object or array expected.

Older versions used the plain --list-tests text output, which tolerated such
noise, so this is a regression people hit when upgrading.

Closes #3162.

How

Before parsing, strip everything before the first { (where Catch2's JSON
output begins) in extras/CatchAddTests.cmake. If no { is present at all,
fail with a clear error that includes the captured output.
This intentionally covers only the case described in the issue - output printed
before discovery starts (e.g. static-init constructors). It does not attempt
to handle output interleaved into the middle of the JSON.

Tests

Extended the existing CMakeHelper::DiscoverTests integration test:

  • register-tests.cpp now prints to stdout from a static initializer, so the
    discovered executable reproduces the scenario.
  • VerifyRegistration.py parses the executable's raw stdout directly, so it
    skips to the first { the same way the CMake script does.

Verified locally: the test fails on devel (JSON syntax error during
discovery) and passes with this change (5 tests matched).

catch_discover_tests runs the test executable with --list-tests
--reporter json and parses the whole stdout as JSON. If a third-party
library writes to stdout from a static initializer, that text precedes
Catch2's JSON output and breaks the parser.

Strip everything before the first '{' (where Catch2's JSON starts)
before parsing, so such startup output is ignored. The registration
test now prints from a static initializer to cover this, and the
Python verifier skips the preamble the same way.
@ShivaPriyanShanmuga ShivaPriyanShanmuga force-pushed the discover-tests-ignore-stdout-preamble branch from c8b5efb to 7991d1c Compare June 20, 2026 22:37
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

catch_discover_tests() should process only json portion of stdout

1 participant