iarna / iarna-toml

Better TOML parsing and stringifying all in that familiar JSON interface.
ISC License
320 stars 43 forks source link

1.0.0-rc.1 stringifier can produce results incompatible with 0.5 and 0.4 #26

Open iarna opened 4 years ago

iarna commented 4 years ago

In and of itself, this is unsurprising: Use new features, it won't work. The place where this is maybe surprising is with the support for mixed-type arrays. Consider the following examples:

# json 1.0.0-rc.1 0.5
1 {a: [1, 2]} a = [ 1, 2 ] a = [ 1, 2 ]
2 {a: [1.0, 2]} a = [ 1, 2 ] a = [ 1, 2 ]
3 {a: [1.1, 2]} a = [ 1.1, 2 ] a = [ 1.1, 2.0 ]
4 {a: [1.1, 2n]} a = [1.1, 2 ] a = [ 1.1, 2.0 ]
5 {a: [1.1, 9999999999999999n]} a = [ 1.1, 9_999_999_999_999_999 ] a = [ 1.1, 9_999_999_999_999_999.0 ]

So my thinking:

  1. this is all good
  2. numbers are numbers in js, we can't tell 1.0 apart from 1, so this is fine
  3. the 1.0.0-rc.1 version is perfectly valid, but nonetheless, let's update this to be compat with 0.5. no reason to introduce gratuitous backward incompatibility -- a compat doc under 0.5 should still produce a compat doc on 1.0.0-rc.1
  4. no change to 1.0.0-rc.1 version, 0.5 should throw as a bigint is defintiely not a float
  5. same as 4, as the fact that bigints are not floats is even more important here as if you load the 0.5 doc you'll get a value of 10000000000000000 due to lack of available precision.
iarna commented 4 years ago

The only thing that makes me feel icky about the change to 4 is that the following:

TOML.stringify(TOML.parse('a = [ 1.1, 2 ]'`)) === 'a = [ 1.1, 2.0 ]'

Part of me feels like it should round trip, but I suppose there are many other TOML documents that don't perfectly round trip and they are equivalent under JS. (Not the least because whitespace, comments.)