2021-06-07 11:20:34 +00:00
|
|
|
TOML stands for Tom's Obvious, Minimal Language. This Go package provides a
|
2023-04-25 10:28:07 +00:00
|
|
|
reflection interface similar to Go's standard library `json` and `xml` packages.
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
Compatible with TOML version [v1.0.0](https://toml.io/en/v1.0.0).
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
Documentation: https://godocs.io/github.com/BurntSushi/toml
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
See the [releases page](https://github.com/BurntSushi/toml/releases) for a
|
|
|
|
changelog; this information is also in the git tag annotations (e.g. `git show
|
|
|
|
v0.4.0`).
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2023-04-25 10:28:07 +00:00
|
|
|
This library requires Go 1.13 or newer; add it to your go.mod with:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
% go get github.com/BurntSushi/toml@latest
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
It also comes with a TOML validator CLI tool:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
% go install github.com/BurntSushi/toml/cmd/tomlv@latest
|
|
|
|
% tomlv some-toml-file.toml
|
2021-06-07 11:20:34 +00:00
|
|
|
|
|
|
|
### Examples
|
2022-02-28 12:32:27 +00:00
|
|
|
For the simplest example, consider some TOML file as just a list of keys and
|
|
|
|
values:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
|
|
|
```toml
|
|
|
|
Age = 25
|
|
|
|
Cats = [ "Cauchy", "Plato" ]
|
|
|
|
Pi = 3.14
|
|
|
|
Perfection = [ 6, 28, 496, 8128 ]
|
|
|
|
DOB = 1987-07-05T05:45:00Z
|
|
|
|
```
|
|
|
|
|
2023-04-25 10:28:07 +00:00
|
|
|
Which can be decoded with:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
|
|
|
```go
|
|
|
|
type Config struct {
|
2022-02-28 12:32:27 +00:00
|
|
|
Age int
|
|
|
|
Cats []string
|
|
|
|
Pi float64
|
|
|
|
Perfection []int
|
2023-04-25 10:28:07 +00:00
|
|
|
DOB time.Time
|
2021-06-07 11:20:34 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
var conf Config
|
2023-04-25 10:28:07 +00:00
|
|
|
_, err := toml.Decode(tomlData, &conf)
|
2021-06-07 11:20:34 +00:00
|
|
|
```
|
|
|
|
|
2023-04-25 10:28:07 +00:00
|
|
|
You can also use struct tags if your struct field name doesn't map to a TOML key
|
|
|
|
value directly:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
|
|
|
```toml
|
|
|
|
some_key_NAME = "wat"
|
|
|
|
```
|
|
|
|
|
|
|
|
```go
|
|
|
|
type TOML struct {
|
2022-02-28 12:32:27 +00:00
|
|
|
ObscureKey string `toml:"some_key_NAME"`
|
2021-06-07 11:20:34 +00:00
|
|
|
}
|
|
|
|
```
|
|
|
|
|
2023-04-25 10:28:07 +00:00
|
|
|
Beware that like other decoders **only exported fields** are considered when
|
|
|
|
encoding and decoding; private fields are silently ignored.
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
### Using the `Marshaler` and `encoding.TextUnmarshaler` interfaces
|
2023-04-25 10:28:07 +00:00
|
|
|
Here's an example that automatically parses values in a `mail.Address`:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
|
|
|
```toml
|
2023-04-25 10:28:07 +00:00
|
|
|
contacts = [
|
|
|
|
"Donald Duck <donald@duckburg.com>",
|
|
|
|
"Scrooge McDuck <scrooge@duckburg.com>",
|
|
|
|
]
|
2021-06-07 11:20:34 +00:00
|
|
|
```
|
|
|
|
|
2023-04-25 10:28:07 +00:00
|
|
|
Can be decoded with:
|
2021-06-07 11:20:34 +00:00
|
|
|
|
|
|
|
```go
|
2023-04-25 10:28:07 +00:00
|
|
|
// Create address type which satisfies the encoding.TextUnmarshaler interface.
|
|
|
|
type address struct {
|
|
|
|
*mail.Address
|
2021-06-07 11:20:34 +00:00
|
|
|
}
|
|
|
|
|
2023-04-25 10:28:07 +00:00
|
|
|
func (a *address) UnmarshalText(text []byte) error {
|
2021-06-07 11:20:34 +00:00
|
|
|
var err error
|
2023-04-25 10:28:07 +00:00
|
|
|
a.Address, err = mail.ParseAddress(string(text))
|
2021-06-07 11:20:34 +00:00
|
|
|
return err
|
|
|
|
}
|
2023-04-25 10:28:07 +00:00
|
|
|
|
|
|
|
// Decode it.
|
|
|
|
func decode() {
|
|
|
|
blob := `
|
|
|
|
contacts = [
|
|
|
|
"Donald Duck <donald@duckburg.com>",
|
|
|
|
"Scrooge McDuck <scrooge@duckburg.com>",
|
|
|
|
]
|
|
|
|
`
|
|
|
|
|
|
|
|
var contacts struct {
|
|
|
|
Contacts []address
|
|
|
|
}
|
|
|
|
|
|
|
|
_, err := toml.Decode(blob, &contacts)
|
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, c := range contacts.Contacts {
|
|
|
|
fmt.Printf("%#v\n", c.Address)
|
|
|
|
}
|
|
|
|
|
|
|
|
// Output:
|
|
|
|
// &mail.Address{Name:"Donald Duck", Address:"donald@duckburg.com"}
|
|
|
|
// &mail.Address{Name:"Scrooge McDuck", Address:"scrooge@duckburg.com"}
|
|
|
|
}
|
2021-06-07 11:20:34 +00:00
|
|
|
```
|
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
To target TOML specifically you can implement `UnmarshalTOML` TOML interface in
|
|
|
|
a similar way.
|
2021-06-07 11:20:34 +00:00
|
|
|
|
2022-02-28 12:32:27 +00:00
|
|
|
### More complex usage
|
2023-04-25 10:28:07 +00:00
|
|
|
See the [`_example/`](/_example) directory for a more complex example.
|