Skip to content

Commit 0cc833e

Browse files
committed
Make JSONWriter's number handling locale-independent
Closes #3176
1 parent 8494e2d commit 0cc833e

19 files changed

Lines changed: 211 additions & 19 deletions

src/catch2/internal/catch_jsonwriter.cpp

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@
99
#include <catch2/internal/catch_jsonwriter.hpp>
1010
#include <catch2/internal/catch_unreachable.hpp>
1111

12+
#include <locale>
13+
1214
namespace Catch {
1315

1416
namespace {
@@ -126,7 +128,10 @@ namespace Catch {
126128

127129
JsonValueWriter::JsonValueWriter( std::ostream& os,
128130
std::uint64_t indent_level ):
129-
m_os{ os }, m_indent_level{ indent_level } {}
131+
m_os{ os }, m_indent_level{ indent_level } {
132+
// We use C locale so that writing of numerical values is locale-independent.
133+
m_sstream.imbue( std::locale::classic() );
134+
}
130135

131136
JsonObjectWriter JsonValueWriter::writeObject() && {
132137
return JsonObjectWriter{ m_os, m_indent_level };

tests/SelfTest/Baselines/automake.sw.approved.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -190,6 +190,7 @@ Nor would this
190190
:test-result: PASS Inequality checks that should succeed
191191
:test-result: PASS JsonWriter
192192
:test-result: PASS JsonWriter escapes characters in strings properly
193+
:test-result: PASS JsonWriter serializes numbers independently of the global locale
193194
:test-result: PASS Lambdas in assertions
194195
:test-result: PASS Less-than inequalities with different epsilons
195196
:test-result: PASS ManuallyRegistered

tests/SelfTest/Baselines/automake.sw.multi.approved.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -188,6 +188,7 @@
188188
:test-result: PASS Inequality checks that should succeed
189189
:test-result: PASS JsonWriter
190190
:test-result: PASS JsonWriter escapes characters in strings properly
191+
:test-result: PASS JsonWriter serializes numbers independently of the global locale
191192
:test-result: PASS Lambdas in assertions
192193
:test-result: PASS Less-than inequalities with different epsilons
193194
:test-result: PASS ManuallyRegistered

tests/SelfTest/Baselines/compact.sw.approved.txt

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1248,6 +1248,20 @@ Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\n\"" for: ""\n"" ==
12481248
Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\r\"" for: ""\r"" == ""\r""
12491249
Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\t\"" for: ""\t"" == ""\t""
12501250
Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\\\/\\t\\r\\n\"" for: ""\\/\t\r\n"" == ""\\/\t\r\n""
1251+
Json.tests.cpp:<line number>: passed: sstream.str(), ContainsSubstring( "\"double\": 1.5," ) && ContainsSubstring( "\"int\": 1234567," ) && ContainsSubstring( "\"bool-1\": true," ) && ContainsSubstring( "\"bool-2\": false," ) && ContainsSubstring( "\"array\": [\n 2.5,\n 1234567\n ]\n}" ) for: "{
1252+
"double": 1.5,
1253+
"int": 1234567,
1254+
"bool-1": true,
1255+
"bool-2": false,
1256+
"array": [
1257+
2.5,
1258+
1234567
1259+
]
1260+
}" ( contains: ""double": 1.5," and contains: ""int": 1234567," and contains: ""bool-1": true," and contains: ""bool-2": false," and contains: ""array": [
1261+
2.5,
1262+
1234567
1263+
]
1264+
}" )
12511265
Compilation.tests.cpp:<line number>: passed: []() { return true; }() for: true
12521266
Approx.tests.cpp:<line number>: passed: d <= Approx( 1.24 ) for: 1.22999999999999998
12531267
<=
@@ -3000,7 +3014,7 @@ InternalBenchmark.tests.cpp:<line number>: passed: med == 18. for: 18.0 == 18.0
30003014
InternalBenchmark.tests.cpp:<line number>: passed: q3 == 23. for: 23.0 == 23.0
30013015
Misc.tests.cpp:<line number>: passed:
30023016
Misc.tests.cpp:<line number>: passed:
3003-
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
3004-
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
3017+
test cases: 452 | 332 passed | 96 failed | 6 skipped | 18 failed as expected
3018+
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected
30053019

30063020

tests/SelfTest/Baselines/compact.sw.multi.approved.txt

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1246,6 +1246,20 @@ Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\n\"" for: ""\n"" ==
12461246
Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\r\"" for: ""\r"" == ""\r""
12471247
Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\t\"" for: ""\t"" == ""\t""
12481248
Json.tests.cpp:<line number>: passed: sstream.str() == "\"\\\\/\\t\\r\\n\"" for: ""\\/\t\r\n"" == ""\\/\t\r\n""
1249+
Json.tests.cpp:<line number>: passed: sstream.str(), ContainsSubstring( "\"double\": 1.5," ) && ContainsSubstring( "\"int\": 1234567," ) && ContainsSubstring( "\"bool-1\": true," ) && ContainsSubstring( "\"bool-2\": false," ) && ContainsSubstring( "\"array\": [\n 2.5,\n 1234567\n ]\n}" ) for: "{
1250+
"double": 1.5,
1251+
"int": 1234567,
1252+
"bool-1": true,
1253+
"bool-2": false,
1254+
"array": [
1255+
2.5,
1256+
1234567
1257+
]
1258+
}" ( contains: ""double": 1.5," and contains: ""int": 1234567," and contains: ""bool-1": true," and contains: ""bool-2": false," and contains: ""array": [
1259+
2.5,
1260+
1234567
1261+
]
1262+
}" )
12491263
Compilation.tests.cpp:<line number>: passed: []() { return true; }() for: true
12501264
Approx.tests.cpp:<line number>: passed: d <= Approx( 1.24 ) for: 1.22999999999999998
12511265
<=
@@ -2989,7 +3003,7 @@ InternalBenchmark.tests.cpp:<line number>: passed: med == 18. for: 18.0 == 18.0
29893003
InternalBenchmark.tests.cpp:<line number>: passed: q3 == 23. for: 23.0 == 23.0
29903004
Misc.tests.cpp:<line number>: passed:
29913005
Misc.tests.cpp:<line number>: passed:
2992-
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
2993-
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
3006+
test cases: 452 | 332 passed | 96 failed | 6 skipped | 18 failed as expected
3007+
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected
29943008

29953009

tests/SelfTest/Baselines/console.std.approved.txt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1743,6 +1743,6 @@ due to unexpected exception with message:
17431743
Why would you throw a std::string?
17441744

17451745
===============================================================================
1746-
test cases: 451 | 349 passed | 76 failed | 7 skipped | 19 failed as expected
1747-
assertions: 2394 | 2215 passed | 136 failed | 43 failed as expected
1746+
test cases: 452 | 350 passed | 76 failed | 7 skipped | 19 failed as expected
1747+
assertions: 2395 | 2216 passed | 136 failed | 43 failed as expected
17481748

tests/SelfTest/Baselines/console.sw.approved.txt

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8219,6 +8219,31 @@ Json.tests.cpp:<line number>: PASSED:
82198219
with expansion:
82208220
""\\/\t\r\n"" == ""\\/\t\r\n""
82218221

8222+
-------------------------------------------------------------------------------
8223+
JsonWriter serializes numbers independently of the global locale
8224+
-------------------------------------------------------------------------------
8225+
Json.tests.cpp:<line number>
8226+
...............................................................................
8227+
8228+
Json.tests.cpp:<line number>: PASSED:
8229+
REQUIRE_THAT( sstream.str(), ContainsSubstring( "\"double\": 1.5," ) && ContainsSubstring( "\"int\": 1234567," ) && ContainsSubstring( "\"bool-1\": true," ) && ContainsSubstring( "\"bool-2\": false," ) && ContainsSubstring( "\"array\": [\n 2.5,\n 1234567\n ]\n}" ) )
8230+
with expansion:
8231+
"{
8232+
"double": 1.5,
8233+
"int": 1234567,
8234+
"bool-1": true,
8235+
"bool-2": false,
8236+
"array": [
8237+
2.5,
8238+
1234567
8239+
]
8240+
}" ( contains: ""double": 1.5," and contains: ""int": 1234567," and contains:
8241+
""bool-1": true," and contains: ""bool-2": false," and contains: ""array": [
8242+
2.5,
8243+
1234567
8244+
]
8245+
}" )
8246+
82228247
-------------------------------------------------------------------------------
82238248
Lambdas in assertions
82248249
-------------------------------------------------------------------------------
@@ -20134,6 +20159,6 @@ Misc.tests.cpp:<line number>
2013420159
Misc.tests.cpp:<line number>: PASSED:
2013520160

2013620161
===============================================================================
20137-
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
20138-
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
20162+
test cases: 452 | 332 passed | 96 failed | 6 skipped | 18 failed as expected
20163+
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected
2013920164

tests/SelfTest/Baselines/console.sw.multi.approved.txt

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8217,6 +8217,31 @@ Json.tests.cpp:<line number>: PASSED:
82178217
with expansion:
82188218
""\\/\t\r\n"" == ""\\/\t\r\n""
82198219

8220+
-------------------------------------------------------------------------------
8221+
JsonWriter serializes numbers independently of the global locale
8222+
-------------------------------------------------------------------------------
8223+
Json.tests.cpp:<line number>
8224+
...............................................................................
8225+
8226+
Json.tests.cpp:<line number>: PASSED:
8227+
REQUIRE_THAT( sstream.str(), ContainsSubstring( "\"double\": 1.5," ) && ContainsSubstring( "\"int\": 1234567," ) && ContainsSubstring( "\"bool-1\": true," ) && ContainsSubstring( "\"bool-2\": false," ) && ContainsSubstring( "\"array\": [\n 2.5,\n 1234567\n ]\n}" ) )
8228+
with expansion:
8229+
"{
8230+
"double": 1.5,
8231+
"int": 1234567,
8232+
"bool-1": true,
8233+
"bool-2": false,
8234+
"array": [
8235+
2.5,
8236+
1234567
8237+
]
8238+
}" ( contains: ""double": 1.5," and contains: ""int": 1234567," and contains:
8239+
""bool-1": true," and contains: ""bool-2": false," and contains: ""array": [
8240+
2.5,
8241+
1234567
8242+
]
8243+
}" )
8244+
82208245
-------------------------------------------------------------------------------
82218246
Lambdas in assertions
82228247
-------------------------------------------------------------------------------
@@ -20123,6 +20148,6 @@ Misc.tests.cpp:<line number>
2012320148
Misc.tests.cpp:<line number>: PASSED:
2012420149

2012520150
===============================================================================
20126-
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
20127-
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
20151+
test cases: 452 | 332 passed | 96 failed | 6 skipped | 18 failed as expected
20152+
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected
2012820153

tests/SelfTest/Baselines/junit.sw.approved.txt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
<?xml version="1.0" encoding="UTF-8"?>
22
<testsuitesloose text artifact
33
>
4-
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2428" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
4+
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2429" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
55
<properties>
66
<property name="random-seed" value="1"/>
77
<property name="filters" value="&quot;*&quot; ~[!nonportable] ~[!benchmark] ~[approvals]"/>
@@ -774,6 +774,7 @@ at Condition.tests.cpp:<line number>
774774
<testcase classname="<exe-name>.global" name="JsonWriter escapes characters in strings properly/carriage return in a string is escaped" time="{duration}" status="run"/>
775775
<testcase classname="<exe-name>.global" name="JsonWriter escapes characters in strings properly/tab in a string is escaped" time="{duration}" status="run"/>
776776
<testcase classname="<exe-name>.global" name="JsonWriter escapes characters in strings properly/combination of characters is escaped" time="{duration}" status="run"/>
777+
<testcase classname="<exe-name>.global" name="JsonWriter serializes numbers independently of the global locale" time="{duration}" status="run"/>
777778
<testcase classname="<exe-name>.global" name="Lambdas in assertions" time="{duration}" status="run"/>
778779
<testcase classname="<exe-name>.global" name="Less-than inequalities with different epsilons" time="{duration}" status="run"/>
779780
<testcase classname="<exe-name>.global" name="ManuallyRegistered" time="{duration}" status="run"/>

tests/SelfTest/Baselines/junit.sw.multi.approved.txt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
<?xml version="1.0" encoding="UTF-8"?>
22
<testsuites>
3-
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2428" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
3+
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2429" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
44
<properties>
55
<property name="random-seed" value="1"/>
66
<property name="filters" value="&quot;*&quot; ~[!nonportable] ~[!benchmark] ~[approvals]"/>
@@ -773,6 +773,7 @@ at Condition.tests.cpp:<line number>
773773
<testcase classname="<exe-name>.global" name="JsonWriter escapes characters in strings properly/carriage return in a string is escaped" time="{duration}" status="run"/>
774774
<testcase classname="<exe-name>.global" name="JsonWriter escapes characters in strings properly/tab in a string is escaped" time="{duration}" status="run"/>
775775
<testcase classname="<exe-name>.global" name="JsonWriter escapes characters in strings properly/combination of characters is escaped" time="{duration}" status="run"/>
776+
<testcase classname="<exe-name>.global" name="JsonWriter serializes numbers independently of the global locale" time="{duration}" status="run"/>
776777
<testcase classname="<exe-name>.global" name="Lambdas in assertions" time="{duration}" status="run"/>
777778
<testcase classname="<exe-name>.global" name="Less-than inequalities with different epsilons" time="{duration}" status="run"/>
778779
<testcase classname="<exe-name>.global" name="ManuallyRegistered" time="{duration}" status="run"/>

0 commit comments

Comments
 (0)