What's new
What changed in TDC that you can see — a new command or flag, a new check, something that now works differently — newest first, each with a link to where the docs explain it now. Changes inside the engine that alter nothing you write or read are left out; every change is in the changelog.
25 October 2026 — version 0.3.6
<line each="Pool">prints a pool record by record. One line per record, every field read as${{Pool.field}}, so a lookup table comes out of the same config as the rows that point at it. The positionsPool._first,Pool._lastandPool._itemcount the lines actually printed, which is what puts a comma between JSON objects and not after the last one. → A whole pool, record by record<group>keeps several lines together.<group each="Depts">prints its lines once per department, and a group inside it prints that department's doctors — a nested JSON document from one config. Withouteach, itsif=keeps or drops all its lines at once. → Several lines per element- The
jsonfilter.${{Name | json}}writes a JSON string with the escaping done, ornullfor an empty value;${{Tags | json:;}}writes a list as a JSON array. A list printed without its separator gets a warning,TDC312. →json plus=reads the distance from a column.<gen type="date" of="Start" plus="Length m">ends each appointment its own length after it starts. → A distance read from another column- The
if=of aneachline decides element by element.<line each="Orders" if="Orders > 5000">prints the large orders only; it used to keep or drop the whole line. → What's visible inside aneachline - Fixture lines are checked, and their
if=is read. A misspelled${{Name}}in<before>is an error incheckinstead of reaching the file as written. → Fixtures - Health identifiers with real check digits: the US NPI, Germany's KVNR and LANR, France's RPPS and FINESS, Brazil's CNS. → National tax and document numbers
- US and Canadian phone numbers use every area code in service, with 555-0100 to 555-0199,
the line numbers reserved for fiction. Every US number used to start
+1 202 555. → Phone numbers - The pack registry holds 294 bundles. Traditional Chinese, Uzbek, Montenegrin,
Breton, Sindhi, four more languages and 46 countries can be downloaded now, and
tdcv2 pack listnames countries as names: United States, not "Usa". →pack list - Rust and C#: a pack whose
<valid>check rejects a value now redraws it the way the other three do. Eleven shipped packs, the ISO 6346 container code and Slovenian postal codes among them, gave different values there. →<valid> - AI agents. Claude Code, Codex, Cursor, VS Code and Gemini CLI can write and run TDC configs for you, through a skill and an MCP server. → AI Agents
17 October 2026 — version 0.3.5
checksays which engine will run the config, and why. A second line after "is valid", such asruns on engine 1 (in memory): uniq="true" on "Code"— that is where the run's memory goes.--briefleaves it out. →tdcv2 check--engine 3says when engine 1 runs the config instead. On a running total, a statistic or auniq="true"column it always handed the run to the in-memory engine; it now prints a note, so a memory reading is not quietly one of engine 1. → Which engine runs your config- Fixed: a lookup or a formula reading a
<uniq>member saw the value from before the group was settled — the day printed and the day looked up disagreed on almost every row. →<uniq>— across separate sequences - Fixed:
<assert>andif=read a field two or more pools deep, such asD.room.dept.dep_id. → How deep can it go - Fixed: a filter inside a pool reads the fields beside it.
filter="dept_no == want", withwanta field of the same pool, was refused as a filter that can never match. → What a name means insidefilter - Fixed: every element of a
repeat=is its own draw. A repeated e-mail address no longer repeats one domain, and a distribution whose parameter names another column reads each row's own value. → Multiple values in a cell - Fixed: February 29 stays February 29. In the npm package a date bounded by or measured from 2024-02-29 came out as March 1. → A random date in a range
- Python, Rust, Java and C#: a
<switch>on a field of a pool record, a date measured from one, andrepeat=inside a<switch>branch or a<mix>case work as they do in the npm package. → Two names, one dot
16 October 2026 — version 0.3.4
-
initcan leave the examples out.tdcv2 init --yes --no-exampleswrites the config and the pack folder and nothing else — for a script or an AI agent that sets up a project on someone's behalf. →--no-examples -
checkwarns about three mistakes that used to pass in silence. Each one ran without a word and gave the wrong data:- no
seed=on<env>: every run draws a different file →seed mmin a date format is minutes, soYYYY-mm-DDprinted month00; the month isMM→ Formatting the output"or another XML entity in<data>is printed as written →<data>— raw text
They are warnings:
checkstill exits with 0. A run given--seedhas nothing to warn about, and a run without one prints the seed it drew instead. →tdcv2 check, codesTDC309–TDC311in the diagnostics reference - no
-
A date measured from another date has its format checked.
format="YYY"on a date withof=/plus=printed25Yon every row;checknow refuses it, as it does for any other date. → A date measured from another date -
npm package:
init --localewith no value is refused. It used to write anenconfig without a word; the other four implementations already refused it. →--locale