Skip to content

generate

Generate relational synthetic SQL from a hand-authored YAML model, a model inferred from a SQL dump, or an inferred model plus explicit overrides.

Alias: gen (e.g., sql-splitter gen production.sql -o synthetic.sql)

  • Seed relational fixtures — Produce data that satisfies its own primary keys and foreign keys, so it loads cleanly into the same schema
  • Share safe datasets — Ship synthetic dumps that keep a real schema’s shape without exposing its rows
  • Make CI fixtures repeatable — Pin --seed so every run produces byte-identical output
  • Scale a dataset up or down — Multiply or cap row counts with --scale, --rows, and per-table overrides for load tests or small demos
  • Derive a model from a real dump — Profile and infer a starting model automatically, then edit and reuse it

Use redact instead when you must anonymize the real rows rather than synthesize new ones.

generate turns a model into SQL. When you pass a source dump, it derives that model first, without ever loading the full dataset into memory:

  1. Profile — A bounded basic/full streaming profiler samples the dump’s columns within a fixed memory budget
  2. Infer — Structural referential-integrity and column heuristics resolve an explicit per-column rule for each table
  3. Compile — The model is validated and resolved into a plan (row counts, dependency order, key domains)
  4. Render — The engine produces CREATE TABLE DDL and batched INSERT/COPY rows in the target dialect

A hand-authored --config model skips the profile and infer steps. See Profiling and inference for how rules are chosen and Privacy and verification for what --verify audits.

Terminal window
sql-splitter generate [OPTIONS] [INPUT]

Provide a source dump, a complete --config model, or both. A kind: overrides document requires a source dump or base model because it patches the inferred model rather than standing alone.

Terminal window
# Profile production.sql, infer a model, and generate synthetic SQL
sql-splitter generate production.sql -o synthetic.sql
Terminal window
# A pinned seed makes the output byte-identical across runs
sql-splitter generate --config model.yaml --seed 42 -o synthetic.sql
Terminal window
# Write the resolved model without generating SQL, then edit and reuse it
sql-splitter generate production.sql --emit-config model.yaml
sql-splitter generate --config model.yaml -o synthetic.sql
Terminal window
# Patch the inferred model, save the resolved model, and emit 10% of the rows
sql-splitter generate production.sql \
--config overrides.yaml \
--emit-config resolved.yaml \
--scale 0.1 \
-o synthetic.sql
Terminal window
# Parse and compile a complete model; write nothing
sql-splitter generate --config model.yaml --check
# Resolve counts and dependencies without generating rows
sql-splitter generate --config model.yaml --dry-run
# Explain inferred column rules without printing observed values
sql-splitter generate production.sql --dry-run --explain
# Generate, audit exact constraints, then publish atomically
sql-splitter generate --config model.yaml --verify -o synthetic.sql

--strict promotes warning-severity diagnostics to failures; informational diagnostics and advisories stay non-fatal. --quiet suppresses the ordinary human report, but safety advisories still reach stderr.

FlagShortDescriptionDefault
[INPUT]Source SQL dump to profilenone
--config-cComplete model or overrides YAMLnone
--emit-configWrite the resolved complete modelnone
--output-oGenerated SQL; - means stdoutstdout
--profile-depthProfiling depth: basic or fullbasic
--profile-sampleRetained profiling sample capacity1000
--input-dialectForce the source parsing dialectauto-detect
FlagShortDescriptionDefault
--dialectOutput SQL dialectmodel, source, then MySQL
--schema-onlyEmit DDL onlyfalse
--data-onlyEmit row data onlyfalse
--batch-sizeRows per INSERT/COPY batch (1–1,000,000)1000
--no-copyUse PostgreSQL INSERT instead of COPYfalse
--mssql-production-styleAdd production-style MSSQL DDL conventionsfalse
--mssql-goEmit GO every N MSSQL insert batchesevery batch
--compressReserved; currently unavailablenone
FlagShortDescriptionDefault
--scaleMultiply every resolved row countnone
--rowsSet absolute root-table countsnone
--table-rowsPer-table absolute count (table=count); repeatablenone
--table-scalePer-table scale (table=factor); repeatablenone
--max-rowsCap every table, including family-planner children, lastnone
--tablesInclude matching tables and required dependenciesall
--excludeExclude matching tablesnone
FlagShortDescriptionDefault
--seedStable root seedmodel or fresh entropy
--randomizeIgnore the configured seed; use a new onefalse
FlagShortDescriptionDefault
--checkCompile a complete model onlyfalse
--dry-runCompile and report resolved countsfalse
--verifyGenerate, audit, and publish atomicallyfalse
--explainInclude inference decisionsfalse
--strictFail on warning-severity diagnosticsfalse
--jsonPrint a machine-readable report on stdoutfalse
--quietSuppress ordinary human reportingfalse
--progressAccepted but not wired to generationfalse
  • --check, --dry-run, and --verify are mutually exclusive.
  • --schema-only and --data-only are mutually exclusive.
  • --seed and --randomize are mutually exclusive.
  • --scale and --rows are mutually exclusive.
  • A table cannot receive both --table-rows and --table-scale.
  • --json, --output -, and --emit-config - each own stdout; select only one.
  • --json writes only the report to stdout, so it needs -o <path> for the generated SQL (or a report-only --check/--dry-run run).
  • --check requires a complete model and cannot profile [INPUT].
  • --verify requires a real output path and cannot use compression.
  • MSSQL-specific flags require an explicit --dialect mssql.

--json writes a machine-readable report to stdout, so pair it with -o <path> for the generated SQL (or use --check/--dry-run for a report-only run):

Terminal window
sql-splitter generate --config model.yaml --seed 42 -o synthetic.sql --json
{
"mode": "generate",
"rows_written": 65,
"effective_seed": 42,
"diagnostics": [
{
"code": "GEN-SOURCE-VALUES",
"severity": "advisory",
"path": "tables",
"message": "2 rule(s) replay hand-authored literal values; the output is synthetic, not anonymized source data",
"documentation_url": "https://sql-splitter.dev/commands/generate/diagnostics/#GEN-SOURCE-VALUES",
"related": [
{ "path": "tables.customers.columns.notes", "description": "constant" },
{
"path": "tables.orders.columns.status",
"description": "source_default"
}
]
}
]
}

mode is generate, dry_run, or check. Every diagnostic carries a stable code, a severity, the config path it applies to, and a documentation_url.

CodeMeaning
0Generation or the requested preflight mode succeeded
1Model, warning-under-strict, runtime, I/O, or verification failure
2Invalid CLI usage or conflicting flags

See Exit Codes for scripting examples.

Terminal window
# Save the inferred model, hand-tune it, then generate from the frozen model
sql-splitter generate production.sql --emit-config model.yaml
$EDITOR model.yaml
sql-splitter generate --config model.yaml --seed 42 -o synthetic.sql
Terminal window
# Confirm the synthetic dump parses and its foreign keys resolve
sql-splitter generate --config model.yaml -o synthetic.sql
sql-splitter validate synthetic.sql

(--verify runs an equivalent audit inline and only publishes on success.)

Terminal window
# Generate one dump, then break it into per-table files
sql-splitter generate --config model.yaml -o synthetic.sql
sql-splitter split synthetic.sql -o tables/
Terminal window
# Reduce a huge production dump first, then synthesize from the smaller sample
sql-splitter sample production.sql --rows 5000 -o sample.sql
sql-splitter generate sample.sql -o synthetic.sql

Conflicting flags rejected with exit code 2

Section titled “Conflicting flags rejected with exit code 2”

Symptom: The command exits immediately with a message about mutually exclusive options.

Cause: Two flags that own the same behavior were passed together — for example --check with --verify, --scale with --rows, or --seed with --randomize.

Fix: Keep one flag from each conflicting pair. See Constraints for the full list.

Symptom: With --json you get the report on stdout, but no generated SQL.

Cause: In generate mode --json owns stdout and emits only the report, so the SQL has nowhere to go.

Fix: Add -o <path> for the SQL, or use --check/--dry-run for a report-only run.

Symptom: --check errors when you pass a source dump.

Cause: --check validates a complete --config model and does not profile [INPUT].

Fix: Run --check against a --config model, or use --dry-run to compile and report counts for a profiled dump.

Symptom: --mssql-production-style or --mssql-go errors.

Cause: These flags only apply to MSSQL output and require the dialect to be set explicitly.

Fix: Add --dialect mssql.

Symptom: Generated values match values from the source dump, and a GEN-SOURCE-VALUES advisory appears.

Cause: Some rules (constants, replayed defaults, observed samples) can reproduce literal values. The output is synthetic, not anonymized.

Fix: Review the rules the advisory names, or replace them with non-replaying generators. To anonymize real rows instead, use redact.

Generate’s detail lives in dedicated reference pages:

Related commands and references:

  • redact — Anonymize real data instead of synthesizing new data
  • sample — Reduce a real dump before profiling it
  • validate — Check the generated dump’s integrity
  • Dialects — Dialect-specific output behavior
  • JSON Output Schema — Schema for --json output