marshal.go 36 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308
  1. package toml
  2. import (
  3. "bytes"
  4. "encoding"
  5. "errors"
  6. "fmt"
  7. "io"
  8. "reflect"
  9. "sort"
  10. "strconv"
  11. "strings"
  12. "time"
  13. )
  14. const (
  15. tagFieldName = "toml"
  16. tagFieldComment = "comment"
  17. tagCommented = "commented"
  18. tagMultiline = "multiline"
  19. tagLiteral = "literal"
  20. tagDefault = "default"
  21. )
  22. type tomlOpts struct {
  23. name string
  24. nameFromTag bool
  25. comment string
  26. commented bool
  27. multiline bool
  28. literal bool
  29. include bool
  30. omitempty bool
  31. defaultValue string
  32. }
  33. type encOpts struct {
  34. quoteMapKeys bool
  35. arraysOneElementPerLine bool
  36. }
  37. var encOptsDefaults = encOpts{
  38. quoteMapKeys: false,
  39. }
  40. type annotation struct {
  41. tag string
  42. comment string
  43. commented string
  44. multiline string
  45. literal string
  46. defaultValue string
  47. }
  48. var annotationDefault = annotation{
  49. tag: tagFieldName,
  50. comment: tagFieldComment,
  51. commented: tagCommented,
  52. multiline: tagMultiline,
  53. literal: tagLiteral,
  54. defaultValue: tagDefault,
  55. }
  56. type MarshalOrder int
  57. // Orders the Encoder can write the fields to the output stream.
  58. const (
  59. // Sort fields alphabetically.
  60. OrderAlphabetical MarshalOrder = iota + 1
  61. // Preserve the order the fields are encountered. For example, the order of fields in
  62. // a struct.
  63. OrderPreserve
  64. )
  65. var timeType = reflect.TypeOf(time.Time{})
  66. var marshalerType = reflect.TypeOf(new(Marshaler)).Elem()
  67. var unmarshalerType = reflect.TypeOf(new(Unmarshaler)).Elem()
  68. var textMarshalerType = reflect.TypeOf(new(encoding.TextMarshaler)).Elem()
  69. var textUnmarshalerType = reflect.TypeOf(new(encoding.TextUnmarshaler)).Elem()
  70. var localDateType = reflect.TypeOf(LocalDate{})
  71. var localTimeType = reflect.TypeOf(LocalTime{})
  72. var localDateTimeType = reflect.TypeOf(LocalDateTime{})
  73. var mapStringInterfaceType = reflect.TypeOf(map[string]interface{}{})
  74. // Check if the given marshal type maps to a Tree primitive
  75. func isPrimitive(mtype reflect.Type) bool {
  76. switch mtype.Kind() {
  77. case reflect.Ptr:
  78. return isPrimitive(mtype.Elem())
  79. case reflect.Bool:
  80. return true
  81. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  82. return true
  83. case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
  84. return true
  85. case reflect.Float32, reflect.Float64:
  86. return true
  87. case reflect.String:
  88. return true
  89. case reflect.Struct:
  90. return isTimeType(mtype)
  91. default:
  92. return false
  93. }
  94. }
  95. func isTimeType(mtype reflect.Type) bool {
  96. return mtype == timeType || mtype == localDateType || mtype == localDateTimeType || mtype == localTimeType
  97. }
  98. // Check if the given marshal type maps to a Tree slice or array
  99. func isTreeSequence(mtype reflect.Type) bool {
  100. switch mtype.Kind() {
  101. case reflect.Ptr:
  102. return isTreeSequence(mtype.Elem())
  103. case reflect.Slice, reflect.Array:
  104. return isTree(mtype.Elem())
  105. default:
  106. return false
  107. }
  108. }
  109. // Check if the given marshal type maps to a slice or array of a custom marshaler type
  110. func isCustomMarshalerSequence(mtype reflect.Type) bool {
  111. switch mtype.Kind() {
  112. case reflect.Ptr:
  113. return isCustomMarshalerSequence(mtype.Elem())
  114. case reflect.Slice, reflect.Array:
  115. return isCustomMarshaler(mtype.Elem()) || isCustomMarshaler(reflect.New(mtype.Elem()).Type())
  116. default:
  117. return false
  118. }
  119. }
  120. // Check if the given marshal type maps to a slice or array of a text marshaler type
  121. func isTextMarshalerSequence(mtype reflect.Type) bool {
  122. switch mtype.Kind() {
  123. case reflect.Ptr:
  124. return isTextMarshalerSequence(mtype.Elem())
  125. case reflect.Slice, reflect.Array:
  126. return isTextMarshaler(mtype.Elem()) || isTextMarshaler(reflect.New(mtype.Elem()).Type())
  127. default:
  128. return false
  129. }
  130. }
  131. // Check if the given marshal type maps to a non-Tree slice or array
  132. func isOtherSequence(mtype reflect.Type) bool {
  133. switch mtype.Kind() {
  134. case reflect.Ptr:
  135. return isOtherSequence(mtype.Elem())
  136. case reflect.Slice, reflect.Array:
  137. return !isTreeSequence(mtype)
  138. default:
  139. return false
  140. }
  141. }
  142. // Check if the given marshal type maps to a Tree
  143. func isTree(mtype reflect.Type) bool {
  144. switch mtype.Kind() {
  145. case reflect.Ptr:
  146. return isTree(mtype.Elem())
  147. case reflect.Map:
  148. return true
  149. case reflect.Struct:
  150. return !isPrimitive(mtype)
  151. default:
  152. return false
  153. }
  154. }
  155. func isCustomMarshaler(mtype reflect.Type) bool {
  156. return mtype.Implements(marshalerType)
  157. }
  158. func callCustomMarshaler(mval reflect.Value) ([]byte, error) {
  159. return mval.Interface().(Marshaler).MarshalTOML()
  160. }
  161. func isTextMarshaler(mtype reflect.Type) bool {
  162. return mtype.Implements(textMarshalerType) && !isTimeType(mtype)
  163. }
  164. func callTextMarshaler(mval reflect.Value) ([]byte, error) {
  165. return mval.Interface().(encoding.TextMarshaler).MarshalText()
  166. }
  167. func isCustomUnmarshaler(mtype reflect.Type) bool {
  168. return mtype.Implements(unmarshalerType)
  169. }
  170. func callCustomUnmarshaler(mval reflect.Value, tval interface{}) error {
  171. return mval.Interface().(Unmarshaler).UnmarshalTOML(tval)
  172. }
  173. func isTextUnmarshaler(mtype reflect.Type) bool {
  174. return mtype.Implements(textUnmarshalerType)
  175. }
  176. func callTextUnmarshaler(mval reflect.Value, text []byte) error {
  177. return mval.Interface().(encoding.TextUnmarshaler).UnmarshalText(text)
  178. }
  179. // Marshaler is the interface implemented by types that
  180. // can marshal themselves into valid TOML.
  181. type Marshaler interface {
  182. MarshalTOML() ([]byte, error)
  183. }
  184. // Unmarshaler is the interface implemented by types that
  185. // can unmarshal a TOML description of themselves.
  186. type Unmarshaler interface {
  187. UnmarshalTOML(interface{}) error
  188. }
  189. /*
  190. Marshal returns the TOML encoding of v. Behavior is similar to the Go json
  191. encoder, except that there is no concept of a Marshaler interface or MarshalTOML
  192. function for sub-structs, and currently only definite types can be marshaled
  193. (i.e. no `interface{}`).
  194. The following struct annotations are supported:
  195. toml:"Field" Overrides the field's name to output.
  196. omitempty When set, empty values and groups are not emitted.
  197. comment:"comment" Emits a # comment on the same line. This supports new lines.
  198. commented:"true" Emits the value as commented.
  199. Note that pointers are automatically assigned the "omitempty" option, as TOML
  200. explicitly does not handle null values (saying instead the label should be
  201. dropped).
  202. Tree structural types and corresponding marshal types:
  203. *Tree (*)struct, (*)map[string]interface{}
  204. []*Tree (*)[](*)struct, (*)[](*)map[string]interface{}
  205. []interface{} (as interface{}) (*)[]primitive, (*)[]([]interface{})
  206. interface{} (*)primitive
  207. Tree primitive types and corresponding marshal types:
  208. uint64 uint, uint8-uint64, pointers to same
  209. int64 int, int8-uint64, pointers to same
  210. float64 float32, float64, pointers to same
  211. string string, pointers to same
  212. bool bool, pointers to same
  213. time.LocalTime time.LocalTime{}, pointers to same
  214. For additional flexibility, use the Encoder API.
  215. */
  216. func Marshal(v interface{}) ([]byte, error) {
  217. return NewEncoder(nil).marshal(v)
  218. }
  219. // Encoder writes TOML values to an output stream.
  220. type Encoder struct {
  221. w io.Writer
  222. encOpts
  223. annotation
  224. line int
  225. col int
  226. order MarshalOrder
  227. promoteAnon bool
  228. compactComments bool
  229. indentation string
  230. }
  231. // NewEncoder returns a new encoder that writes to w.
  232. func NewEncoder(w io.Writer) *Encoder {
  233. return &Encoder{
  234. w: w,
  235. encOpts: encOptsDefaults,
  236. annotation: annotationDefault,
  237. line: 0,
  238. col: 1,
  239. order: OrderAlphabetical,
  240. indentation: " ",
  241. }
  242. }
  243. // Encode writes the TOML encoding of v to the stream.
  244. //
  245. // See the documentation for Marshal for details.
  246. func (e *Encoder) Encode(v interface{}) error {
  247. b, err := e.marshal(v)
  248. if err != nil {
  249. return err
  250. }
  251. if _, err := e.w.Write(b); err != nil {
  252. return err
  253. }
  254. return nil
  255. }
  256. // QuoteMapKeys sets up the encoder to encode
  257. // maps with string type keys with quoted TOML keys.
  258. //
  259. // This relieves the character limitations on map keys.
  260. func (e *Encoder) QuoteMapKeys(v bool) *Encoder {
  261. e.quoteMapKeys = v
  262. return e
  263. }
  264. // ArraysWithOneElementPerLine sets up the encoder to encode arrays
  265. // with more than one element on multiple lines instead of one.
  266. //
  267. // For example:
  268. //
  269. // A = [1,2,3]
  270. //
  271. // Becomes
  272. //
  273. // A = [
  274. // 1,
  275. // 2,
  276. // 3,
  277. // ]
  278. func (e *Encoder) ArraysWithOneElementPerLine(v bool) *Encoder {
  279. e.arraysOneElementPerLine = v
  280. return e
  281. }
  282. // Order allows to change in which order fields will be written to the output stream.
  283. func (e *Encoder) Order(ord MarshalOrder) *Encoder {
  284. e.order = ord
  285. return e
  286. }
  287. // Indentation allows to change indentation when marshalling.
  288. func (e *Encoder) Indentation(indent string) *Encoder {
  289. e.indentation = indent
  290. return e
  291. }
  292. // SetTagName allows changing default tag "toml"
  293. func (e *Encoder) SetTagName(v string) *Encoder {
  294. e.tag = v
  295. return e
  296. }
  297. // SetTagComment allows changing default tag "comment"
  298. func (e *Encoder) SetTagComment(v string) *Encoder {
  299. e.comment = v
  300. return e
  301. }
  302. // SetTagCommented allows changing default tag "commented"
  303. func (e *Encoder) SetTagCommented(v string) *Encoder {
  304. e.commented = v
  305. return e
  306. }
  307. // SetTagMultiline allows changing default tag "multiline"
  308. func (e *Encoder) SetTagMultiline(v string) *Encoder {
  309. e.multiline = v
  310. return e
  311. }
  312. // PromoteAnonymous allows to change how anonymous struct fields are marshaled.
  313. // Usually, they are marshaled as if the inner exported fields were fields in
  314. // the outer struct. However, if an anonymous struct field is given a name in
  315. // its TOML tag, it is treated like a regular struct field with that name.
  316. // rather than being anonymous.
  317. //
  318. // In case anonymous promotion is enabled, all anonymous structs are promoted
  319. // and treated like regular struct fields.
  320. func (e *Encoder) PromoteAnonymous(promote bool) *Encoder {
  321. e.promoteAnon = promote
  322. return e
  323. }
  324. // CompactComments removes the new line before each comment in the tree.
  325. func (e *Encoder) CompactComments(cc bool) *Encoder {
  326. e.compactComments = cc
  327. return e
  328. }
  329. func (e *Encoder) marshal(v interface{}) ([]byte, error) {
  330. // Check if indentation is valid
  331. for _, char := range e.indentation {
  332. if !isSpace(char) {
  333. return []byte{}, fmt.Errorf("invalid indentation: must only contains space or tab characters")
  334. }
  335. }
  336. mtype := reflect.TypeOf(v)
  337. if mtype == nil {
  338. return []byte{}, errors.New("nil cannot be marshaled to TOML")
  339. }
  340. switch mtype.Kind() {
  341. case reflect.Struct, reflect.Map:
  342. case reflect.Ptr:
  343. if mtype.Elem().Kind() != reflect.Struct {
  344. return []byte{}, errors.New("Only pointer to struct can be marshaled to TOML")
  345. }
  346. if reflect.ValueOf(v).IsNil() {
  347. return []byte{}, errors.New("nil pointer cannot be marshaled to TOML")
  348. }
  349. default:
  350. return []byte{}, errors.New("Only a struct or map can be marshaled to TOML")
  351. }
  352. sval := reflect.ValueOf(v)
  353. if isCustomMarshaler(mtype) {
  354. return callCustomMarshaler(sval)
  355. }
  356. if isTextMarshaler(mtype) {
  357. return callTextMarshaler(sval)
  358. }
  359. t, err := e.valueToTree(mtype, sval)
  360. if err != nil {
  361. return []byte{}, err
  362. }
  363. var buf bytes.Buffer
  364. _, err = t.writeToOrdered(&buf, "", "", 0, e.arraysOneElementPerLine, e.order, e.indentation, e.compactComments, false)
  365. return buf.Bytes(), err
  366. }
  367. // Create next tree with a position based on Encoder.line
  368. func (e *Encoder) nextTree() *Tree {
  369. return newTreeWithPosition(Position{Line: e.line, Col: 1})
  370. }
  371. // Convert given marshal struct or map value to toml tree
  372. func (e *Encoder) valueToTree(mtype reflect.Type, mval reflect.Value) (*Tree, error) {
  373. if mtype.Kind() == reflect.Ptr {
  374. return e.valueToTree(mtype.Elem(), mval.Elem())
  375. }
  376. tval := e.nextTree()
  377. switch mtype.Kind() {
  378. case reflect.Struct:
  379. switch mval.Interface().(type) {
  380. case Tree:
  381. reflect.ValueOf(tval).Elem().Set(mval)
  382. default:
  383. for i := 0; i < mtype.NumField(); i++ {
  384. mtypef, mvalf := mtype.Field(i), mval.Field(i)
  385. opts := tomlOptions(mtypef, e.annotation)
  386. if opts.include && ((mtypef.Type.Kind() != reflect.Interface && !opts.omitempty) || !isZero(mvalf)) {
  387. val, err := e.valueToToml(mtypef.Type, mvalf)
  388. if err != nil {
  389. return nil, err
  390. }
  391. if tree, ok := val.(*Tree); ok && mtypef.Anonymous && !opts.nameFromTag && !e.promoteAnon {
  392. e.appendTree(tval, tree)
  393. } else {
  394. val = e.wrapTomlValue(val, tval)
  395. tval.SetPathWithOptions([]string{opts.name}, SetOptions{
  396. Comment: opts.comment,
  397. Commented: opts.commented,
  398. Multiline: opts.multiline,
  399. Literal: opts.literal,
  400. }, val)
  401. }
  402. }
  403. }
  404. }
  405. case reflect.Map:
  406. keys := mval.MapKeys()
  407. if e.order == OrderPreserve && len(keys) > 0 {
  408. // Sorting []reflect.Value is not straight forward.
  409. //
  410. // OrderPreserve will support deterministic results when string is used
  411. // as the key to maps.
  412. typ := keys[0].Type()
  413. kind := keys[0].Kind()
  414. if kind == reflect.String {
  415. ikeys := make([]string, len(keys))
  416. for i := range keys {
  417. ikeys[i] = keys[i].Interface().(string)
  418. }
  419. sort.Strings(ikeys)
  420. for i := range ikeys {
  421. keys[i] = reflect.ValueOf(ikeys[i]).Convert(typ)
  422. }
  423. }
  424. }
  425. for _, key := range keys {
  426. mvalf := mval.MapIndex(key)
  427. if (mtype.Elem().Kind() == reflect.Ptr || mtype.Elem().Kind() == reflect.Interface) && mvalf.IsNil() {
  428. continue
  429. }
  430. val, err := e.valueToToml(mtype.Elem(), mvalf)
  431. if err != nil {
  432. return nil, err
  433. }
  434. val = e.wrapTomlValue(val, tval)
  435. if e.quoteMapKeys {
  436. keyStr, err := tomlValueStringRepresentation(key.String(), "", "", e.order, e.arraysOneElementPerLine)
  437. if err != nil {
  438. return nil, err
  439. }
  440. tval.SetPath([]string{keyStr}, val)
  441. } else {
  442. tval.SetPath([]string{key.String()}, val)
  443. }
  444. }
  445. }
  446. return tval, nil
  447. }
  448. // Convert given marshal slice to slice of Toml trees
  449. func (e *Encoder) valueToTreeSlice(mtype reflect.Type, mval reflect.Value) ([]*Tree, error) {
  450. tval := make([]*Tree, mval.Len(), mval.Len())
  451. for i := 0; i < mval.Len(); i++ {
  452. val, err := e.valueToTree(mtype.Elem(), mval.Index(i))
  453. if err != nil {
  454. return nil, err
  455. }
  456. tval[i] = val
  457. }
  458. return tval, nil
  459. }
  460. // Convert given marshal slice to slice of toml values
  461. func (e *Encoder) valueToOtherSlice(mtype reflect.Type, mval reflect.Value) (interface{}, error) {
  462. tval := make([]interface{}, mval.Len(), mval.Len())
  463. for i := 0; i < mval.Len(); i++ {
  464. val, err := e.valueToToml(mtype.Elem(), mval.Index(i))
  465. if err != nil {
  466. return nil, err
  467. }
  468. tval[i] = val
  469. }
  470. return tval, nil
  471. }
  472. // Convert given marshal value to toml value
  473. func (e *Encoder) valueToToml(mtype reflect.Type, mval reflect.Value) (interface{}, error) {
  474. if mtype.Kind() == reflect.Ptr {
  475. switch {
  476. case isCustomMarshaler(mtype):
  477. return callCustomMarshaler(mval)
  478. case isTextMarshaler(mtype):
  479. b, err := callTextMarshaler(mval)
  480. return string(b), err
  481. default:
  482. return e.valueToToml(mtype.Elem(), mval.Elem())
  483. }
  484. }
  485. if mtype.Kind() == reflect.Interface {
  486. return e.valueToToml(mval.Elem().Type(), mval.Elem())
  487. }
  488. switch {
  489. case isCustomMarshaler(mtype):
  490. return callCustomMarshaler(mval)
  491. case isTextMarshaler(mtype):
  492. b, err := callTextMarshaler(mval)
  493. return string(b), err
  494. case isTree(mtype):
  495. return e.valueToTree(mtype, mval)
  496. case isOtherSequence(mtype), isCustomMarshalerSequence(mtype), isTextMarshalerSequence(mtype):
  497. return e.valueToOtherSlice(mtype, mval)
  498. case isTreeSequence(mtype):
  499. return e.valueToTreeSlice(mtype, mval)
  500. default:
  501. switch mtype.Kind() {
  502. case reflect.Bool:
  503. return mval.Bool(), nil
  504. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  505. if mtype.Kind() == reflect.Int64 && mtype == reflect.TypeOf(time.Duration(1)) {
  506. return fmt.Sprint(mval), nil
  507. }
  508. return mval.Int(), nil
  509. case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
  510. return mval.Uint(), nil
  511. case reflect.Float32, reflect.Float64:
  512. return mval.Float(), nil
  513. case reflect.String:
  514. return mval.String(), nil
  515. case reflect.Struct:
  516. return mval.Interface(), nil
  517. default:
  518. return nil, fmt.Errorf("Marshal can't handle %v(%v)", mtype, mtype.Kind())
  519. }
  520. }
  521. }
  522. func (e *Encoder) appendTree(t, o *Tree) error {
  523. for key, value := range o.values {
  524. if _, ok := t.values[key]; ok {
  525. continue
  526. }
  527. if tomlValue, ok := value.(*tomlValue); ok {
  528. tomlValue.position.Col = t.position.Col
  529. }
  530. t.values[key] = value
  531. }
  532. return nil
  533. }
  534. // Create a toml value with the current line number as the position line
  535. func (e *Encoder) wrapTomlValue(val interface{}, parent *Tree) interface{} {
  536. _, isTree := val.(*Tree)
  537. _, isTreeS := val.([]*Tree)
  538. if isTree || isTreeS {
  539. e.line++
  540. return val
  541. }
  542. ret := &tomlValue{
  543. value: val,
  544. position: Position{
  545. e.line,
  546. parent.position.Col,
  547. },
  548. }
  549. e.line++
  550. return ret
  551. }
  552. // Unmarshal attempts to unmarshal the Tree into a Go struct pointed by v.
  553. // Neither Unmarshaler interfaces nor UnmarshalTOML functions are supported for
  554. // sub-structs, and only definite types can be unmarshaled.
  555. func (t *Tree) Unmarshal(v interface{}) error {
  556. d := Decoder{tval: t, tagName: tagFieldName}
  557. return d.unmarshal(v)
  558. }
  559. // Marshal returns the TOML encoding of Tree.
  560. // See Marshal() documentation for types mapping table.
  561. func (t *Tree) Marshal() ([]byte, error) {
  562. var buf bytes.Buffer
  563. _, err := t.WriteTo(&buf)
  564. if err != nil {
  565. return nil, err
  566. }
  567. return buf.Bytes(), nil
  568. }
  569. // Unmarshal parses the TOML-encoded data and stores the result in the value
  570. // pointed to by v. Behavior is similar to the Go json encoder, except that there
  571. // is no concept of an Unmarshaler interface or UnmarshalTOML function for
  572. // sub-structs, and currently only definite types can be unmarshaled to (i.e. no
  573. // `interface{}`).
  574. //
  575. // The following struct annotations are supported:
  576. //
  577. // toml:"Field" Overrides the field's name to map to.
  578. // default:"foo" Provides a default value.
  579. //
  580. // For default values, only fields of the following types are supported:
  581. // * string
  582. // * bool
  583. // * int
  584. // * int64
  585. // * float64
  586. //
  587. // See Marshal() documentation for types mapping table.
  588. func Unmarshal(data []byte, v interface{}) error {
  589. t, err := LoadReader(bytes.NewReader(data))
  590. if err != nil {
  591. return err
  592. }
  593. return t.Unmarshal(v)
  594. }
  595. // Decoder reads and decodes TOML values from an input stream.
  596. type Decoder struct {
  597. r io.Reader
  598. tval *Tree
  599. encOpts
  600. tagName string
  601. strict bool
  602. visitor visitorState
  603. }
  604. // NewDecoder returns a new decoder that reads from r.
  605. func NewDecoder(r io.Reader) *Decoder {
  606. return &Decoder{
  607. r: r,
  608. encOpts: encOptsDefaults,
  609. tagName: tagFieldName,
  610. }
  611. }
  612. // Decode reads a TOML-encoded value from it's input
  613. // and unmarshals it in the value pointed at by v.
  614. //
  615. // See the documentation for Marshal for details.
  616. func (d *Decoder) Decode(v interface{}) error {
  617. var err error
  618. d.tval, err = LoadReader(d.r)
  619. if err != nil {
  620. return err
  621. }
  622. return d.unmarshal(v)
  623. }
  624. // SetTagName allows changing default tag "toml"
  625. func (d *Decoder) SetTagName(v string) *Decoder {
  626. d.tagName = v
  627. return d
  628. }
  629. // Strict allows changing to strict decoding. Any fields that are found in the
  630. // input data and do not have a corresponding struct member cause an error.
  631. func (d *Decoder) Strict(strict bool) *Decoder {
  632. d.strict = strict
  633. return d
  634. }
  635. func (d *Decoder) unmarshal(v interface{}) error {
  636. mtype := reflect.TypeOf(v)
  637. if mtype == nil {
  638. return errors.New("nil cannot be unmarshaled from TOML")
  639. }
  640. if mtype.Kind() != reflect.Ptr {
  641. return errors.New("only a pointer to struct or map can be unmarshaled from TOML")
  642. }
  643. elem := mtype.Elem()
  644. switch elem.Kind() {
  645. case reflect.Struct, reflect.Map:
  646. case reflect.Interface:
  647. elem = mapStringInterfaceType
  648. default:
  649. return errors.New("only a pointer to struct or map can be unmarshaled from TOML")
  650. }
  651. if reflect.ValueOf(v).IsNil() {
  652. return errors.New("nil pointer cannot be unmarshaled from TOML")
  653. }
  654. vv := reflect.ValueOf(v).Elem()
  655. if d.strict {
  656. d.visitor = newVisitorState(d.tval)
  657. }
  658. sval, err := d.valueFromTree(elem, d.tval, &vv)
  659. if err != nil {
  660. return err
  661. }
  662. if err := d.visitor.validate(); err != nil {
  663. return err
  664. }
  665. reflect.ValueOf(v).Elem().Set(sval)
  666. return nil
  667. }
  668. // Convert toml tree to marshal struct or map, using marshal type. When mval1
  669. // is non-nil, merge fields into the given value instead of allocating a new one.
  670. func (d *Decoder) valueFromTree(mtype reflect.Type, tval *Tree, mval1 *reflect.Value) (reflect.Value, error) {
  671. if mtype.Kind() == reflect.Ptr {
  672. return d.unwrapPointer(mtype, tval, mval1)
  673. }
  674. // Check if pointer to value implements the Unmarshaler interface.
  675. if mvalPtr := reflect.New(mtype); isCustomUnmarshaler(mvalPtr.Type()) {
  676. d.visitor.visitAll()
  677. if tval == nil {
  678. return mvalPtr.Elem(), nil
  679. }
  680. if err := callCustomUnmarshaler(mvalPtr, tval.ToMap()); err != nil {
  681. return reflect.ValueOf(nil), fmt.Errorf("unmarshal toml: %v", err)
  682. }
  683. return mvalPtr.Elem(), nil
  684. }
  685. var mval reflect.Value
  686. switch mtype.Kind() {
  687. case reflect.Struct:
  688. if mval1 != nil {
  689. mval = *mval1
  690. } else {
  691. mval = reflect.New(mtype).Elem()
  692. }
  693. switch mval.Interface().(type) {
  694. case Tree:
  695. mval.Set(reflect.ValueOf(tval).Elem())
  696. default:
  697. for i := 0; i < mtype.NumField(); i++ {
  698. mtypef := mtype.Field(i)
  699. an := annotation{tag: d.tagName}
  700. opts := tomlOptions(mtypef, an)
  701. if !opts.include {
  702. continue
  703. }
  704. baseKey := opts.name
  705. keysToTry := []string{
  706. baseKey,
  707. strings.ToLower(baseKey),
  708. strings.ToTitle(baseKey),
  709. strings.ToLower(string(baseKey[0])) + baseKey[1:],
  710. }
  711. found := false
  712. if tval != nil {
  713. for _, key := range keysToTry {
  714. exists := tval.HasPath([]string{key})
  715. if !exists {
  716. continue
  717. }
  718. d.visitor.push(key)
  719. val := tval.GetPath([]string{key})
  720. fval := mval.Field(i)
  721. mvalf, err := d.valueFromToml(mtypef.Type, val, &fval)
  722. if err != nil {
  723. return mval, formatError(err, tval.GetPositionPath([]string{key}))
  724. }
  725. mval.Field(i).Set(mvalf)
  726. found = true
  727. d.visitor.pop()
  728. break
  729. }
  730. }
  731. if !found && opts.defaultValue != "" {
  732. mvalf := mval.Field(i)
  733. var val interface{}
  734. var err error
  735. switch mvalf.Kind() {
  736. case reflect.String:
  737. val = opts.defaultValue
  738. case reflect.Bool:
  739. val, err = strconv.ParseBool(opts.defaultValue)
  740. case reflect.Uint:
  741. val, err = strconv.ParseUint(opts.defaultValue, 10, 0)
  742. case reflect.Uint8:
  743. val, err = strconv.ParseUint(opts.defaultValue, 10, 8)
  744. case reflect.Uint16:
  745. val, err = strconv.ParseUint(opts.defaultValue, 10, 16)
  746. case reflect.Uint32:
  747. val, err = strconv.ParseUint(opts.defaultValue, 10, 32)
  748. case reflect.Uint64:
  749. val, err = strconv.ParseUint(opts.defaultValue, 10, 64)
  750. case reflect.Int:
  751. val, err = strconv.ParseInt(opts.defaultValue, 10, 0)
  752. case reflect.Int8:
  753. val, err = strconv.ParseInt(opts.defaultValue, 10, 8)
  754. case reflect.Int16:
  755. val, err = strconv.ParseInt(opts.defaultValue, 10, 16)
  756. case reflect.Int32:
  757. val, err = strconv.ParseInt(opts.defaultValue, 10, 32)
  758. case reflect.Int64:
  759. // Check if the provided number has a non-numeric extension.
  760. var hasExtension bool
  761. if len(opts.defaultValue) > 0 {
  762. lastChar := opts.defaultValue[len(opts.defaultValue)-1]
  763. if lastChar < '0' || lastChar > '9' {
  764. hasExtension = true
  765. }
  766. }
  767. // If the value is a time.Duration with extension, parse as duration.
  768. // If the value is an int64 or a time.Duration without extension, parse as number.
  769. if hasExtension && mvalf.Type().String() == "time.Duration" {
  770. val, err = time.ParseDuration(opts.defaultValue)
  771. } else {
  772. val, err = strconv.ParseInt(opts.defaultValue, 10, 64)
  773. }
  774. case reflect.Float32:
  775. val, err = strconv.ParseFloat(opts.defaultValue, 32)
  776. case reflect.Float64:
  777. val, err = strconv.ParseFloat(opts.defaultValue, 64)
  778. default:
  779. return mvalf, fmt.Errorf("unsupported field type for default option")
  780. }
  781. if err != nil {
  782. return mvalf, err
  783. }
  784. mvalf.Set(reflect.ValueOf(val).Convert(mvalf.Type()))
  785. }
  786. // save the old behavior above and try to check structs
  787. if !found && opts.defaultValue == "" && mtypef.Type.Kind() == reflect.Struct {
  788. tmpTval := tval
  789. if !mtypef.Anonymous {
  790. tmpTval = nil
  791. }
  792. fval := mval.Field(i)
  793. v, err := d.valueFromTree(mtypef.Type, tmpTval, &fval)
  794. if err != nil {
  795. return v, err
  796. }
  797. mval.Field(i).Set(v)
  798. }
  799. }
  800. }
  801. case reflect.Map:
  802. mval = reflect.MakeMap(mtype)
  803. for _, key := range tval.Keys() {
  804. d.visitor.push(key)
  805. // TODO: path splits key
  806. val := tval.GetPath([]string{key})
  807. mvalf, err := d.valueFromToml(mtype.Elem(), val, nil)
  808. if err != nil {
  809. return mval, formatError(err, tval.GetPositionPath([]string{key}))
  810. }
  811. mval.SetMapIndex(reflect.ValueOf(key).Convert(mtype.Key()), mvalf)
  812. d.visitor.pop()
  813. }
  814. }
  815. return mval, nil
  816. }
  817. // Convert toml value to marshal struct/map slice, using marshal type
  818. func (d *Decoder) valueFromTreeSlice(mtype reflect.Type, tval []*Tree) (reflect.Value, error) {
  819. mval, err := makeSliceOrArray(mtype, len(tval))
  820. if err != nil {
  821. return mval, err
  822. }
  823. for i := 0; i < len(tval); i++ {
  824. d.visitor.push(strconv.Itoa(i))
  825. val, err := d.valueFromTree(mtype.Elem(), tval[i], nil)
  826. if err != nil {
  827. return mval, err
  828. }
  829. mval.Index(i).Set(val)
  830. d.visitor.pop()
  831. }
  832. return mval, nil
  833. }
  834. // Convert toml value to marshal primitive slice, using marshal type
  835. func (d *Decoder) valueFromOtherSlice(mtype reflect.Type, tval []interface{}) (reflect.Value, error) {
  836. mval, err := makeSliceOrArray(mtype, len(tval))
  837. if err != nil {
  838. return mval, err
  839. }
  840. for i := 0; i < len(tval); i++ {
  841. val, err := d.valueFromToml(mtype.Elem(), tval[i], nil)
  842. if err != nil {
  843. return mval, err
  844. }
  845. mval.Index(i).Set(val)
  846. }
  847. return mval, nil
  848. }
  849. // Convert toml value to marshal primitive slice, using marshal type
  850. func (d *Decoder) valueFromOtherSliceI(mtype reflect.Type, tval interface{}) (reflect.Value, error) {
  851. val := reflect.ValueOf(tval)
  852. length := val.Len()
  853. mval, err := makeSliceOrArray(mtype, length)
  854. if err != nil {
  855. return mval, err
  856. }
  857. for i := 0; i < length; i++ {
  858. val, err := d.valueFromToml(mtype.Elem(), val.Index(i).Interface(), nil)
  859. if err != nil {
  860. return mval, err
  861. }
  862. mval.Index(i).Set(val)
  863. }
  864. return mval, nil
  865. }
  866. // Create a new slice or a new array with specified length
  867. func makeSliceOrArray(mtype reflect.Type, tLength int) (reflect.Value, error) {
  868. var mval reflect.Value
  869. switch mtype.Kind() {
  870. case reflect.Slice:
  871. mval = reflect.MakeSlice(mtype, tLength, tLength)
  872. case reflect.Array:
  873. mval = reflect.New(reflect.ArrayOf(mtype.Len(), mtype.Elem())).Elem()
  874. if tLength > mtype.Len() {
  875. return mval, fmt.Errorf("unmarshal: TOML array length (%v) exceeds destination array length (%v)", tLength, mtype.Len())
  876. }
  877. }
  878. return mval, nil
  879. }
  880. // Convert toml value to marshal value, using marshal type. When mval1 is non-nil
  881. // and the given type is a struct value, merge fields into it.
  882. func (d *Decoder) valueFromToml(mtype reflect.Type, tval interface{}, mval1 *reflect.Value) (reflect.Value, error) {
  883. if mtype.Kind() == reflect.Ptr {
  884. return d.unwrapPointer(mtype, tval, mval1)
  885. }
  886. switch t := tval.(type) {
  887. case *Tree:
  888. var mval11 *reflect.Value
  889. if mtype.Kind() == reflect.Struct {
  890. mval11 = mval1
  891. }
  892. if isTree(mtype) {
  893. return d.valueFromTree(mtype, t, mval11)
  894. }
  895. if mtype.Kind() == reflect.Interface {
  896. if mval1 == nil || mval1.IsNil() {
  897. return d.valueFromTree(reflect.TypeOf(map[string]interface{}{}), t, nil)
  898. } else {
  899. return d.valueFromToml(mval1.Elem().Type(), t, nil)
  900. }
  901. }
  902. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to a tree", tval, tval)
  903. case []*Tree:
  904. if isTreeSequence(mtype) {
  905. return d.valueFromTreeSlice(mtype, t)
  906. }
  907. if mtype.Kind() == reflect.Interface {
  908. if mval1 == nil || mval1.IsNil() {
  909. return d.valueFromTreeSlice(reflect.TypeOf([]map[string]interface{}{}), t)
  910. } else {
  911. ival := mval1.Elem()
  912. return d.valueFromToml(mval1.Elem().Type(), t, &ival)
  913. }
  914. }
  915. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to trees", tval, tval)
  916. case []interface{}:
  917. d.visitor.visit()
  918. if isOtherSequence(mtype) {
  919. return d.valueFromOtherSlice(mtype, t)
  920. }
  921. if mtype.Kind() == reflect.Interface {
  922. if mval1 == nil || mval1.IsNil() {
  923. return d.valueFromOtherSlice(reflect.TypeOf([]interface{}{}), t)
  924. } else {
  925. ival := mval1.Elem()
  926. return d.valueFromToml(mval1.Elem().Type(), t, &ival)
  927. }
  928. }
  929. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to a slice", tval, tval)
  930. default:
  931. d.visitor.visit()
  932. mvalPtr := reflect.New(mtype)
  933. // Check if pointer to value implements the Unmarshaler interface.
  934. if isCustomUnmarshaler(mvalPtr.Type()) {
  935. if err := callCustomUnmarshaler(mvalPtr, tval); err != nil {
  936. return reflect.ValueOf(nil), fmt.Errorf("unmarshal toml: %v", err)
  937. }
  938. return mvalPtr.Elem(), nil
  939. }
  940. // Check if pointer to value implements the encoding.TextUnmarshaler.
  941. if isTextUnmarshaler(mvalPtr.Type()) && !isTimeType(mtype) {
  942. if err := d.unmarshalText(tval, mvalPtr); err != nil {
  943. return reflect.ValueOf(nil), fmt.Errorf("unmarshal text: %v", err)
  944. }
  945. return mvalPtr.Elem(), nil
  946. }
  947. switch mtype.Kind() {
  948. case reflect.Bool, reflect.Struct:
  949. val := reflect.ValueOf(tval)
  950. switch val.Type() {
  951. case localDateType:
  952. localDate := val.Interface().(LocalDate)
  953. switch mtype {
  954. case timeType:
  955. return reflect.ValueOf(time.Date(localDate.Year, localDate.Month, localDate.Day, 0, 0, 0, 0, time.Local)), nil
  956. }
  957. case localDateTimeType:
  958. localDateTime := val.Interface().(LocalDateTime)
  959. switch mtype {
  960. case timeType:
  961. return reflect.ValueOf(time.Date(
  962. localDateTime.Date.Year,
  963. localDateTime.Date.Month,
  964. localDateTime.Date.Day,
  965. localDateTime.Time.Hour,
  966. localDateTime.Time.Minute,
  967. localDateTime.Time.Second,
  968. localDateTime.Time.Nanosecond,
  969. time.Local)), nil
  970. }
  971. }
  972. // if this passes for when mtype is reflect.Struct, tval is a time.LocalTime
  973. if !val.Type().ConvertibleTo(mtype) {
  974. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v", tval, tval, mtype.String())
  975. }
  976. return val.Convert(mtype), nil
  977. case reflect.String:
  978. val := reflect.ValueOf(tval)
  979. // stupidly, int64 is convertible to string. So special case this.
  980. if !val.Type().ConvertibleTo(mtype) || val.Kind() == reflect.Int64 {
  981. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v", tval, tval, mtype.String())
  982. }
  983. return val.Convert(mtype), nil
  984. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  985. val := reflect.ValueOf(tval)
  986. if mtype.Kind() == reflect.Int64 && mtype == reflect.TypeOf(time.Duration(1)) && val.Kind() == reflect.String {
  987. d, err := time.ParseDuration(val.String())
  988. if err != nil {
  989. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v. %s", tval, tval, mtype.String(), err)
  990. }
  991. return reflect.ValueOf(d), nil
  992. }
  993. if !val.Type().ConvertibleTo(mtype) || val.Kind() == reflect.Float64 {
  994. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v", tval, tval, mtype.String())
  995. }
  996. if reflect.Indirect(reflect.New(mtype)).OverflowInt(val.Convert(reflect.TypeOf(int64(0))).Int()) {
  997. return reflect.ValueOf(nil), fmt.Errorf("%v(%T) would overflow %v", tval, tval, mtype.String())
  998. }
  999. return val.Convert(mtype), nil
  1000. case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
  1001. val := reflect.ValueOf(tval)
  1002. if !val.Type().ConvertibleTo(mtype) || val.Kind() == reflect.Float64 {
  1003. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v", tval, tval, mtype.String())
  1004. }
  1005. if val.Type().Kind() != reflect.Uint64 && val.Convert(reflect.TypeOf(int(1))).Int() < 0 {
  1006. return reflect.ValueOf(nil), fmt.Errorf("%v(%T) is negative so does not fit in %v", tval, tval, mtype.String())
  1007. }
  1008. if reflect.Indirect(reflect.New(mtype)).OverflowUint(val.Convert(reflect.TypeOf(uint64(0))).Uint()) {
  1009. return reflect.ValueOf(nil), fmt.Errorf("%v(%T) would overflow %v", tval, tval, mtype.String())
  1010. }
  1011. return val.Convert(mtype), nil
  1012. case reflect.Float32, reflect.Float64:
  1013. val := reflect.ValueOf(tval)
  1014. if !val.Type().ConvertibleTo(mtype) || val.Kind() == reflect.Int64 {
  1015. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v", tval, tval, mtype.String())
  1016. }
  1017. if reflect.Indirect(reflect.New(mtype)).OverflowFloat(val.Convert(reflect.TypeOf(float64(0))).Float()) {
  1018. return reflect.ValueOf(nil), fmt.Errorf("%v(%T) would overflow %v", tval, tval, mtype.String())
  1019. }
  1020. return val.Convert(mtype), nil
  1021. case reflect.Interface:
  1022. if mval1 == nil || mval1.IsNil() {
  1023. return reflect.ValueOf(tval), nil
  1024. } else {
  1025. ival := mval1.Elem()
  1026. return d.valueFromToml(mval1.Elem().Type(), t, &ival)
  1027. }
  1028. case reflect.Slice, reflect.Array:
  1029. if isOtherSequence(mtype) && isOtherSequence(reflect.TypeOf(t)) {
  1030. return d.valueFromOtherSliceI(mtype, t)
  1031. }
  1032. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v(%v)", tval, tval, mtype, mtype.Kind())
  1033. default:
  1034. return reflect.ValueOf(nil), fmt.Errorf("Can't convert %v(%T) to %v(%v)", tval, tval, mtype, mtype.Kind())
  1035. }
  1036. }
  1037. }
  1038. func (d *Decoder) unwrapPointer(mtype reflect.Type, tval interface{}, mval1 *reflect.Value) (reflect.Value, error) {
  1039. var melem *reflect.Value
  1040. if mval1 != nil && !mval1.IsNil() && (mtype.Elem().Kind() == reflect.Struct || mtype.Elem().Kind() == reflect.Interface) {
  1041. elem := mval1.Elem()
  1042. melem = &elem
  1043. }
  1044. val, err := d.valueFromToml(mtype.Elem(), tval, melem)
  1045. if err != nil {
  1046. return reflect.ValueOf(nil), err
  1047. }
  1048. mval := reflect.New(mtype.Elem())
  1049. mval.Elem().Set(val)
  1050. return mval, nil
  1051. }
  1052. func (d *Decoder) unmarshalText(tval interface{}, mval reflect.Value) error {
  1053. var buf bytes.Buffer
  1054. fmt.Fprint(&buf, tval)
  1055. return callTextUnmarshaler(mval, buf.Bytes())
  1056. }
  1057. func tomlOptions(vf reflect.StructField, an annotation) tomlOpts {
  1058. tag := vf.Tag.Get(an.tag)
  1059. parse := strings.Split(tag, ",")
  1060. var comment string
  1061. if c := vf.Tag.Get(an.comment); c != "" {
  1062. comment = c
  1063. }
  1064. commented, _ := strconv.ParseBool(vf.Tag.Get(an.commented))
  1065. multiline, _ := strconv.ParseBool(vf.Tag.Get(an.multiline))
  1066. literal, _ := strconv.ParseBool(vf.Tag.Get(an.literal))
  1067. defaultValue := vf.Tag.Get(tagDefault)
  1068. result := tomlOpts{
  1069. name: vf.Name,
  1070. nameFromTag: false,
  1071. comment: comment,
  1072. commented: commented,
  1073. multiline: multiline,
  1074. literal: literal,
  1075. include: true,
  1076. omitempty: false,
  1077. defaultValue: defaultValue,
  1078. }
  1079. if parse[0] != "" {
  1080. if parse[0] == "-" && len(parse) == 1 {
  1081. result.include = false
  1082. } else {
  1083. result.name = strings.Trim(parse[0], " ")
  1084. result.nameFromTag = true
  1085. }
  1086. }
  1087. if vf.PkgPath != "" {
  1088. result.include = false
  1089. }
  1090. if len(parse) > 1 && strings.Trim(parse[1], " ") == "omitempty" {
  1091. result.omitempty = true
  1092. }
  1093. if vf.Type.Kind() == reflect.Ptr {
  1094. result.omitempty = true
  1095. }
  1096. return result
  1097. }
  1098. func isZero(val reflect.Value) bool {
  1099. switch val.Type().Kind() {
  1100. case reflect.Slice, reflect.Array, reflect.Map:
  1101. return val.Len() == 0
  1102. default:
  1103. return reflect.DeepEqual(val.Interface(), reflect.Zero(val.Type()).Interface())
  1104. }
  1105. }
  1106. func formatError(err error, pos Position) error {
  1107. if err.Error()[0] == '(' { // Error already contains position information
  1108. return err
  1109. }
  1110. return fmt.Errorf("%s: %s", pos, err)
  1111. }
  1112. // visitorState keeps track of which keys were unmarshaled.
  1113. type visitorState struct {
  1114. tree *Tree
  1115. path []string
  1116. keys map[string]struct{}
  1117. active bool
  1118. }
  1119. func newVisitorState(tree *Tree) visitorState {
  1120. path, result := []string{}, map[string]struct{}{}
  1121. insertKeys(path, result, tree)
  1122. return visitorState{
  1123. tree: tree,
  1124. path: path[:0],
  1125. keys: result,
  1126. active: true,
  1127. }
  1128. }
  1129. func (s *visitorState) push(key string) {
  1130. if s.active {
  1131. s.path = append(s.path, key)
  1132. }
  1133. }
  1134. func (s *visitorState) pop() {
  1135. if s.active {
  1136. s.path = s.path[:len(s.path)-1]
  1137. }
  1138. }
  1139. func (s *visitorState) visit() {
  1140. if s.active {
  1141. delete(s.keys, strings.Join(s.path, "."))
  1142. }
  1143. }
  1144. func (s *visitorState) visitAll() {
  1145. if s.active {
  1146. for k := range s.keys {
  1147. if strings.HasPrefix(k, strings.Join(s.path, ".")) {
  1148. delete(s.keys, k)
  1149. }
  1150. }
  1151. }
  1152. }
  1153. func (s *visitorState) validate() error {
  1154. if !s.active {
  1155. return nil
  1156. }
  1157. undecoded := make([]string, 0, len(s.keys))
  1158. for key := range s.keys {
  1159. undecoded = append(undecoded, key)
  1160. }
  1161. sort.Strings(undecoded)
  1162. if len(undecoded) > 0 {
  1163. return fmt.Errorf("undecoded keys: %q", undecoded)
  1164. }
  1165. return nil
  1166. }
  1167. func insertKeys(path []string, m map[string]struct{}, tree *Tree) {
  1168. for k, v := range tree.values {
  1169. switch node := v.(type) {
  1170. case []*Tree:
  1171. for i, item := range node {
  1172. insertKeys(append(path, k, strconv.Itoa(i)), m, item)
  1173. }
  1174. case *Tree:
  1175. insertKeys(append(path, k), m, node)
  1176. case *tomlValue:
  1177. m[strings.Join(append(path, k), ".")] = struct{}{}
  1178. }
  1179. }
  1180. }