feat(go-config): multi-format codecs, envc CLI, fixtures, ASRs

- Module github.com/eslider/go-config with env/yaml/json/ini packages
- internal: source, keymap, merge, structconv, bytesutil
- cmd/envc: convert, get, merge
- docs/asr ASR-0001..0008, README/CHANGELOG/AGENTS refresh
- golangci-lint v2 config; tests + fixtures

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-05-02 14:04:01 +01:00
co-authored by Cursor
parent 288a5b600c
commit c575341178
75 changed files with 2810 additions and 528 deletions
+16 -22
View File
@@ -1,44 +1,39 @@
# AGENTS.md — `go-env`
# AGENTS.md — `go-config`
This module is part of the eSlider `go-*` library standard (inventar ASR-0008).
## Purpose
Decode `os.Environ()` into Go structs. Extracted from
`produktor.io/ai-fabric/pkg/env` on 2026-04-24.
Convert **env**, **YAML**, **JSON**, and **INI** into nested `map[string]any` and Go structs (and back), with multi-source merging and the `envc` CLI.
## Public API surface
- `env.Unmarshal(dst any, opts ...Option) error`
- `env.UnmarshalPrefix(dst any, prefix string, opts ...Option) error`
- `env.AsMap() map[string]any`
- `env.AsMapPrefix(prefix string) map[string]any`
- Options: `WithTrim`, `WithWeaklyTyped`, `WithTagName`, `WithDecodeHook`
- Subpackages: `env`, `yaml`, `json`, `ini` — each exports `New`, `(*Codec).Map`, `Unmarshal`, `UnmarshalContext`, `Marshal`, `WriteTo`, and format-specific options.
- `cmd/envc` — binary `envc`: `convert`, `get`, `merge`.
- Internals under `internal/` are not stable API.
Breaking changes require a new major version tag (SemVer). Internal helpers
(`asMapFromEnviron`, `trimStringHook`, `insertPath`) are unexported and
may change without notice.
Breaking changes require a new major SemVer tag (or `/v2` module path if the policy changes).
## Testing policy
Follows the eSlider "no synthetic mocks" policy:
Follows the eSlider "no synthetic mocks" policy (see [.cursor/rules/no-synthetic-mocks.mdc](.cursor/rules/no-synthetic-mocks.mdc)):
- **Unit tests** (`env_test.go`): pure inputs only. We pass synthetic
`environ` slices to `asMapFromEnviron` — that is not a mock of anything
external; it's the normal way to test a pure function. Use `t.Setenv`
for `Unmarshal*` happy-path tests since Go's `os.Environ` lookup is
well-defined local behaviour, not a vendor protocol.
- **No `httptest`** — this library has no HTTP surface.
- **No integration-test build tag** — everything is in-process.
- **Unit tests** — pure inputs for merge, keymap, structconv, env flat-map helpers.
- **`httptest`** — allowed only to test **our** HTTP client behaviour in `internal/source` (not third-party API emulation).
- **Fixtures** — real files under `fixtures/`; `testfixtures` resolves paths from module root.
## Decisions
Architecture Significant Requirements: [docs/asr/README.md](docs/asr/README.md).
## Checklist before release
```sh
cd go-env
cd go-config
go mod tidy
go vet ./...
go test -race -count=1 ./...
golangci-lint run --timeout 5m # same preset as go-onlyoffice
golangci-lint run --timeout 5m
```
Bump `CHANGELOG.md`, tag `vX.Y.Z`, push.
@@ -46,5 +41,4 @@ Bump `CHANGELOG.md`, tag `vX.Y.Z`, push.
## Related
- `inventar/docs/asr/ASR-0008.md` — Go library module conventions
- `inventar/docs/asr/ASR-0008-ai-fabric-audit.md` — why this module exists
- `go-onlyoffice/AGENTS.md` — reference for the eSlider library template