Linters are where API governance becomes real
Every company I have worked with had API guidelines, and
almost nobody read them past the first month. At Adidas
the guidelines stayed the same; what changed was the day
they started running in the pipeline.
The guidelines lived on a wiki page, sometimes in a nicely
designed PDF, once on a whole site with a table of
contents. Everyone agreed with them. The APIs kept
drifting anyway. Kin Lane counted the same thing from the
other side: across
260 design reviews he ran, about 15 teams had read the
guidelines.
At Adidas we published the
API guidelines in the open, and next to them a Spectral ruleset that encoded the
parts a machine could check. From then on the style guide
was a CI step. It went red when a team shipped a contract
with inconsistent naming, a missing error schema or an
endpoint nobody had bothered to describe. Reviewers got to
argue about design, because the build had already
complained about the camelCase.
API governance only becomes real when your rules run in
CI, and the asset worth owning is the ruleset, not the
linter that runs it.
Why a linter is the cheapest lever you have
Three things make this a CTO problem once more than a
handful of teams build APIs.
Your estate is polyglot whether you like it or not. One
team ships Java, another Go, a third has a Node service
nobody wants to touch. You can't enforce consistency
in that much code, and you can't put a human
architect on every pull request. The one artifact every
team produces in the same format is the API description,
usually OpenAPI. Lint that, and you govern every team
whatever language sits behind it.
Review is expensive. Every hour a senior engineer spends
asking for plural nouns, a 4xx response or a parameter
description is an hour off the design questions that
matter. A ruleset takes that mechanical half of API review
off the table for good. It also removes the awkward
conversation. Nobody argues with the build the way they
argue with a colleague.
The third one is new. Coding assistants now write API
contracts at volume, and they are plausible far more often
than they are right. An assistant will invent a naming
convention used nowhere else in your company, skip the
security scheme, and hand you an OpenAPI document that
validates perfectly while breaking every guideline you
have. More contracts land in your repos each week, and
fewer of them were read by someone who knows your
standards. A deterministic check in CI is the one gate
that grows with that volume.
A ruleset is a product, in five layers
Most companies that say they lint their APIs run the
default ruleset that ships with the tool. That is
spellcheck. Kin Lane went and measured it: of
1,005 public GitHub repositories running Spectral in
CI, 63% use the default ruleset and nothing else. 13% set
continue-on-error, so a failing lint never blocks anything.
A ruleset that earns its place works in layers, and each
one costs more effort and pays back more:
|
-
Validity. Is this a well-formed OpenAPI document?
Every tool does this out of the box.
-
Naming and structure. Path casing, plural resources,
consistent parameter names, versioning in the right
place, one shape for pagination. Most day-to-day
review noise lives here, and this layer pays for
itself in the first month.
-
Security. Every operation has a security scheme,
nothing goes over plain HTTP, no sensitive data in
query strings. You don't have to write these.
Stoplight's
OWASP ruleset
targets the OWASP API Security Top 10 2023, API
Commons maintains a
version with 22 checks
covering all ten categories, and Vacuum ships one
built in.
-
Documentation. Descriptions on every operation and
parameter, examples on every schema, tags that mean
something. Boring to write. It is also the difference
between an API that gets adopted and one that gets a
Slack message asking how it works.
-
Business rules. Every money field uses the company
Money schema. Every list endpoint supports the
standard filter syntax. Every event carries the tenant
identifier. These need custom functions, they are
yours alone, and they are the rules that protect your
actual architecture.
If you want proof that a ruleset can carry real policy,
look at the Netherlands. The government's
REST API Design Rules
are mandatory for public bodies under a "comply or
explain" regime, and they
ship as Spectral rulesets. The linter is named right there in the normative text.
For a quick audit of your own setup, ask which layer your
ruleset stops at. In my experience most stop at two.
Nobody reaches five without treating the ruleset as a
product, with an owner, tests and a changelog.
Own the ruleset, rent the runtime
For years the tool was Spectral and nobody got fired for
it. The decision that matters now is the ruleset format,
because the format outlives whatever runs it.
Spectral is still the reference. It shipped five releases
in 2026, from 6.15.1 in April to
6.16.3 in August, and Spectral's maintainers merged OpenAPI 3.2
support on 17 September. The community side is another
picture. According to
Kin's count, maintainers closed 157 issues in 2021, 12 in 2025 and
10 so far this year. There are 241 open issues, and the
oldest open community pull request has waited five years.
Then on 30 June a 29-line pull request called "chore:
added scarf telemetry to cli" made the linter
phone home on install. You can switch it off with
scarfSettings.enabled: false.
My read on the four options, as of September 2026:
|
Tool
|
What it is
|
Pick it when
|
Watch out for
|
|
Spectral
|
The reference implementation. Most published
rulesets target it.
|
You run it, your custom functions are JavaScript,
and it works.
|
A JavaScript toolchain in CI, telemetry since
June, a stalled issue tracker.
|
|
Vacuum
|
Go, single binary, MIT. Spectral ruleset
compatible. OpenAPI 2 to 3.2, AsyncAPI 3, JSON
Schema. Language server, HTML report, MCP server.
|
You want speed, no Node in the pipeline and a
short dependency list. Large monorepos of specs.
|
Smaller community. JavaScript custom functions use
a "very similar" design to
Spectral's, so check the signatures before
you migrate.
|
|
Redocly CLI
|
Part of the Redocly platform. Strong built-in
rules and good docs.
|
You already publish docs with Redocly and want one
toolchain.
|
Its own format. Coming from Spectral means a
migration guide
and rewritten rules.
|
|
Speakeasy CLI
|
A
linter built on its own Go OpenAPI library, around SDK generation.
|
SDK generation is your main workflow and lint is a
means to it.
|
Its own
lint.yaml
and TypeScript rules. The linter is there to serve
the generator.
|
Write your rules in the Spectral-compatible YAML format,
keep them in their own repository with tests, and treat
the tool that runs them as replaceable. Vacuum runs them
today. OpenLint is being designed to run them tomorrow.
Write your rules in a vendor's native format instead
and you have signed up for that vendor's roadmap,
whether you meant to or not.
What leaving Spectral looked like at Apideck
I love Spectral. It has saved me more review hours than
any other tool in the API space. We still moved off it at
Apideck, and the reason had nothing to do with rules.
It was the dependency tree. Spectral pulls in a large
graph of JavaScript packages, and every few weeks one of
them showed up in a vulnerability report. None of them
were about linting. All of them needed a human to look,
decide, bump and rerun the pipeline. That is a lot of
maintenance for a tool whose whole job is to say yes or no
in CI. Add the telemetry, and the case for staying got
thin.
Vacuum is one Go binary. We dropped it into the pipeline
and it read the rulesets we already had. The migration
took few hours mostly spent checking the handful of custom
functions. Our governance didn't change. The cost of
maintaining the thing that enforces it went to almost
zero.
What I took from it:
-
Keep the rules, swap the runtime.
-
Check your custom functions first, they are the only
part that doesn't move for free.
-
Do it before the next vulnerability report lands.
The case against: green-check theatre
The strongest objection to all of this comes from the same
data I just used. If 63% of pipelines lint on factory
settings and 13% never block, most of what passes for
linting is a green tick that makes everyone feel governed.
In Kin's census,
2 pipelines out of roughly a thousand
scored 6 out of 8 on his maturity rubric.
Kin takes it further. He calls governance
a stack: a machine rule enforces a written policy, a piece of
guidance explains it, and it protects a consumer
experience. The linter is the only part you can see from
outside. In his version of what governing APIs at scale
looks like,
75% is people work.
He is right, and it's worse than the census shows.
You can pass a lint run today that touched almost nothing
in your document, and you would never know.
My answer is to treat the ruleset as software: an owner, a
good and a bad example per rule as tests, a changelog, and
a build that blocks. A wiki page with nobody reading it
can't fail a build. The people forking Spectral put
coverage on their roadmap, which tells you they treat the
ruleset the same way.
OpenLint makes the format a real spec
Kin Lane
announced the fork
on 29 July, starting from Spectral 6.16.2. The core idea
is to pull the ruleset format out of the tool. Today it is
"described by five internal draft-07 meta-schemas
coupled to that linter's runtime", in the words
of the
spec repository. The fork turns it into one normative JSON Schema with
its own versioning and a conformance suite any linter can
be tested against.
Phil Sturgeon and Jakub Rożek, who built Spectral at
Stoplight, are in, along with Dave Shanley of Vacuum and
Frank Kilcommins. Mike Kistler is too. His
OpenAPI 3.2 pull request
to Spectral sat for six months with an approving review,
was closed on 16 September, and the maintainers merged
their own version built on it the next day. Kin says most
of the working group is European, including two national
governments.
The name came from a
community vote
that ended in a tie: OpenLint at +6, Spectical at +6. A
trademark check settled it. Kin's line:
"The name is the first compliance artifact you
ship."
Someone in the comments
asked why nobody had proposed Sporky McSporkface. Fair
question.
I watched the
recording
of the first office hours on 23 September. The
agenda
reads like the list enterprises have been asking Spectral
for: modular rulesets, federation so a platform team owns
the core and product teams extend it, ratings, autofix,
overlays, and industry rulesets (FHIR and PSD2 came up on
the call). The group split coverage in two: how much of
the ruleset your tests exercise, and how much of the
document your rules reached. Kin wants one ruleset format
that every linter runs, so nobody has to migrate. Vacuum
could become the Go implementation of the same standard.
The
meeting summary
puts the home at Open Source Europe, for "sovereignty
reasons", with funding through Open Collective and
Spectral's Apache-2.0 license carried forward. The
code starts as a fresh repository with Spectral's
full history rather than a GitHub fork, so fixes can be
cherry-picked in both directions. Removing telemetry and
supply chain health are on the list, which is the polite
version of why we left. AI use is minimal and agreed per
pull request, and not used for writing issues. Phil's
line: paste your prompt, not the result.
Nothing is installable yet. The first four discussions are
aliases, multi-format support, cleaning out what they call
Stoplightisms, and rules testing. Don't wait for it,
but keep your rules compatible with it.
What I would do this quarter
If I walked into a company as CTO tomorrow and the APIs
were a mess, this is the order:
-
Put a linter in CI this week, even with the default
ruleset, and make it block. No
continue-on-error. Use Vacuum unless you have a reason not to.
-
Write your own rules in the Spectral-compatible
format, in their own repository, with an owner, tests
and a changelog. Reaching layer three by December is
still more governance than most companies have.
-
Run the ruleset in the editor, on the pull request,
and on the assistant's output before a human
looks at it. The earlier it fails, the cheaper the
fix.
-
Watch OpenLint. If federation and coverage ship, a
portable ruleset gets them the same week.
Guidelines tell people what good looks like. Linters check
it when nobody is looking, and next year more of your
contracts will be written by something that doesn't
read wiki pages.
Reply and tell me which of the five layers your ruleset
stops at.
Unsubscribe
| 1 Bd des clubs - CFC, 20200 Casablanca, Morocco
|