Skip to content

Document the language service, and the gap it leaves in Python - #3

Merged
samuelduchesne merged 1 commit into
mainfrom
005-idf-language-service
Sep 4, 2026
Merged

Document the language service, and the gap it leaves in Python#3
samuelduchesne merged 1 commit into
mainfrom
005-idf-language-service

Conversation

@samuelduchesne

Copy link
Copy Markdown
Contributor

A capability page for idf-language-service, the answers an editor needs about IDF text: which statement the cursor is in, what may be written here, what this field means, where this name is declared, which characters a finding is about. Reading a model answers none of them, because by the time a document exists the text has been forgotten.

Blocked on idfkit-conformance#2.pyproject.toml moves [tool.idfkit.governance] to governance-2026.11, which does not exist on main there yet. Every governance-reading script here (parity_macro.py, render_parity_page.py, render_naming_map.py) fails to resolve the ref until that PR merges and the tag is cut. Merge order is conformance, then idfkit-js, then this.

The page

Language-neutral prose with the code in one language and an explicit rendered absence in the other, which is the remedy Principle III provides rather than an exception to Principle IV. It follows the shape of explanation/browser-simulation.md, the standing precedent.

It carries {{ parity("idf-language-service") }}, and that macro fails the site build when its argument resolves to nothing. That is what makes the gap impossible to publish as an empty panel, and it is verified rather than assumed: removing the id aborts the build with a BuildError naming the page and the id, and restoring it builds clean.

Python is absent with absence_kind = "never", and the notice says so in those terms: a permanent boundary, no issue tracking it, and a constitutional amendment rather than a ledger edit to move it. The reason is on the page. The answers are byte-offset arithmetic, and a second implementation of that arithmetic is the drift surface the corpus is least able to police, since it compares findings on (code, line, typeName) and never on a column. Two implementations could disagree about a position for a long time with no gate noticing. The editor extension needs no port either: its existing Python server keeps serving Python source, and a second server serves IDF text.

Regenerated artifacts

parity.md and naming-map.md are rendered at governance-2026.11. The parity page had not been regenerated since the ledger gained the capability, so the notice linked to explanation/parity.md#idf-language-service, an anchor that did not exist, and the tier was stated nowhere the reader could reach. Both files are generated, not hand-edited: re-running the render scripts after this commit produces no diff.

Levels

[tool.idfkit.governance] moves to governance-2026.11. The conformance, docs and library levels do not.

What this PR does not close, and why

The two TypeScript snippets are checked by nothing in this repository, and that is a gap rather than a decision. Every non-vendored snippet here is Python, checked by pyright, and the only checked TypeScript tree is docs/snippets/js/, which sync_js_artifacts.py compares byte for byte against the pinned docs release and which is never hand-edited. Both files type-check clean under strict against the live @idfkit/core and @idfkit/language sources and are prettier-clean, proven by hand rather than by a gate. Closing it properly means authoring them in idfkit-js/docs-snippets/, publishing a docs-2026.N artifact, vendoring it, and bumping [tool.idfkit.docs], which is a release cycle rather than an edit.

One of them is the worked protocol-translation example, and its whole content is translation: it contains no line or column computation of its own and splits no region it was given. That is the point of it. If a consumer finds itself counting commas, the service has failed.

Two pre-existing failures, neither caused by this branch

make check is red.ruff reports S310 in scripts/sync_js_artifacts.py, a file this branch does not touch.

make docs-test cannot pass in this environment. The strict build aborts with 107 warnings and all 107 are the social plugin reporting that cairosvg cannot load libcairo. libcairo is installed; macOS SIP strips DYLD_* from the make and uv chain before the plugin sees it. None of the 107 name any file in this change. With that one plugin disabled the strict build exits 0 and the page renders correctly, with the parity link resolving and the absence statement naming the kind. check_page_kinds.py and check_capability_declarations.py both pass.

Separately, and worth flagging to whoever owns the library pin: [tool.idfkit.library] is 0.15.0, which carries neither load_idf_with_diagnostics nor ParseResult nor the five write_idf controls that pages already merged here document. A reader on the version the site itself declares would hit an ImportError copying those examples. That needs a library release plus a uv lock, and is out of scope for this branch.

A capability page for `idf-language-service`, the answers an editor needs
about IDF text: which statement the cursor is in, what may be written here,
what this field means, where this name is declared, which characters a finding
is about. Reading a model answers none of them, because by the time a document
exists the text has been forgotten.
The page is language-neutral prose with the code in one language and an
explicit rendered absence in the other, which is the remedy Principle III
provides rather than an exception to Principle IV. It carries
`parity("idf-language-service")`, and that macro fails the site build when its
argument resolves to nothing, which is what makes the gap impossible to
publish as an empty panel. Verified by removing the id and watching the build
abort, then restoring it.
Python is `absent` with `absence_kind = "never"`, and the notice says so in
those terms: a permanent boundary, no issue tracking it, and a constitutional
amendment rather than a ledger edit to move it. The reason is on the page. The
answers are byte-offset arithmetic, and a second implementation of that
arithmetic is the drift surface the corpus is least able to police, since it
compares findings on (code, line, typeName) and never on a column. Two
implementations could disagree about a position for a long time with no gate
noticing. The editor extension needs no port either: its existing Python
server keeps serving Python source, and a second server serves IDF text.
parity.md and naming-map.md are regenerated at governance-2026.11. The parity
page had not been rendered since the ledger gained the capability, so the
notice linked to an anchor that did not exist and the tier was stated nowhere
the reader could reach. Both are generated artifacts, not hand edits.
The governance level moves to governance-2026.11. The conformance, docs and
library levels do not.
The two TypeScript snippets are checked by nothing in this repository, and
that is a gap rather than a decision. Every non-vendored snippet here is
Python, checked by pyright, and the only checked TypeScript tree is
docs/snippets/js/, which sync_js_artifacts.py compares byte for byte against
the pinned docs release and which is never hand-edited. Both files type-check
clean under strict against the live sources and are prettier-clean, proven by
hand rather than by a gate. Closing it properly means authoring them in
idfkit-js/docs-snippets/, publishing a docs artifact and bumping
[tool.idfkit.docs], which is a release cycle rather than an edit.
github-actionsBot added a commit that referenced this pull request Sep 4, 2026
@samuelduchesne
samuelduchesne merged commit 7486ee3 into mainSep 4, 2026
9 of 12 checks passed
@samuelduchesne
samuelduchesne deleted the 005-idf-language-service branch September 4, 2026 19:39
github-actionsBot added a commit that referenced this pull request Sep 4, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant

@samuelduchesne