Skip to content

Deleting Duplicate Schemas

 4 min The same deletion across years of work: when two representations of one truth appear, keep one and derive the rest.
Published

Aug 28, 2026

The tag filter on this site keeps its state in the URL hash, and the first version of multi-select kept it twice: a single click wrote #tag=gaming, while a Cmd/Ctrl-click multi-select wrote a separate custom key holding one comma-joined value. The review question was:

why also tag? why not e.g. tag=abc[&tag=…]

The resolution was one key, repeated, so a single click’s #tag=gaming and a multi-select’s #tag=gaming&tag=infra have the same shape at every count, needing one parser and one restore path.

That fix is the newest entry in a habit I can trace across years of my own repositories: two representations of the same truth appear, one of them gets deleted, and the survivor becomes the source everything else is derived from.

One ordered import path

settingsd applied the rule to application settings, a place where a second schema tends to accrete—a layered config on disk for prod, qa, and staging, and a settings module mirroring it in code. settingsd deleted the mirror. settings.d/ holds numbered Python fragments, and one call:

settings = __import__('settingsd').install(__name__)

assembles numbered fragments in one shared namespace and installs the result as <pkg>.settings. The fragments are not a source that settings get loaded from; executed in order, they are the settings, and the object every other import sees is their sum.

Deleting the duplicate did not delete the audit trail. The shared namespace records which fragment and directory assigned a setting. It traces assignments of different objects to uppercase names, not in-place mutations. Within that boundary, “where did this setting come from” is answered by the assembly namespace rather than by a second registry kept alongside it.

One table, two JSON copies, three consumers

zippy, from the same stretch—a waf-based tool that built CPython plus a whole Python application into a single artifact—pushed the rule into a concrete early form: one ConfigSet table serving three unrelated consumers through two generated JSON copies.

Its ConfigSet writer tees the same table into build/config.json and the install-tree zippy.<identifier>.json. The install copy doubles as the landmark compiled into the interpreter to find its Python home, and carries metadata the packed application reads back at runtime. Waf build state, PYTHONHOME discovery, runtime metadata—three consumers of one table. Two files exist, but neither is a separately maintained schema.

Where duplication stayed

The same pipeline marks the boundary of the habit. zippy wrote metadata 2.0—pydist.json, before the ecosystem settled—and then wrote the legacy formats right back out beside it: METADATA and entry_points.txt. The readers of those files belonged to other people’s tools. Deleting a duplicate schema is only safe when every reader is yours to change; when it isn’t, you write both and stay clear about which one is authoritative.

One file, three agents

My dotfiles apply the rule to agent configuration. One protocol document, AGENTS.md, is served to three coding agents under each vendor’s expected filename:

.claude/CLAUDE.md -> ../AGENTS.md
.codex/AGENTS.md  -> ../AGENTS.md
.gemini/GEMINI.md -> ../AGENTS.md

Three tools, three filename conventions, one source; the symlink layer is the entire adapter. Updating the document updates what every tool reads.

One walk that decides

The current statement of the rule is in Spice, the agent harness, where the schema at risk is not a file format but a procedure. Control tokens ride inside model prose, and a single iterator decides, line by line, whether a token is being displayed rather than issued—inside a code fence, under a > quote, behind four-space indentation, or on a rendered source-context line. The doctrine is written on the iterator itself:

Every reader that decides whether a line acts must share this walk, so a display and the supervisor cannot disagree about which lines are real.

Even trimming blank lines off a segment is centralized. The comment explains:

four spaces there is the difference between code being shown and a directive being issued.

A second reader carrying its own copy of the walk would drift from the first, and drift here means a shown directive gets executed. The grammar around it has its own note; the point for this thread is why the walk exists exactly once.