naoina / toml

TOML parser and encoder library for Golang
MIT License
294 stars 50 forks source link

Decoding into embedded struct #38

Open vmihailenco opened 7 years ago

vmihailenco commented 7 years ago

At some point this library was changed so it can't decode into embedded structs any more

package main

import (
    "fmt"

    "github.com/naoina/toml"
)

type DBConfig struct {
    User string `toml:"user"`
}

type DBClusterConfig struct {
    DBConfig
}

func main() {
    doc := []byte(`
        user = "test_user"
    `)

    config := new(DBClusterConfig)
    if err := toml.Unmarshal(doc, &config); err != nil {
        panic(err)
    }
    fmt.Println("user", config.User)
}

Old revisions (such as 7a3d4a6210ea3f8a66f704c5603ff27fb91fea8e) work just fine.

fjl commented 7 years ago

I'm thinking about how to do this. The best way would probably be to use the same rules as "encoding/json", but they're complicated:

// Anonymous struct fields are usually marshaled as if their inner exported fields
// were fields in the outer struct, subject to the usual Go visibility rules amended
// as described in the next paragraph.
// An anonymous struct field with a name given in its JSON tag is treated as
// having that name, rather than being anonymous.
// An anonymous struct field of interface type is treated the same as having
// that type as its name, rather than being anonymous.
//
// The Go visibility rules for struct fields are amended for JSON when
// deciding which field to marshal or unmarshal. If there are
// multiple fields at the same level, and that level is the least
// nested (and would therefore be the nesting level selected by the
// usual Go rules), the following extra rules apply:
//
// 1) Of those fields, if any are JSON-tagged, only tagged fields are considered,
// even if there are multiple untagged fields that would otherwise conflict.
//
// 2) If there is exactly one field (tagged or not according to the first rule), that is selected.
//
// 3) Otherwise there are multiple fields, and all are ignored; no error occurs.