Skip to content

Commit

Permalink
Preserve defaults for zero initialised structs as well
Browse files Browse the repository at this point in the history
  • Loading branch information
yhabteab committed Mar 29, 2024
1 parent 4653a1b commit 1d13c5f
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 4 deletions.
12 changes: 8 additions & 4 deletions decode.go
Original file line number Diff line number Diff line change
Expand Up @@ -954,18 +954,22 @@ func (d *Decoder) createDecodedNewValue(
return newValue, nil
}
}
var newValue reflect.Value
if node.Type() == ast.NullType {
return reflect.Zero(typ), nil
newValue = reflect.New(typ).Elem()
} else {
newValue = d.createDecodableValue(typ)
}
newValue := d.createDecodableValue(typ)
for defaultVal.Kind() == reflect.Ptr {
defaultVal = defaultVal.Elem()
}
if defaultVal.IsValid() && defaultVal.Type().AssignableTo(newValue.Type()) {
newValue.Set(defaultVal)
}
if err := d.decodeValue(ctx, newValue, node); err != nil {
return newValue, errors.Wrapf(err, "failed to decode value")
if node.Type() != ast.NullType {
if err := d.decodeValue(ctx, newValue, node); err != nil {
return newValue, errors.Wrapf(err, "failed to decode value")
}
}
return newValue, nil
}
Expand Down
25 changes: 25 additions & 0 deletions decode_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2906,3 +2906,28 @@ func TestSameNameInineStruct(t *testing.T) {
t.Fatalf("failed to decode")
}
}

func TestDecoderPreservesDefaultValues(t *testing.T) {
type second struct {
Val string `yaml:"val"`
}

type test struct {
First string `yaml:"first"`
Defaults second `yaml:"second"`
}

yml := `
first: "Test"
second:
# Just some comment here
# val: "default"
`
v := test{Defaults: second{Val: "default"}}
if err := yaml.Unmarshal([]byte(yml), &v); err != nil {
t.Fatal(err)
}
if v.Defaults.Val != "default" {
t.Fatal("decoder doesn't preserve struct defaults")
}
}

0 comments on commit 1d13c5f

Please sign in to comment.