cue
cue copied to clipboard
go/encoding/yaml uses LiteralStyle
Is your feature request related to a problem? Please describe.
I'm always frustrated when I want to encode CUE values in YAML and multiline strings are serialized as the YAML flow literal style (like\nthis\n) rather than in block style (i.e. with | )
Describe the solution you'd like I'd like multiline strings to stay multi-line when exported to YAML.
Describe alternatives you've considered
Currently, I use yq -P a lot
Would this be driven only by a heuristic, or also via some option?
I'm not sure what heuristics are available, curious what you are thinking there.
My intuition is that
- it would be an option (flag/attr/other)
- default would be the one most human readable / what a human would write, which is block style, but there are many variations/chomps... fortunately, a kind soul made a site just for YAML multiline craziness: https://yaml-multiline.info/
Another consideration is that a user may want to use different variations on different values
Yeah, I'm not sure what configuration you could usefully use? Maybe a callback function, where the caller could decide how to format. Alternatively, a well known CUE attribute (@yaml(multiline)?) would let CUE authors decide.
A callback and a default attribute handler? So you'd yaml.Encode(value, yaml.DefaultFormatter) to let @yaml(multiline) work, or wrap it in your own function to make other choices?
As for a default heuristic "The string includes an internal \n" feels sufficient. Client code of the YAML shouldn't care what format it's presented in, so we're mostly concerned with human readibility.
As soon as you open up on configuration value, there are a whole lot more. For example, there are times where CUE outputs !!binary ... which other programs dislike (this was k8s related, and maybe changed since?) Should I expect to be able to change this, what about indentation?
Rhetorically, which multiline yaml format (there's more than one) should something like @yaml(multiline) use?
That attr probably can't be used, or would have to be changed to cover more intents, as it is already used in en/decoding Go structs.
Rhetorically, which multiline yaml format (there's more than one) should something like @yaml(multiline) use?
I can't see why CUE wouldn't always use |+ - what I'm looking for is for strings with internal newlines to be serialized in YAML with raw newlines instead of "\n".
If you wanted to get very clever, you could decide on |-,|,|+ based on trailing newlines. Heck, you could even use > for strings longer than ~70 bytes with internal " "s. But I don't think "clever" is recommended here.
Also, you could use @yaml(multiline="|+")
That attr probably can't be used, or would have to be changed to cover more intents, as it is already used in en/decoding Go structs.
Maybe I don't understand what you mean here. Wouldn't the @go(yaml='') attr be used for Go?
We always use the new YAML decoder as of v0.10.0, based on the latest go-yaml: https://github.com/cue-lang/cue/issues/3027
And, from what I can see, we already do use multi-line YAML strings when the input CUE string contains any newlines: https://cuelang.org/play/?id=uiGBaBknij2#w=function&i=cue&f=export&o=yaml
So what exactly isn't working correctly as of v0.10.0?
It seems to be using yaml multiline (|-) as long as there is no lines that end with whitespace.
See the following example:
spec: {
pipeline: [{
input: {
inline: template: """
#{{$xr :=.observed.composite.resource}}
---
apiVersion: network.azure.upbound.io/v1beta1
kind: Subnet
spec:
...
"""
}
}, {
input: {
inline: template: """
#{{$xr :=.observed.composite.resource}}
---
apiVersion: network.azure.upbound.io/v1beta1
kind: Subnet
spec:
...
"""
}
}]
}
The first template here uses yaml multiline, while the other one uses doublequoted string with newlines
I see. In that specific scenario I would say the YAML library is working as intended: it avoids producing output with trailing whitespace in lines, as that is very often misleading or causes the lines to be "trimmed", changing the values of the strings. I think it's correct for https://github.com/go-yaml/yaml and CUE to avoid using the multi-line form in that case.
Yes, I'm happy with the current behaviour now that I know what causes it.