Skip to content

docs(about): the test a function has to pass to be part of this package's surface - #246

Merged
FBumann merged 1 commit into
mainfrom
claude/what-counts-as-a-verb
Sep 2, 2026
Merged

FBumann merged 1 commit into
mainfrom
claude/what-counts-as-a-verb

Conversation

@FBumann

@FBumann FBumann commented Aug 29, 2026

Copy link
Copy Markdown
Contributor

Prompt: "Please add a pr then is visionary regarding the best and most capable api which stays safe and predictable."

Note

The following content was generated by AI.

What this changes

A third page in about/, beside the two that already decide things. what-counts-as-language.md says which rules belong here; ceiling.md says which constructs may enter; neither says which functions may. That gap is how a small surface grows a verb per feature.

A verb is admissible iff every decision it makes is one the language has already stated, and iff it needs nothing but the file to make it.

Plus one behaviour fix and two property tests, because the page argues from a property the code had quietly lost.

The argument, in three moves

Capability is measured on the far side. The temptation is to measure an API by what a caller can call. Wrong end: this package builds nothing and solves nothing, so what it is worth is what a second consumer can build. A wide surface one program uses is narrower, in the sense that matters, than a small one a dozen programs read.

Which is why the largest capability this API can gain is not a verb. It is Program becoming a value another language can read — one serialisation, and every non-Python consumer stops needing a second implementation of the language to exist. Nothing else multiplies like that, and it adds nothing a caller must learn.

Growth happens in the schema. The normal way this package gets more capable is a declaration:

The capability What it cost the API
Regimes in one quantity (cases:) nothing
A curve as facts (piecewise:) nothing
A set a solver branches on (sos:) nothing
Whether a missing row was meant (coverage:) nothing
Composition (merge) one verb

A capability that arrives as a declaration is inspectable, printable, diffable and serialisable, because those are properties of the file. The same capability as a callback is none of them. A feature that can be a declaration must be one.

Three properties every verb keeps — pure, total at load, and closed under composition.

The property the code had lost

The third one is easy to lose and expensive to notice, and writing the page found it had already gone.

merge wrapped a lone objective in parentheses. Nothing was wrong with the answer — and merging one fragment gave back something that was not that fragment, while every nesting added another pair. An API can be correct and unpredictable at the same time, which is most of why the page is worth having.

Fixed: a single objective is returned as written. Both properties are now pinned rather than asserted:

  • test_merging_one_fragment_gives_back_that_fragment
  • test_a_composition_does_not_depend_on_how_it_was_grouped — merging is associative, so a library may ship a prelude already merged and a caller may merge it with their own fragments and reach what merging all of them at once reaches. Without it a composed library would have to document an order.

to_spec and to_program were already idempotent; the page says so and the suite already held it.

The sharp edge

The test cuts both ways, and the second cut is what keeps the page from being a fence around a museum:

  • A verb may not decide something the language has not stated. merge passes only because the rules it implements are written in file.md and not in its docstring.
  • A verb may not take what a consumer owns — a sink's capabilities, how data binds, which solver runs.
  • But the language may not refuse a verb for being new. A pure function of the file that states no rule of its own costs nothing to have and nothing to keep, and refusing one on taste is how an API becomes a lecture.

What lpspec removes or changes

Nothing, and that is the point being made. No verb changes signature, merge's output differs only in a redundant paren, and nothing here binds data.

What it offers lpspec is a shared test rather than a shared rule. lpspec/AGENTS.md has no equivalent page, and its surface is the one under real pressure — the operational verbs (IIS, elastic relaxation, run diffing) are all arriving at once. The second clause inverts cleanly for a consumer: a verb there is admissible iff every decision it makes is one the language or the sink has already stated. That is what keeps relax= from becoming an engine flag on a model nobody can see, and it is why elastic relaxation belongs above as a Spec → Spec function.

Verified

Toolchain reconstructed at the versions pixi.toml pins: ruff format --check / ruff check (0.16.1, pinned) clean; pyrefly (1.2.0, pinned) 0 errors; reuse compliant; typos clean; prettier --check over **/*.{md,yml,yaml} clean; pytest -q -n auto 856 passed, 1 skipped (854 on the base — 2 new); python -m tools.render_tex renders 27 models; mkdocs build --strict builds with the new page and its nav entry.

Not run: zizmor, taplo (neither's files changed), and the tectonic half of compile-tex.

Deliberately not done

No new verbs. A page arguing for a small surface that shipped three would be arguing against itself. The two it names as worth having — a serialised Program, and qualified names — are issues, not this diff.

Not merged into what-counts-as-language.md. They answer different questions about different things and that page already warns how easily it is confused with the ceiling; a third distinction inside it would be worse than a third page beside it.

The falsification clause is not decoration. A capability somebody genuinely needs, which this test refuses, and which cannot be reshaped into a declaration, is a row against the page rather than an exception to it — the same standing the ceiling's refusal ledger has.

Stack: fifth, on #245 → #244 → #243 → #242 → #168.


Generated by Claude Code

…ge's surface

The language has a test for what belongs in it and the ceiling has one for what
may enter it; the API had neither, which is how a small surface grows a verb per
feature. A verb decides nothing the language has not stated and needs nothing
but the file, and the three properties it keeps are pure, total at load, and
closed under composition.

Reframed to stand on main: the merge.py bugfix and its tests that were bundled
here now live on the composition PR (#244), where the behaviour and its test
belong, and the page states composition-closure as the property a verb earns
rather than a past defect in shipped code.

Co-Authored-By: Claude <noreply@anthropic.com>
@FBumann
FBumann force-pushed the claude/what-counts-as-a-verb branch from ab21495 to a32b6fc Compare August 31, 2026 20:56
@FBumann
FBumann changed the base branch from claude/lookup-coverage to main August 31, 2026 21:02
@FBumann
FBumann marked this pull request as ready for review September 2, 2026 12:40
@FBumann
FBumann merged commit cc1414a into main Sep 2, 2026
6 checks passed
@FBumann
FBumann deleted the claude/what-counts-as-a-verb branch September 9, 2026 06:45
@FBumann FBumann added the docs Documentation pages, guides, reference and README label Sep 24, 2026 — with Claude
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

docs Documentation pages, guides, reference and README

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant