mirror of
https://github.com/goccy/go-yaml.git
synced 2025-10-27 19:34:20 +00:00
Add Flow option for Encoder
This commit is contained in:
parent
5e642017ee
commit
e4be76e5f8
3 changed files with 49 additions and 9 deletions
21
encode.go
21
encode.go
|
|
@ -28,6 +28,7 @@ type Encoder struct {
|
||||||
writer io.Writer
|
writer io.Writer
|
||||||
opts []EncodeOption
|
opts []EncodeOption
|
||||||
indent int
|
indent int
|
||||||
|
isFlowStyle bool
|
||||||
anchorPtrToNameMap map[uintptr]string
|
anchorPtrToNameMap map[uintptr]string
|
||||||
|
|
||||||
line int
|
line int
|
||||||
|
|
@ -64,6 +65,11 @@ func (e *Encoder) Close() error {
|
||||||
//
|
//
|
||||||
// See the documentation for Marshal for details about the conversion of Go values to YAML.
|
// See the documentation for Marshal for details about the conversion of Go values to YAML.
|
||||||
func (e *Encoder) Encode(v interface{}) error {
|
func (e *Encoder) Encode(v interface{}) error {
|
||||||
|
for _, opt := range e.opts {
|
||||||
|
if err := opt(e); err != nil {
|
||||||
|
return errors.Wrapf(err, "failed to run option for encoder")
|
||||||
|
}
|
||||||
|
}
|
||||||
node, err := e.encodeValue(reflect.ValueOf(v), 1)
|
node, err := e.encodeValue(reflect.ValueOf(v), 1)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.Wrapf(err, "failed to encode value")
|
return errors.Wrapf(err, "failed to encode value")
|
||||||
|
|
@ -225,10 +231,7 @@ func (e *Encoder) encodeBool(v bool) ast.Node {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *Encoder) encodeSlice(value reflect.Value) (ast.Node, error) {
|
func (e *Encoder) encodeSlice(value reflect.Value) (ast.Node, error) {
|
||||||
sequence := &ast.SequenceNode{
|
sequence := ast.Sequence(token.New("-", "-", e.pos(e.column)), e.isFlowStyle)
|
||||||
Start: token.New("-", "-", e.pos(e.column)),
|
|
||||||
Values: []ast.Node{},
|
|
||||||
}
|
|
||||||
for i := 0; i < value.Len(); i++ {
|
for i := 0; i < value.Len(); i++ {
|
||||||
node, err := e.encodeValue(value.Index(i), e.column)
|
node, err := e.encodeValue(value.Index(i), e.column)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -259,7 +262,7 @@ func (e *Encoder) encodeMapItem(item MapItem, column int) (*ast.MappingValueNode
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *Encoder) encodeMapSlice(value MapSlice, column int) (ast.Node, error) {
|
func (e *Encoder) encodeMapSlice(value MapSlice, column int) (ast.Node, error) {
|
||||||
node := ast.Mapping(token.New("", "", e.pos(column)), false)
|
node := ast.Mapping(token.New("", "", e.pos(column)), e.isFlowStyle)
|
||||||
for _, item := range value {
|
for _, item := range value {
|
||||||
value, err := e.encodeMapItem(item, column)
|
value, err := e.encodeMapItem(item, column)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -271,7 +274,7 @@ func (e *Encoder) encodeMapSlice(value MapSlice, column int) (ast.Node, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *Encoder) encodeMap(value reflect.Value, column int) ast.Node {
|
func (e *Encoder) encodeMap(value reflect.Value, column int) ast.Node {
|
||||||
node := ast.Mapping(token.New("", "", e.pos(column)), false)
|
node := ast.Mapping(token.New("", "", e.pos(column)), e.isFlowStyle)
|
||||||
keys := []string{}
|
keys := []string{}
|
||||||
for _, k := range value.MapKeys() {
|
for _, k := range value.MapKeys() {
|
||||||
keys = append(keys, k.Interface().(string))
|
keys = append(keys, k.Interface().(string))
|
||||||
|
|
@ -345,7 +348,7 @@ func (e *Encoder) isZeroValue(v reflect.Value) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *Encoder) encodeStruct(value reflect.Value, column int) (ast.Node, error) {
|
func (e *Encoder) encodeStruct(value reflect.Value, column int) (ast.Node, error) {
|
||||||
node := ast.Mapping(token.New("", "", e.pos(column)), false)
|
node := ast.Mapping(token.New("", "", e.pos(column)), e.isFlowStyle)
|
||||||
structType := value.Type()
|
structType := value.Type()
|
||||||
structFieldMap, err := structFieldMap(structType)
|
structFieldMap, err := structFieldMap(structType)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -367,7 +370,7 @@ func (e *Encoder) encodeStruct(value reflect.Value, column int) (ast.Node, error
|
||||||
return nil, errors.Wrapf(err, "failed to encode value")
|
return nil, errors.Wrapf(err, "failed to encode value")
|
||||||
}
|
}
|
||||||
if m, ok := value.(*ast.MappingNode); ok {
|
if m, ok := value.(*ast.MappingNode); ok {
|
||||||
if structField.IsFlow {
|
if !e.isFlowStyle && structField.IsFlow {
|
||||||
m.IsFlowStyle = true
|
m.IsFlowStyle = true
|
||||||
}
|
}
|
||||||
for _, value := range m.Values {
|
for _, value := range m.Values {
|
||||||
|
|
@ -375,7 +378,7 @@ func (e *Encoder) encodeStruct(value reflect.Value, column int) (ast.Node, error
|
||||||
value.Value.GetToken().Position.Column += e.indent
|
value.Value.GetToken().Position.Column += e.indent
|
||||||
}
|
}
|
||||||
} else if s, ok := value.(*ast.SequenceNode); ok {
|
} else if s, ok := value.(*ast.SequenceNode); ok {
|
||||||
if structField.IsFlow {
|
if !e.isFlowStyle && structField.IsFlow {
|
||||||
s.IsFlowStyle = true
|
s.IsFlowStyle = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -495,6 +495,35 @@ c: true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestEncoder_Flow(t *testing.T) {
|
||||||
|
var buf bytes.Buffer
|
||||||
|
enc := yaml.NewEncoder(&buf, yaml.Flow(true))
|
||||||
|
var v struct {
|
||||||
|
A int
|
||||||
|
B string
|
||||||
|
C struct {
|
||||||
|
D int
|
||||||
|
E string
|
||||||
|
}
|
||||||
|
F []int
|
||||||
|
}
|
||||||
|
v.A = 1
|
||||||
|
v.B = "hello"
|
||||||
|
v.C.D = 3
|
||||||
|
v.C.E = "world"
|
||||||
|
v.F = []int{1, 2}
|
||||||
|
if err := enc.Encode(v); err != nil {
|
||||||
|
t.Fatalf("%+v", err)
|
||||||
|
}
|
||||||
|
expect := `
|
||||||
|
{a: 1, b: hello, c: {d: 3, e: world}, f: [1, 2]}
|
||||||
|
`
|
||||||
|
actual := "\n" + buf.String()
|
||||||
|
if expect != actual {
|
||||||
|
t.Fatalf("flow style marshal error: expect=[%s] actual=[%s]", expect, actual)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func Example_Marshal_ExplicitAnchorAlias() {
|
func Example_Marshal_ExplicitAnchorAlias() {
|
||||||
type T struct {
|
type T struct {
|
||||||
A int
|
A int
|
||||||
|
|
|
||||||
|
|
@ -55,3 +55,11 @@ func Indent(spaces int) EncodeOption {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Flow encoding by flow style
|
||||||
|
func Flow(isFlowStyle bool) EncodeOption {
|
||||||
|
return func(e *Encoder) error {
|
||||||
|
e.isFlowStyle = isFlowStyle
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue