From 7e789d470fa6c360aff95cb052923aea7d272dc0 Mon Sep 17 00:00:00 2001 From: Lilleman auf Larv Date: Mon, 14 Sep 2026 23:39:07 +0200 Subject: [PATCH] Name the record entry points after the string ones --- README.md | 12 ++++++------ cmd/fejkdata/main.go | 2 +- record.go | 8 ++++---- todo.md | 2 -- 4 files changed, 11 insertions(+), 13 deletions(-) diff --git a/README.md b/README.md index a86800e..02c7f22 100644 --- a/README.md +++ b/README.md @@ -82,7 +82,7 @@ For structured output a record writes the row for you. A record is a template seen as columns: its fields are the columns, its `format` the whole. `--format json|ndjson|csv|sql` writes the records; the library's -`Record` (below) hands back the columns. Every column is a string — typed scalars +`FakeRecord` (below) hands back the columns. Every column is a string — typed scalars are on the release checklist, see [`todo.md`](todo.md). Save `mydata/users.json`: @@ -152,9 +152,9 @@ paths := f.List() // every path Fake accepts, sorted v, err = f.FakeTemplate("name: {/sv_SE.person.last}") // compile + render in one call t, err := f.NewTemplate(`{"format":"name: {x}","x":["bosse","lina"]}`) // compile once v = t.Fake() // render many times, no re-parse -r, err := f.Record("users") // one record: each field a column +r, err := f.FakeRecord("users") // one record: each field a column s := r.JSON() // {"first":"Ada","last":"Lovelace"} -r, err = f.FakeRecord(`{"format":"{x}","x":["a","b"]}`) // compile + render inline +r, err = f.FakeRecordTemplate(`{"format":"{x}","x":["a","b"]}`) // compile + render inline ``` | Option | | @@ -166,8 +166,8 @@ r, err = f.FakeRecord(`{"format":"{x}","x":["a","b"]}`) // compile + render inli A `*Record` carries its columns via `Columns()`, and serializes them with `JSON()` (one object), `CSVHeader()`/`CSVLine()`, or `SQLInsert(table)` — the shapes the -CLI's `--format` writes. `Record` and `FakeRecord` take a record; a path or -template that is not one — a bare string, a choice, or a folder — errors. +CLI's `--format` writes. `FakeRecord` and `FakeRecordTemplate` take a record; a +path or template that is not one — a bare string, a choice, or a folder — errors. A `*Generator` is safe for concurrent use; a seeded sequence is reproducible only when drawn from one goroutine. Changing how a value is composed shifts the seeded @@ -526,7 +526,7 @@ tokens add cost in proportion to the output. letters, `{uppercase(x)}` is `x` upper-cased; one name for both would turn on whether the argument looks like a number. - **A record is a template seen as columns, not a second schema format.** A - template's `format` composes its fields into one string; `Record` and + template's `format` composes its fields into one string; `FakeRecord` and `--format` project the same fields as columns. Two views of one dataset, so a record author writes the same JSON they already know, and a column is the same field `Fake` renders by dotted path. The `format` is inert to a record — a diff --git a/cmd/fejkdata/main.go b/cmd/fejkdata/main.go index cfd5909..36b605f 100644 --- a/cmd/fejkdata/main.go +++ b/cmd/fejkdata/main.go @@ -341,7 +341,7 @@ func (in invocation) textDraw(f *fejkdata.Generator, kind argKind, arg string) ( // recordStream builds the record drawer for the argument, plus the INSERT table // a sql format names. func (in invocation) recordStream(f *fejkdata.Generator, kind argKind, arg string) (func() (*fejkdata.Record, error), string, error) { - record := func() (*fejkdata.Record, error) { return f.Record(arg) } + record := func() (*fejkdata.Record, error) { return f.FakeRecord(arg) } if kind == argTemplate { t, err := f.NewRecordTemplate(arg) if err != nil { diff --git a/record.go b/record.go index 4a70eaf..803e041 100644 --- a/record.go +++ b/record.go @@ -92,10 +92,10 @@ func quoteIdent(s string) string { return `"` + strings.ReplaceAll(s, `"`, `""`) + `"` } -// Record renders a path as one record: the template it names, with each direct +// FakeRecord renders a path as one record: the template it names, with each direct // field drawn as a column. Only a category-level template is a record — a path // that descends into a field, or that names a folder or a choice, is an error. -func (f *Generator) Record(path string) (*Record, error) { +func (f *Generator) FakeRecord(path string) (*Record, error) { f.mu.Lock() defer f.mu.Unlock() _, n, tail, err := resolveCategory(f.categories, strings.Split(path, ".")) @@ -164,8 +164,8 @@ func (f *Generator) NewRecordTemplate(input string) (*RecordTemplate, error) { return &RecordTemplate{g: f, t: tm, columns: columns}, nil } -// FakeRecord compiles and renders an inline record in one call. -func (f *Generator) FakeRecord(input string) (*Record, error) { +// FakeRecordTemplate compiles and renders an inline record in one call. +func (f *Generator) FakeRecordTemplate(input string) (*Record, error) { t, err := f.NewRecordTemplate(input) if err != nil { return nil, err diff --git a/todo.md b/todo.md index dae3a44..0c2b28f 100644 --- a/todo.md +++ b/todo.md @@ -6,8 +6,6 @@ The record API lands first, so the data update can use it. ### Record API -- Rename the record entry points after the string ones: `Record(path)` becomes - `FakeRecord(path)`, and `FakeRecord(inline)` becomes `FakeRecordTemplate(inline)`. - Typed columns — a column declares its type, so `json` writes `42` rather than `"42"` and `sql` an unquoted literal: string, integer, number, boolean, and a way to write null. A template that can render a value its type rejects is a