clojure.spec CONTRACT for the language-surface tool RESULTS (format_code,
lint_code, run_tests).
Every language pack that registers a :format-fn / :lint-fn / :test-fn
under
:ext/language-tools returns a result map that MUST conform to these specs,
so the shape is UNIFORM across packs (clojure, and a future python / js) and
can never silently drift. Both results share the directory-nested by-cwd
grouping ({<dir> {<basename> <payload>}}) that writes each long directory
prefix ONCE.
The result maps cross the strings-only Python boundary, so their keys are
STRINGS ("op", "findings", "by-cwd", ...). clojure.spec's s/keys only
speaks keyword keys, so the map specs here are plain predicates over the
string keys, composed from s/map-of / s/coll-of for the nested pieces.
check validates a result and returns it UNCHANGED, throwing ex-info with
s/explain-data when it violates the contract — the schema check the packs
run on every format/lint result before handing it back through the surface.
capability->spec is the single source of truth mapping a capability keyword
to its result spec.
clojure.spec CONTRACT for the language-surface tool RESULTS (`format_code`,
`lint_code`, `run_tests`).
Every language pack that registers a `:format-fn` / `:lint-fn` / `:test-fn`
under
`:ext/language-tools` returns a result map that MUST conform to these specs,
so the shape is UNIFORM across packs (clojure, and a future python / js) and
can never silently drift. Both results share the directory-nested `by-cwd`
grouping (`{<dir> {<basename> <payload>}}`) that writes each long directory
prefix ONCE.
The result maps cross the strings-only Python boundary, so their keys are
STRINGS ("op", "findings", "by-cwd", ...). clojure.spec's `s/keys` only
speaks keyword keys, so the map specs here are plain predicates over the
string keys, composed from `s/map-of` / `s/coll-of` for the nested pieces.
`check` validates a result and returns it UNCHANGED, throwing ex-info with
`s/explain-data` when it violates the contract — the schema check the packs
run on every format/lint result before handing it back through the surface.
`capability->spec` is the single source of truth mapping a capability keyword
to its result spec.Maps a language-tool capability keyword to the spec its result must satisfy.
Capabilities absent here (:repl-eval-fn, ...) are unconstrained.
Maps a language-tool capability keyword to the spec its result must satisfy. Capabilities absent here (`:repl-eval-fn`, ...) are unconstrained.
(check capability result)Validate result against the language-surface contract for capability,
returning it UNCHANGED when it conforms. Throws ex-info carrying the spec
explain-data when it violates the contract. Unknown capabilities pass
through unchecked, so this is a no-op for tools without a registered spec.
Validate `result` against the language-surface contract for `capability`, returning it UNCHANGED when it conforms. Throws ex-info carrying the spec `explain-data` when it violates the contract. Unknown capabilities pass through unchecked, so this is a no-op for tools without a registered spec.
(complete-test-result language result)One pack's raw run_tests result onto test-result-base — the SINGLE place
the uniform shape is made true.
NOTHING is translated here: every pack speaks the contract's OWN words.
A runner that counts in other ones — pytest's passed/failed/errored,
bun's N pass / N fail lines — is folded onto pass/fail/errored
INSIDE its pack, where what those words mean is known (pytest's failed
and errors are DISJOINT; lazytest's are not). A completed result
therefore names each fact once because it only ever carried one name.
What is filled in here is what a pack could not know: total, errored,
is_pass and language are DERIVED only when the pack reported none —
nothing a pack said is ever overwritten.
errored is a count BESIDE fail, not inside a second list, because it
names a different fact (how many threw), stays a SUBSET of fail, and
survives where the typed fault list cannot: a runner that reported counts
and no per-test detail lists no faults to type.
Non-map results (a pack that returned something else) pass through.
One pack's raw run_tests `result` onto `test-result-base` — the SINGLE place the uniform shape is made true. NOTHING is translated here: every pack speaks the contract's OWN words. A runner that counts in other ones — pytest's `passed`/`failed`/`errored`, bun's `N pass` / `N fail` lines — is folded onto `pass`/`fail`/`errored` INSIDE its pack, where what those words mean is known (pytest's `failed` and `errors` are DISJOINT; lazytest's are not). A completed result therefore names each fact once because it only ever carried one name. What is filled in here is what a pack could not know: `total`, `errored`, `is_pass` and `language` are DERIVED only when the pack reported none — nothing a pack said is ever overwritten. `errored` is a count BESIDE `fail`, not inside a second list, because it names a different fact (how many threw), stays a SUBSET of `fail`, and survives where the typed fault list cannot: a runner that reported counts and no per-test detail lists no faults to type. Non-map results (a pack that returned something else) pass through.
(explain capability result)The human explain string for a non-conforming result, or nil when valid /
the capability has no registered spec.
The human explain string for a non-conforming `result`, or nil when valid / the capability has no registered spec.
TOTAL key set of EVERY run_tests result — one tool, ONE result shape across
every language pack. A pack fills what its runner measured; the keys it does
NOT fill keep these neutral values instead of VANISHING, so ordinary model
Python (r["failures"][:3], r["total"]) can never KeyError, and never
reads None where a collection belongs.
Counts stay nil when the runner reported none — UNKNOWN is not zero — while
collections default empty and flags default false. Applied ONCE at the
language surface (language-surface/run-tests), AFTER the pack's own
check, so packs keep returning only what they know.
TOTAL key set of EVERY `run_tests` result — one tool, ONE result shape across every language pack. A pack fills what its runner measured; the keys it does NOT fill keep these neutral values instead of VANISHING, so ordinary model Python (`r["failures"][:3]`, `r["total"]`) can never KeyError, and never reads None where a collection belongs. Counts stay nil when the runner reported none — UNKNOWN is not zero — while collections default empty and flags default false. Applied ONCE at the language surface (`language-surface/run-tests`), AFTER the pack's own `check`, so packs keep returning only what they know.
(valid? capability result)True when result conforms to the contract for capability (or the
capability has no registered spec).
True when `result` conforms to the contract for `capability` (or the capability has no registered spec).
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |