feat: add field comments, local time zone decoding and in-value cancellation
Test / test (push) Successful in 1m32s

Assisted-by: GLM 5.3 Flash
This commit is contained in:
2026-09-22 00:44:23 +02:00
parent 71bd82a7a5
commit d18935ebc2
8 changed files with 307 additions and 11 deletions
+15 -1
View File
@@ -314,6 +314,12 @@ error. The date-time types take a bare timestamp and never a quoted string, so a
document that writes a date-time with quotes does not decode into them, and
neither `encoding.TextUnmarshaler` nor the embedded `time.Time` changes that.
`NewDecoder().LocalTimeLocation(loc)` lets a local date-time fill a plain
`time.Time` destination as well: the wall-clock value is carried in the
location given, relabelled rather than shifted, so `07:32` in the document is
`07:32` in the zone. Without the option the wrapper types are the only
destinations a local kind fills.
### Arrays of tables
A `[[a]]` block parses into a `[]map[string]any` element of the tree. When the
@@ -438,7 +444,9 @@ one, so it does not depend on map iteration order.
`ParseContext`, `UnmarshalContext` and `(*Decoder).DecodeContext` accept a
`context.Context`. An already-cancelled context short-circuits with
`context.Canceled` before any work begins; afterwards the context is checked
every 64 top-level statements.
every 64 top-level statements, and inside a value too: an array, an inline
table and a multi-line string check every 64 elements or lines, so one huge
value cannot hold the parse past its cancellation.
### Flow
@@ -509,6 +517,11 @@ its key whether the table it came from was written inline or under a header.
embedded struct tagged this way does the same. A field holding an array of
tables is an error under `inline`, because the inline form would re-parse
as a value array and change the value's Go type.
- `comment=text` carries a comment for the field, which
`NewEncoder().EmitFieldComments()` prints above the field's line or
header, each line of a multi-line text with its own `# ` marker. Go doc
comments are not visible to reflection, so the tag is the channel that
carries the text; without the encoder option the tag is ignored.
```go
type Config struct {
@@ -817,6 +830,7 @@ encoder:
| `OmitEmptyArrays()` | off | skip `key = []` for empty scalar arrays |
| `UseLiteralMultiline(threshold int)` | `0` | emit multi-line strings of at least `threshold` bytes as literal `'''...'''` |
| `InlineTables(threshold int)` | `0` | write a sub-table inline when its single-line form is at most `threshold` bytes |
| `EmitFieldComments()` | off | print the `comment=` tag option of a field above its line or header |
```go
out, err := interpres.NewEncoder().