ron icon indicating copy to clipboard operation
ron copied to clipboard

Consider supporting "compact-pretty-printed" mode

Open nyurik opened this issue 2 months ago • 3 comments

Would it be possible to support json_pretty_compact-style formatting? From that crate's example - note how it tries to fit as many elements on a single line as possible, and only when it can't fit more, it inserts a line break. This implies a back-tracking algorithm - for each sub-tree, render it as a one-liner until it no longer fits, otherwise backtrack and break into multiple lines

[
  {
    "name": { "first": "Kobe", "middle": "Nico", "last": "Grimes" },
    "phoneNumber": "1-547-479-5471 x062",
    "username": "Kobe-Grimes",
    "emails": [ "[email protected]", "[email protected]" ],
    "coordinates": { "latitude": "-66.3821", "longitude": "127.117" }
  },
  {
    "name": { "first": "Adrian", "middle": "Finley", "last": "Koch" },
    "phoneNumber": "1-420-853-5251 x68083",
    "username": "Adrian-Koch",
    "emails": [ "[email protected]", "[email protected]" ],
    "coordinates": { "latitude": "51.4003", "longitude": "3.351" }
  }
]

nyurik avatar Oct 06 '25 23:10 nyurik

Implementing support for this in RON directly would be possible but would likely require quite some refactoring, though in principle we already have all pretty-printing tools to produce pretty one-liners and can also serialize the same value multiple times (though this would also require some buffering), so checking after a "container" whether a line limit was exceeded and if so retrying with line breaks is certainly possible.

I wonder though if this could also be implemented as a post-processing step on a buffered serialized string that was produced with fully-expanding pretty formatting. Since RON uses the usual delimiters, ([{,, a simple state machine could count open and closed brackets to find the bounds of each "container", then bottom-up determine if it fits on one line and if so removing excessive newlines and indentation.

juntyr avatar Oct 07 '25 03:10 juntyr

It can certainly be done in a post-processing, but I have a feeling it would be somewhat slow to remove all the unneeded extra spacing/newlines

nyurik avatar Oct 07 '25 03:10 nyurik

You're likely right, an optimised implementation would have O(N) just from the necessary copying, bracket counting would also be O(N), deciding when to collapse could maybe be done in at worst O(N) as well if you keep an additional tree structure for all "containers" that remembers the single-line-length for each.

The other downside would of course be having to buffer the entire string, though I don't think you could get away with that either if we implemented it during serialising since re-serialising several times would require buffering per-container anyways. Furthermore, implementing it during serialising might also be slower since we potentially have to serialise every container twice and that quickly adds up - working in-place on a string might be faster here

juntyr avatar Oct 07 '25 05:10 juntyr