# API surface history One file per released `v3.*` tag: `.json`, e.g. `v3.12.0.json`. Each is the output of `extract_api.py --surface-output` at that tag (see `tools/api_checker/README.md` for the schema), with additional immutable provenance in `meta`: `ref`, `commit` (the tag's resolved commit sha), `generated_at`, and `generator`. ## Conventions - **Immutable once committed.** Files here are never hand-edited or silently regenerated. `snapshot_release.py` refuses to overwrite an existing file unless `--force` is passed, and that should only happen for a deliberate, reviewed fix — the resulting diff should be inspected before committing, same as any other source change. - **Generated by `tools/api_checker/snapshot_release.py`**, run manually as part of cutting a release (see `tools/api_checker/README.md`'s "Workflow: Release Checklist"). Not CI-automated. - **`diff_api.py` uses these automatically.** `--old`/`--new` check here first (matching the ref string to `.json`) before falling back to live `git archive` extraction — see `tools/api_checker/README.md`'s `diff_api.py` section. ## Coverage Backfilled: every `v3.*` tag from `v3.1.0` through the latest release at backfill time (`v3.12.0`), covering the full public API history of the `include/nlohmann/` header layout. ## Format history - **`format_version: 2`** (current). Fixed `extract_api.py`'s `ABI_TAG_PATTERN` to also strip the pre-rename ABI inline-namespace form used by `v3.11.0`/`v3.11.1`: `json_v3_11_0` (no `_abi` segment), renamed to today's `json_abi_v3_11_2`-style tag starting with `v3.11.2`. Under `format_version: 1`, that older form wasn't recognized, so every `scope`/`signature` at `v3.11.0`/`v3.11.1` retained the raw un-stripped namespace segment, making `diff_api.py` report essentially the entire API (~330 of ~332 entries) as removed-and-readded across `v3.10.5`->`v3.11.0`->`v3.11.1`->`v3.11.2` — a bug of the same shape as the earlier USR-arity issue documented in `extract_api.py`'s `identity_key()` docstring, caught the same way: by actually diffing real consecutive release pairs instead of trusting the extractor in isolation. All 27 files were regenerated under `format_version: 2`; only `v3.11.0.json` and `v3.11.1.json` actually changed content (every other tag's scopes never contained the old-style tag). ## Known gaps - **`v3.0.0`, `v3.0.1`**: not backfilled. These predate the `include/nlohmann/` directory structure entirely — headers lived under `src/` at that point (a single `src/json.hpp`). Since `extract_api.py` hardcodes `include/nlohmann/json.hpp` as the entry point, `snapshot_release.py --all-tags` fails cleanly on these two refs (`git archive ... -- include` finds nothing) rather than silently producing a wrong/empty result. Not pursued: two tags, immediately superseded by `v3.1.0`, and supporting the pre-restructuring layout would need a separate header/include-path convention with no other benefit. If full pre-3.1 coverage is ever wanted, `extract_api.py` would need a `src/json.hpp`-aware mode first. - Pre-`v3.0.0` tags (`v1.x`, `v2.x`, `v3.0.0-rc*`, etc.) were never attempted — out of scope for this backfill; see `tools/api_checker/POLICY.md` for the stated boundary.