From d4d7611b175970714abca4efdc91692ee958a80f Mon Sep 17 00:00:00 2001 From: Alan Donovan Date: Tue, 19 Nov 2024 18:05:59 -0500 Subject: [PATCH] lib/json: encode floating point numbers with a decimal point (#564) The previous code carelessly used Go's %g operator when it should have used Starlark's. Fixes #563 --- lib/json/json.go | 3 ++- starlark/testdata/json.star | 7 ++++++- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/lib/json/json.go b/lib/json/json.go index 5979b6f8..bc67be5d 100644 --- a/lib/json/json.go +++ b/lib/json/json.go @@ -147,7 +147,8 @@ func encode(thread *starlark.Thread, b *starlark.Builtin, args starlark.Tuple, k if !isFinite(float64(x)) { return fmt.Errorf("cannot encode non-finite float %v", x) } - fmt.Fprintf(buf, "%g", x) // always contains a decimal point + // Float.String always contains a decimal point. (%g does not!) + buf.WriteString(x.String()) case starlark.String: quote(string(x)) diff --git a/starlark/testdata/json.star b/starlark/testdata/json.star index 62a457b8..1df9dee9 100644 --- a/starlark/testdata/json.star +++ b/starlark/testdata/json.star @@ -144,8 +144,13 @@ numbers = [ 0, 1, -1, +1, 1.23e45, -1.23e-45, 3539537889086624823140625, float(3539537889086624823140625), + float(1.0), ] -assert.eq(codec(numbers), numbers) +def number_roundtrip(): + show = lambda n: (n, type(n)) + for n in numbers: + assert.eq(show(codec(n)), show(n)) # ensure no int/float confusion +number_roundtrip() ## json.indent