net/http middleware in Go, and Rack middleware in Ruby. Mount it in front of your marketing site, and agent traffic gets agentified markdown while everyone else gets your site untouched.
All four implement one contract:
- Only
GETrequests are considered; every other method passes through. - Detection is one predicate over the request’s
AcceptandUser-Agentheaders: markdown-preferring or AI-agent traffic matches. - A match short-circuits with
200 text/markdown, forwarding the Agentify response’scache-controlandetagso your CDN caches the markdown too, plusVary: accept, user-agentso a shared cache never hands it to a browser. - Any Agentify failure falls through to your app. A missing key, a network error, a non-200, a timeout — the middleware never breaks your site. The worst case is an agent seeing HTML.
Configure the key
Agentify calls use a dedicated config field holding azc_ key with the agentify:convert scope; when unset, they fall back to the combined apiKey. The field has no construction-time requirement — a client that never agentifies needs no key — so a missing key surfaces as a typed error at call time, which the middleware absorbs by falling through.
agentifyTimeoutMs / agentify_timeout_seconds / AgentifyTimeout), independent of the allowance check’s much tighter one.
Mount the middleware
Options
Each middleware takes the same three options, named in its language’s idiom:
By default the middleware converts the URL the agent requested, as far as your process can see it. Behind a proxy or load balancer that rewrites the scheme or host, override it — the API fetches this URL from the outside, so it must be the public one:
Failing open, observably
The middleware exists to add an agent-readable representation, never to add an outage: any error on the Agentify path serves your HTML instead. That silence is deliberate, and it also means a misconfigured key looks exactly like working HTML — so wire the error hook to your logger:OnError falls back to the client’s configured Logger.
Verify
With the middleware mounted, the same page answers both audiences:Next steps
SPA setup
No server to mount middleware in? Front the SPA with an edge function.
REST quickstart
The underlying endpoint: request, response anatomy, and errors.