zkry/yaml.el

Bug with nested array of key-value pairs

etiago opened this issue · 1 comments

Hi!

I'm relatively confident I've found a bug in how the library handles nested key value pairs.

First an example of it working as expected, with an array of key-value pairs at the root level.

This:

(yaml-encode
 `[((foo . bar) (baz . bax))])

Results in :

- foo: bar
  baz: bax

However, if I nest this array of key-values one level deeper, the indentation (and therefore meaning of the yaml) breaks.

This:

(yaml-encode
 `((deeper . [((foo . bar) (baz . bax))])))

Results in:

deeper: 
    -  foo: bar
    baz: bax

As you'll notice, baz should be aligned with foo but the indentation is wrong. Parsing back that string fails, as deeper now has a mixed meaning between an array of objects and a single nested object.

I think I've identified the change needed. I've gotten good results by changing line 2793 from:

                 (indent-string (make-string (* 2 indent) ?\s)))

To:

                 (indent-string (make-string (* 2 (- indent 2)) ?\s)))

Where the difference is discounting 2 from the indent such that we're accounting for the "- " that precedes the first element of a list.

After making this change, I can produce yaml with differing depths of arrays of key-values, that I can then parse back.

But I haven't tested this much beyond a couple of manual tests, so take it with a bit of salt.

zkry commented

Thanks for reporting this and going through the work of locating the bug! I'll go through your solution and make sure it works in general.