{"openapi":"3.1.0","info":{"title":"aadhar.sh public API","version":"1","summary":"Keyless, read-only JSON endpoints on aadhar.sh.","description":"The public HTTP API of aadhar.sh, Aadharsh Pannirselvam's personal site. Every endpoint is read-only and needs no key, account or signup: production is the sandbox. Errors are JSON with at least an `error` sentence (see the Error schema). The same capabilities are tools on the MCP server at https://aadhar.sh/mcp. Guide: https://aadhar.sh/developers.\n\nWhat it leaves out: Keys, accounts and OAuth. Every endpoint is free, public and read-only, so there is nothing to sign up for and a credential would unlock nothing. The site once issued anonymous OAuth tokens that no endpoint checked, and dropped them. A sandbox or test mode. Production is the sandbox. Every endpoint is read-only, so a test call changes nothing, and a separate copy would only drift from the real API. On the MCP server, representation_capture and representation_compare each store a snapshot row, and their descriptions say so. Version headers and pinning. One person maintains the API, and it has one live shape: the one /openapi.json describes. New endpoints, parameters and fields arrive without notice, so ignore fields you don't know. Deprecation and Sunset headers. A notice period protects clients that depend on an exact shape, and none is known here. A breaking change lands in /openapi.json the day it ships.","contact":{"name":"Aadharsh Pannirselvam","email":"coffee@aadhar.sh","url":"https://aadhar.sh/contact"}},"externalDocs":{"description":"Developer guide","url":"https://aadhar.sh/developers"},"servers":[{"url":"https://aadhar.sh","description":"Production, which is also the sandbox: every endpoint is keyless and read-only, so a test call needs no account and cannot change anything."}],"security":[],"tags":[{"name":"search","description":"Find pages on the site."},{"name":"photos","description":"The photo archive and its Fuji recipes."},{"name":"lens","description":"How machines read the web."},{"name":"music","description":"What is playing right now."},{"name":"around","description":"The crawled neighborhood of venture firm homepages."},{"name":"contact","description":"Reaching Aadharsh."},{"name":"about","description":"Who runs the site."}],"paths":{"/search.json":{"get":{"operationId":"searchSite","tags":["search"],"summary":"Search the site","description":"Lexical search over the public pages, writing, garage notes and utility descriptions. Use it to find a page by topic before fetching that page's Markdown twin.","parameters":[{"name":"q","in":"query","required":true,"description":"Search terms. Stopwords are dropped and at most 12 terms are used.","schema":{"type":"string","maxLength":160}},{"name":"limit","in":"query","required":false,"description":"Maximum results. Values outside the range are clamped, and a non-number falls back to the default.","schema":{"type":"integer","minimum":1,"maximum":50,"default":20}}],"responses":{"200":{"description":"Ranked results.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchResults"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"400":{"description":"q is missing or blank.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/ask":{"get":{"operationId":"askSite","tags":["search"],"summary":"Ask a natural-language question (NLWeb)","description":"NLWeb's REST endpoint over the same corpus as /search.json. Streaming is on by default, per the protocol: a bare GET is a server-sent event stream, and streaming=0 returns one JSON body. Results are ranked by Clef, a decision model that chooses among every page on the site, so a page can answer a question it shares no word with; score is then the probability Clef puts on that page. When Clef is slow, unavailable or past its 20 questions per caller per minute, ranking falls back to lexical and _meta.ranking says which ran. Descriptions are extractive: this origin runs no generative model, so it never writes an answer, and mode=summarize or generate is refused by name. The same answer is the ask tool on /mcp.","parameters":[{"name":"query","in":"query","required":true,"description":"The question.","schema":{"type":"string"}},{"name":"streaming","in":"query","required":false,"description":"0, false, no or off returns one JSON body. Any other value, or none, streams text/event-stream.","schema":{"type":"string","default":"1"}},{"name":"mode","in":"query","required":false,"description":"Only list is served. summarize and generate return 501 with supported_modes.","schema":{"type":"string","enum":["list","summarize","generate"],"default":"list"}},{"name":"site","in":"query","required":false,"description":"The only site is aadhar.sh.","schema":{"type":"string","enum":["","all","aadhar.sh","https://aadhar.sh"]}},{"name":"top_k","in":"query","required":false,"description":"Maximum results. `limit` is read when top_k is absent.","schema":{"type":"integer","minimum":1,"maximum":50,"default":10}},{"name":"prev","in":"query","required":false,"description":"Earlier queries in the conversation, comma-separated, at most 10.","schema":{"type":"string"}},{"name":"decontextualized_query","in":"query","required":false,"description":"If present, this string is searched instead of query.","schema":{"type":"string"}},{"name":"query_id","in":"query","required":false,"description":"Echoed back. A UUID is generated when absent.","schema":{"type":"string"}}],"responses":{"200":{"description":"One JSON body when streaming=0, otherwise an NLWeb event stream.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AskResponse"}},"text/event-stream":{"schema":{"type":"string"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"400":{"description":"query is missing, or site or mode is unknown.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, POST, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"501":{"description":"mode is summarize or generate.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}},"post":{"operationId":"askSiteStructured","tags":["search"],"summary":"Ask with an NLWeb v0.55 body","description":"The NLWeb v0.55 dialect: a JSON body whose query is an object selects it, and streaming answers use named start, result and complete events. Body fields win over query-string fields.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"query":{"type":"object","properties":{"text":{"type":"string"},"site":{"type":"string"}},"required":["text"]},"prefer":{"type":"object","properties":{"streaming":{"type":"boolean"},"mode":{"type":"string","enum":["list"]}}},"context":{"type":"object","properties":{"prev":{"type":"array","items":{"type":"string"}}}},"query_id":{"type":"string"},"top_k":{"type":"integer","minimum":1,"maximum":50}},"required":["query"]}}}},"responses":{"200":{"description":"One JSON body when prefer.streaming is false, otherwise named server-sent events.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AskResponse"}},"text/event-stream":{"schema":{"type":"string"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"400":{"description":"The body is not JSON, or a field is invalid.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, POST or HEAD.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/photos/query.json":{"get":{"operationId":"queryPhotos","tags":["photos"],"summary":"Query the photo archive","description":"Filter the published photo archive by caption, camera, lens, film simulation, Fuji recipe or date. Returned EXIF is a public-safe allowlist. Every Fuji frame carries a recipe card naming the settings it was shot with (film simulation, dynamic range, grain, color chrome, white balance shift, tone, color, sharpness, clarity), and recipe= matches anywhere inside it, as in recipe=DR400 or recipe=Clarity:%20-2, so a look can be read back and re-shot.","parameters":[{"name":"q","in":"query","required":false,"description":"Caption search; the only ranked field.","schema":{"type":"string","maxLength":120}},{"name":"camera","in":"query","required":false,"description":"Case-insensitive substring of the camera.","schema":{"type":"string","maxLength":120}},{"name":"lens","in":"query","required":false,"description":"Case-insensitive substring of the lens.","schema":{"type":"string","maxLength":120}},{"name":"film","in":"query","required":false,"description":"Case-insensitive substring of the film simulation.","schema":{"type":"string","maxLength":120}},{"name":"recipe","in":"query","required":false,"description":"Case-insensitive substring anywhere in the recipe card, for example DR400.","schema":{"type":"string","maxLength":120}},{"name":"from","in":"query","required":false,"description":"Earliest date, YYYY-MM-DD.","schema":{"type":"string","format":"date"}},{"name":"to","in":"query","required":false,"description":"Latest date, YYYY-MM-DD.","schema":{"type":"string","format":"date"}},{"name":"limit","in":"query","required":false,"description":"Page size. Values outside the range are clamped, and a non-number falls back to the default.","schema":{"type":"integer","minimum":1,"maximum":100,"default":25}},{"name":"offset","in":"query","required":false,"description":"Rows to skip.","schema":{"type":"integer","minimum":0,"maximum":10000,"default":0}}],"responses":{"200":{"description":"Matching photos.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PhotoQuery"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/lens/fetch":{"get":{"operationId":"inspectUrl","tags":["lens"],"summary":"Inspect how a machine reads a URL","description":"Fetch one public URL server-side as AadharshBot and return what a machine sees: status, headers, structured data, the token cost of the HTML, per-bot robots verdicts, discovery surfaces and an agent-readiness score. Shares a 30 per minute per-caller budget with /mcp and the terminal tools.","parameters":[{"name":"url","in":"query","required":true,"description":"The public http or https URL. https:// is assumed when no scheme is given. Ports other than 80 and 443, credentials, and private or link-local hosts are refused.","schema":{"type":"string"}},{"name":"phases","in":"query","required":false,"description":"page limits the scan to fields derived from the page itself (one subrequest).","schema":{"type":"string","enum":["page"]}},{"name":"mode","in":"query","required":false,"description":"cloudflare returns the Cloudflare Agent Readiness level instead of the full observation.","schema":{"type":"string","enum":["cloudflare"]}}],"responses":{"200":{"description":"The observation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/LensObservation"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"inspect\";q=30;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"400":{"description":"The URL is missing or refused.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the 30 per minute budget.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"inspect\";q=30;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"502":{"description":"The target timed out (8 seconds) or failed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/lens/compare.json":{"get":{"operationId":"compareUrls","tags":["lens"],"summary":"Compare two URLs","description":"Inspect two public URLs and report the differences in status, content, readiness, tier and agent surfaces. Limited to 4 comparisons per caller per minute.","parameters":[{"name":"left","in":"query","required":true,"description":"The first URL, validated like /lens/fetch.","schema":{"type":"string"}},{"name":"right","in":"query","required":true,"description":"The second URL.","schema":{"type":"string"}}],"responses":{"200":{"description":"The comparison.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/LensComparison"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"compare\";q=4;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"400":{"description":"left or right is missing or refused.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the 4 per minute budget.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"compare\";q=4;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"502":{"description":"The comparison failed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/lens/census.json":{"get":{"operationId":"getCensus","tags":["lens"],"summary":"Read the weekly agent-readiness census","description":"A weekly, longitudinal record of how agent-ready 16 representative sites are, with each site's score and tier over time.","responses":{"200":{"description":"The census.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Census"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"503":{"description":"Census storage is unavailable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/rn/tracks":{"get":{"operationId":"getNowPlaying","tags":["music"],"summary":"Read the current playlist","description":"The tracks on Aadharsh's current \"rn\" Spotify playlist. Each track has a title, its artists, a song.link URL that opens in the listener's own music service, its duration, a preview URL and an explicit flag. Cached for an hour.","responses":{"200":{"description":"The playlist.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Tracks"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"500":{"description":"Storage is not configured.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"502":{"description":"The playlist could not be read from Spotify.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"503":{"description":"No playlist is set (code no_playlist), or storage could not be read (code storage_unavailable).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/around/json":{"get":{"operationId":"getNeighborhood","tags":["around"],"summary":"Read the neighborhood crawl","description":"The latest AadharshBot crawl of a small list of crypto venture firm homepages: status, title, description and robots verdict for each. The same data as the /around page.","responses":{"200":{"description":"The latest snapshot.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AroundReport"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"503":{"description":"No snapshot exists yet. Retry after a day.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Pending"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/around/changes.json":{"get":{"operationId":"getChangeRadar","tags":["around"],"summary":"Read what changed in the neighborhood","description":"A bounded history of changes between crawls of the neighborhood: status, title, description, robots and content changes. Never returns crawled page bodies.","parameters":[{"name":"limit","in":"query","required":false,"description":"Maximum change records. Values outside the range are clamped, and a non-number falls back to the default.","schema":{"type":"integer","minimum":1,"maximum":100,"default":50}}],"responses":{"200":{"description":"Recent changes.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AroundChanges"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"503":{"description":"Change history is temporarily unavailable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/coffee/availability.json":{"get":{"operationId":"getCoffeeAvailability","tags":["contact"],"summary":"List open coffee slots","description":"Bookable coffee slots in New York, in the host's timezone. Fails closed: when the calendar is stale or unreachable it returns no slots. Booking happens at bookingUrl and is confirmed by hand.","responses":{"200":{"description":"Open slots.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Availability"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET or HEAD.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"503":{"description":"The calendar is unavailable; slots is empty. Retry after 60 seconds.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Availability"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/ledger.json":{"get":{"operationId":"getCrawlLedger","tags":["lens"],"summary":"Read the AI-crawler ledger","description":"The last 30 days of identified AI-crawler visits to this site, priced at one cent a page as commentary.","responses":{"200":{"description":"The ledger.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Ledger"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"502":{"description":"Analytics could not be read (code upstream_failed).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Ledger"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"503":{"description":"Analytics is not configured on this deployment (code not_configured).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Ledger"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/images/manifest.json":{"get":{"operationId":"getPhotoManifest","tags":["photos"],"summary":"List every published photo","description":"Every published photo with its thumbnail URLs, full-resolution key, size and upload date. The homepage grid draws from it.","responses":{"200":{"description":"The manifest.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PhotoManifest"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}},"/resume.json":{"get":{"operationId":"getResume","tags":["about"],"summary":"Read the resume","description":"Aadharsh Pannirselvam's resume as JSON Resume. The same content is at /resume.md and /resume.pdf.","responses":{"200":{"description":"The resume.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Resume"}}},"headers":{"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"405":{"description":"A method other than GET, HEAD, OPTIONS (code method_not_allowed). The Allow header lists them.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Link":{"$ref":"#/components/headers/ServiceDesc"}}},"429":{"description":"Over the shared read budget of 120 requests a minute per caller (code rate_limited).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}},"headers":{"Retry-After":{"description":"Seconds until the per-minute budget resets; at most 60. Takes precedence over RateLimit.","schema":{"type":"integer","minimum":1,"maximum":60}},"RateLimit-Policy":{"description":"The quota this endpoint bills, as a Structured Field List: \"read\";q=120;w=60. q is requests and w the window in seconds.","schema":{"type":"string"}},"RateLimit":{"description":"The policy that refused the request, with nothing remaining (r=0) for up to t=60 seconds.","schema":{"type":"string"}},"Link":{"$ref":"#/components/headers/ServiceDesc"}}}}}}},"components":{"schemas":{"Error":{"type":"object","properties":{"ok":{"type":"boolean","description":"Always false on an error, where the endpoint uses an ok flag."},"error":{"type":"string","description":"A sentence describing what went wrong, for a person or an agent to read."},"code":{"type":"string","description":"A stable machine token, where the endpoint sets one: not_found, method_not_allowed, unsupported_api_version, rate_limited, storage_unavailable, internal_error."},"status":{"type":"integer","description":"The HTTP status, repeated in the body."},"hint":{"type":"string","description":"What to try next."},"suggestions":{"type":"array","items":{"type":"string","format":"uri"},"description":"Absolute URLs of the closest real pages, on a 404."},"docs":{"type":"string","format":"uri","description":"Where the API is documented."},"parameter":{"type":"string","description":"The query parameter that was rejected (/ask)."},"allow":{"type":"array","items":{"type":"string"},"description":"The methods the path answers, on a 405."},"supported":{"type":"array","items":{"type":"string"},"description":"The API versions served, on a 400 for API-Version."}},"required":["error"],"description":"The site's error shape. Every JSON endpoint answers its errors in JSON with at least `error`. Endpoints may add their own fields (for example /ask echoes `query_id` and `results`, /rn/tracks keeps `tracks: []`)."},"SearchResult":{"type":"object","properties":{"url":{"type":"string","format":"uri-reference"},"title":{"type":"string"},"description":{"type":"string"},"kind":{"type":"string","enum":["page","writing","document","utility"]},"snippet":{"type":"string"}},"required":["url","title","kind"]},"SearchResults":{"type":"object","properties":{"query":{"type":"string"},"total":{"type":"integer","description":"Matches before the limit."},"returned":{"type":"number","description":"Rows returned."},"results":{"type":"array","items":{"$ref":"#/components/schemas/SearchResult"}}},"required":["query","total","results"]},"AskResult":{"type":"object","properties":{"url":{"type":"string","format":"uri"},"name":{"type":"string"},"site":{"type":"string","const":"aadhar.sh"},"score":{"type":"integer","minimum":0,"maximum":100,"description":"0-100. With Clef ranking, the probability Clef puts on this page."},"description":{"type":"string","description":"An extractive snippet, never model-written."},"schema_object":{"type":"object","properties":{"@context":{"type":"string"},"@type":{"type":"string","enum":["WebPage","BlogPosting","DigitalDocument","WebAPI"]},"@id":{"type":"string"},"url":{"type":"string"},"name":{"type":"string"},"description":{"type":"string"}},"description":"A schema.org node for the result."}},"required":["url","name","score"]},"AskResponse":{"type":"object","properties":{"query_id":{"type":"string"},"query":{"type":"string"},"site":{"type":"string","const":"aadhar.sh"},"mode":{"type":"string","const":"list"},"decontextualized_query":{"type":"string"},"total":{"type":"integer"},"results":{"type":"array","items":{"$ref":"#/components/schemas/AskResult"}},"_meta":{"type":"object","properties":{"version":{"type":"string"},"dialect":{"type":"string","enum":["legacy","0.55"]},"retrieval":{"type":"string"},"ranking":{"type":"string","description":"Which ranker ran: Clef, or lexical with the reason."},"description":{"type":"string","const":"extractive"},"modes_supported":{"type":"array","items":{"type":"string"}}}}},"required":["query_id","results"],"description":"NLWeb /ask answer, returned as one JSON body when streaming=0."},"PhotoMetadata":{"type":"object","properties":{"camera":{"type":["string","null"]},"lens":{"type":["string","null"]},"aperture":{"type":["string","null"],"description":"As written, for example f/2.8."},"shutter":{"type":["string","null"],"description":"As written, for example 1/60."},"iso":{"type":["integer","null"]},"focal":{"type":["string","null"]},"ev":{"type":["number","string","null"],"description":"Exposure compensation: a number, or a signed string such as +0.33."},"date":{"type":["string","null"],"description":"As EXIF writes it, YYYY:MM:DD HH:MM:SS, with no timezone."},"width":{"type":["integer","null"]},"height":{"type":["integer","null"]},"color_space":{"type":["string","null"]},"white_balance":{"type":["string","null"]},"color_temp":{"type":["integer","null"]},"wb_shift":{"type":["string","null"]},"flash":{"type":["string","null"]},"exposure_mode":{"type":["string","null"]},"meter":{"type":["string","null"]},"focus_mode":{"type":["string","null"]},"drive":{"type":["string","null"]},"sharpness":{"type":["string","null"]},"noise_reduction":{"type":["string","null"]},"clarity":{"type":["integer","null"]},"film":{"type":["string","null"],"description":"Fuji film simulation."},"dr":{"type":["string","null"]},"dr_value":{"type":["integer","null"]},"chrome":{"type":["string","null"]},"chrome_blue":{"type":["string","null"]},"grain":{"type":["string","null"]},"grain_size":{"type":["string","null"]},"highlight_tone":{"type":["string","null"]},"shadow_tone":{"type":["string","null"]},"saturation":{"type":["string","null"]},"recipe":{"$ref":"#/components/schemas/FujiRecipe"}},"description":"Public-safe EXIF and Fuji fields, read from the file. A field the camera did not record is null and a field the extractor never read is absent: nothing is guessed."},"FujiRecipe":{"type":"object","description":"The frame's film recipe card, keyed the way a recipe is written down. Absent on frames with no recipe.","properties":{"Film Simulation":{"type":"string"},"Dynamic Range":{"type":"string"},"Grain Effect":{"type":"string"},"Color Chrome Effect":{"type":"string"},"Color Chrome FX Blue":{"type":"string"},"White Balance":{"type":"string"},"Highlight":{"type":"string"},"Shadow":{"type":"string"},"Color":{"type":"string"},"Sharpness":{"type":"string"},"High ISO NR":{"type":"string"},"Clarity":{"type":"string"},"ISO":{"type":"string"},"Exposure Compensation":{"type":"string"}},"additionalProperties":{"type":["string","number","boolean","null"]}},"Photo":{"type":"object","properties":{"stem":{"type":"string","description":"The photo's id."},"alt":{"type":"string","description":"Caption, up to 240 characters."},"full":{"type":["string","null"],"description":"Full-resolution original URL."},"thumb":{"type":"object","properties":{"avif":{"type":["string","null"]},"jpg":{"type":["string","null"]},"small":{"type":["string","null"]},"xs":{"type":["string","null"]}}},"metadata":{"$ref":"#/components/schemas/PhotoMetadata"},"score":{"type":"number","description":"Present when q was given."},"matched":{"type":"array","items":{"type":"string"},"description":"Terms that matched, when q was given."}},"required":["stem","thumb","metadata"]},"PhotoQuery":{"type":"object","properties":{"query":{"type":"object","properties":{"q":{"type":"string"},"camera":{"type":"string"},"lens":{"type":"string"},"film":{"type":"string"},"recipe":{"type":"string"},"from":{"type":"string"},"to":{"type":"string"}},"description":"The normalized filters, empty strings when absent."},"ranking":{"type":"object","properties":{"mode":{"type":"string","enum":["filters-only","no-terms","all-terms","partial","no-match"]},"terms":{"type":"array","items":{"type":"string"}},"semantic":{"type":"boolean"},"dropped":{"type":"array","items":{"type":"string"},"description":"Terms dropped as matching nothing; omitted when empty."},"common":{"type":"array","items":{"type":"string"},"description":"Terms dropped as too common; omitted when empty."}},"required":["mode","terms","semantic"]},"total":{"type":"integer"},"offset":{"type":"integer"},"limit":{"type":"integer"},"photos":{"type":"array","items":{"$ref":"#/components/schemas/Photo"}}},"required":["total","photos"]},"RelLink":{"type":"object","properties":{"rel":{"type":"string"},"href":{"type":"string"},"type":{"type":"string"},"title":{"type":"string"},"hreflang":{"type":"string"}},"required":["rel","href"],"description":"A <link> or Link header entry."},"Probe":{"description":"One well-known path fetched from the target's origin.","anyOf":[{"type":"object","properties":{"ok":{"type":"boolean"},"status":{"type":"integer"},"url":{"type":"string"},"contentType":{"type":"string"},"headers":{"type":"object","additionalProperties":{"type":"string"}},"body":{"type":"string","description":"The body, capped."},"truncated":{"type":"boolean"}},"required":["ok","status","url"],"description":"Reached with a 2xx."},{"type":"object","properties":{"ok":{"type":"boolean"},"status":{"type":"integer"},"url":{"type":"string"},"headers":{"type":"object","additionalProperties":{"type":"string"}}},"required":["ok","status","url"],"description":"Answered with another status."},{"type":"object","properties":{"ok":{"type":"boolean"},"error":{"type":"string"},"url":{"type":"string"}},"required":["ok","error","url"],"description":"Could not be fetched."}]},"LensPhases":{"type":"object","properties":{"page":{"type":"boolean"},"discovery":{"type":"boolean"},"botViews":{"type":"boolean"},"discoveryDeferred":{"type":"boolean"},"discoveryCached":{"type":"boolean"},"discoveryShared":{"type":"boolean"},"subrequestCap":{"type":"boolean"},"wallCheck":{"type":"string","description":"ok, none, no AI binding, or the error the wall check hit."}},"required":["page","discovery","botViews"],"description":"Which passes ran. A field from a pass that did not run is absent, never zero."},"BotView":{"type":"object","properties":{"key":{"type":"string"},"label":{"type":"string"},"owner":{"type":"string"},"userAgent":{"type":"string"},"role":{"type":"string","enum":["control","search","train","answers"]},"status":{"type":["integer","null"]},"contentType":{"type":"string"},"sampleBytes":{"type":"integer"},"blocked":{"type":"boolean"},"challenge":{"type":"boolean"},"redirected":{"type":"boolean"},"error":{"type":"string"},"wall":{"type":"object","properties":{"p":{"type":["number","null"]},"model":{"type":"string"},"error":{"type":"string"}},"required":["p","model"],"description":"A model's read of whether the sample is a bot wall."}},"required":["key","label","role","status","blocked","challenge"],"description":"The target as one crawler's User-Agent sees it."},"AgentDoor":{"description":"A JSON discovery document on the target.","anyOf":[{"type":"object","properties":{"present":{"type":"boolean"},"status":{"type":["integer","null"]},"unknown":{"type":"boolean"}},"required":["present","status","unknown"]},{"type":"object","properties":{"present":{"type":"boolean"},"note":{"type":"string"}},"required":["present","note"]},{"type":"object","properties":{"present":{"type":"boolean"},"detail":{"type":"string"}},"required":["present","detail"]}]},"AgentVerdict":{"type":"object","properties":{"verdict":{"type":"string","enum":["yes","likely","maybe","no","unknown"]},"detail":{"type":"string"},"error":{"type":"string"}},"required":["verdict","detail"]},"ReadinessCheck":{"type":"object","properties":{"key":{"type":"string"},"category":{"type":"string"},"label":{"type":"string"},"status":{"type":"string","enum":["pass","fail","unknown","neutral"]},"detail":{"type":"string"},"optional":{"type":"boolean"},"countInScore":{"type":"boolean"},"notApplicable":{"type":"boolean","description":"Present and true on a check the site has declared does not apply to it; its status is then neutral."}},"required":["key","status"]},"LensObservation":{"type":"object","properties":{"ok":{"type":"boolean"},"url":{"type":"string","format":"uri"},"finalUrl":{"type":"string","format":"uri"},"redirected":{"type":"boolean"},"status":{"type":"integer"},"contentType":{"type":"string"},"binary":{"type":"boolean"},"truncated":{"type":"boolean"},"elapsedMs":{"type":"integer"},"fetchedBy":{"type":"string"},"headers":{"type":"object","additionalProperties":{"type":"string"},"description":"Response headers, lowercased."},"bodyUnreadable":{"type":"object","properties":{"reason":{"type":"string","enum":["undecodable-content-encoding"]},"encoding":{"type":"string"}},"required":["reason","encoding"]},"framable":{"type":"boolean"},"frameReason":{"type":["string","null"]},"phases":{"$ref":"#/components/schemas/LensPhases"},"anatomy":{"type":"object","properties":{"rawHtml":{"type":"string"},"rawBytes":{"type":"integer"},"parsedBytes":{"type":"integer"},"parseTruncated":{"type":"boolean"},"text":{"type":"string"},"wordCount":{"type":"integer"},"imgTotal":{"type":"integer"},"imgNoAlt":{"type":"integer"},"headings":{"type":"array","items":{"type":"object","properties":{"level":{"type":"integer","minimum":1,"maximum":6},"text":{"type":"string"}},"required":["level","text"]}}},"description":"The document itself. parsedBytes and parseTruncated are HTML only."},"structured":{"type":"object","properties":{"title":{"type":"string"},"meta":{"type":"object","additionalProperties":{"type":"string"}},"og":{"type":"object","additionalProperties":{"type":"string"}},"twitter":{"type":"object","additionalProperties":{"type":"string"}},"jsonld":{"type":"array","items":{"anyOf":[{"type":"object","properties":{"valid":{"type":"boolean"},"types":{"type":"array","items":{"type":"string"}},"json":{"type":"string","description":"The block, re-serialized as indented JSON text."}},"required":["valid","types","json"]},{"type":"object","properties":{"valid":{"type":"boolean"},"error":{"type":"string"},"raw":{"type":"string"}},"required":["valid","error","raw"]}]}},"microdata":{"type":"object","properties":{"itemtypes":{"type":"array","items":{"type":"string"}},"props":{"type":"array","items":{"type":"string"}}}},"rdfa":{"type":"object","properties":{"typeof":{"type":"array","items":{"type":"string"}},"properties":{"type":"array","items":{"type":"string"}}}},"microformats":{"type":"array","items":{"type":"string"}},"relLinks":{"type":"array","items":{"$ref":"#/components/schemas/RelLink"}}},"description":"Structured data on an HTML page."},"ai":{"type":"object","properties":{"markdown":{"type":"string","description":"The page as Markdown (HTML only)."},"llmsTxtPresent":{"type":"boolean"},"directives":{"type":"object","properties":{"metaRobots":{"type":["string","null"]},"xRobotsTag":{"type":["string","null"]},"namesAiCrawlers":{"type":"boolean"}}}}},"cost":{"type":["object","null"],"description":"What reading the page costs a model, per representation. Null when nothing could be priced.","properties":{"tokenizer":{"type":"string"},"checked":{"type":"string"},"rates":{"type":"array","items":{"type":"object","properties":{"model":{"type":"string"},"usdPerMtok":{"type":"number"}},"required":["model","usdPerMtok"]}},"tiers":{"type":"array","items":{"type":"object","properties":{"key":{"type":"string","enum":["html","text","markdown","outline","raw"]},"label":{"type":"string"},"note":{"type":"string"},"chars":{"type":"integer"},"tokens":{"type":"integer"}},"required":["key","chars","tokens"]}},"partial":{"type":"object","properties":{"parsedBytes":{"type":"integer"},"rawBytes":{"type":"integer"}}}}},"discovery":{"type":"object","properties":{"origin":{"type":"string"},"feeds":{"type":"array","items":{"$ref":"#/components/schemas/RelLink"}},"oauthDiscovery":{"type":"object","properties":{"openidConfiguration":{"$ref":"#/components/schemas/Probe"},"oauthAuthorizationServer":{"$ref":"#/components/schemas/Probe"}}},"commerce":{"type":"object","properties":{"ucp":{"$ref":"#/components/schemas/Probe"},"acp":{"$ref":"#/components/schemas/Probe"},"ap2":{"$ref":"#/components/schemas/Probe"}}},"robotsTxt":{"$ref":"#/components/schemas/Probe"},"sitemapXml":{"$ref":"#/components/schemas/Probe"},"llmsTxt":{"$ref":"#/components/schemas/Probe"},"llmsFullTxt":{"$ref":"#/components/schemas/Probe"},"aiTxt":{"$ref":"#/components/schemas/Probe"},"securityTxt":{"$ref":"#/components/schemas/Probe"},"webBotAuth":{"$ref":"#/components/schemas/Probe"},"oauthProtectedResource":{"$ref":"#/components/schemas/Probe"},"authMd":{"$ref":"#/components/schemas/Probe"},"mcpServerCard":{"$ref":"#/components/schemas/Probe"},"agentSkills":{"$ref":"#/components/schemas/Probe"},"sitemapDeclared":{"description":"The sitemap robots.txt declares, with an entries count when it parsed. Null when none is declared.","anyOf":[{"$ref":"#/components/schemas/Probe"},{"type":"null"}]},"dnsAid":{"anyOf":[{"type":"object","properties":{"ok":{"type":"boolean"},"found":{"type":"boolean"},"dnssecValidated":{"type":"boolean"},"names":{"type":"array","items":{"type":"string"}},"records":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"status":{"type":"integer"},"dnssecValidated":{"type":"boolean"},"answers":{"type":"integer"}}}}},"required":["ok","found","names","records"]},{"type":"object","properties":{"ok":{"type":"boolean"},"found":{"type":"boolean"},"names":{"type":"array","items":{"type":"string"}},"error":{"type":"string"}},"required":["ok","found","error"]}]},"agentsMd":{"type":"object","properties":{"ok":{"type":"boolean"},"present":{"type":"boolean"},"unknown":{"type":"boolean"},"variant":{"type":"string"},"status":{"type":"integer"},"body":{"type":"string"},"truncated":{"type":"boolean"},"note":{"type":"string"},"error":{"type":"string"}},"required":["ok","present"]}},"description":"Well-known paths on the target's origin. Present when the discovery pass ran."},"wire":{"type":"object","properties":{"dictionary":{"type":"object","properties":{"observed":{"type":"boolean"},"offer":{"type":["string","null"]},"negotiates":{"type":"boolean"},"activeEncoding":{"type":["string","null"]}}},"ech":{"type":"object","properties":{"observed":{"type":"boolean"},"recordPresent":{"type":"boolean"},"parsed":{"type":"boolean"},"dnssecValidated":{"type":"boolean"},"error":{"type":"string"}},"required":["observed","recordPresent","parsed"]}},"description":"Transport features: shared compression dictionaries and Encrypted Client Hello."},"terms":{"type":"object","properties":{"path":{"type":"string"},"robotsPresent":{"type":"boolean"},"robotsUnknown":{"type":"boolean"},"robotsError":{"type":["string","null"]},"scoreboard":{"type":"array","items":{"type":"object","properties":{"ua":{"type":"string"},"owner":{"type":"string"},"kind":{"type":"string"},"note":{"type":"string"},"verdict":{"type":"string","enum":["allow","block","unknown"]},"matchedUa":{"type":["string","null"]},"rule":{"type":["string","null"]}},"required":["ua","verdict"]}},"signals":{"type":"array","items":{"type":"object","properties":{"agents":{"type":"array","items":{"type":"string"}},"raw":{"type":"string"},"parsed":{"type":"object","additionalProperties":{"type":"string"}}}}},"paid":{"type":"object","properties":{"http402":{"type":"boolean"},"crawlerHeaders":{"type":"object","additionalProperties":{"type":"string"}},"x402":{"type":["string","null"]}}},"enforcement":{"type":"object","properties":{"status":{"type":"integer"},"challenged":{"type":"boolean"},"blocked":{"type":"boolean"}}},"directives":{"type":"object","properties":{"metaRobots":{"type":["string","null"]},"xRobotsTag":{"type":["string","null"]},"noai":{"type":"boolean"}}},"tdmrep":{"type":"object","properties":{"present":{"type":"boolean"},"invalid":{"type":"string"},"body":{"type":"string"},"rules":{"type":"integer"},"reserved":{"type":["boolean","null"]},"location":{"type":["string","null"]},"policy":{"type":["string","null"]}},"required":["present"],"description":"TDMRep (W3C) at /.well-known/tdmrep.json."},"spectrum":{"type":"object","properties":{"tier":{"type":"string","enum":["open","signaled","enforced","paid"]},"reasons":{"type":"array","items":{"type":"string"}}},"required":["tier","reasons"]}},"description":"What the target says AI crawlers may do, and whether it enforces it."},"agent":{"type":"object","properties":{"mcp":{"$ref":"#/components/schemas/AgentVerdict"},"nlweb":{"$ref":"#/components/schemas/AgentVerdict"},"webmcp":{"type":"object","properties":{"found":{"type":"boolean"},"kind":{"type":"string","enum":["inline","bridge"]},"marker":{"type":"string"}},"required":["found"]},"agentCard":{"$ref":"#/components/schemas/AgentDoor"},"openapi":{"$ref":"#/components/schemas/AgentDoor"},"aiPlugin":{"$ref":"#/components/schemas/AgentDoor"},"apiCatalog":{"$ref":"#/components/schemas/AgentDoor"},"mdNegotiation":{"type":"object","properties":{"supported":{"type":"boolean"},"contentType":{"type":"string"},"status":{"type":"integer"},"note":{"type":"string"},"error":{"type":"string"}},"required":["supported"]},"llmsTxt":{"type":"object","properties":{"present":{"type":"boolean"},"unknown":{"type":"boolean"}}},"strategy":{"type":"object","properties":{"verdict":{"type":"string","enum":["agent-native","agent-readable","human-only"]},"note":{"type":"string"},"action":{"type":"array","items":{"type":"string"}},"readable":{"type":"array","items":{"type":"string"}},"unknowns":{"type":"array","items":{"type":"string"}}},"required":["verdict"]}},"description":"The doors an agent could use."},"botViews":{"type":"array","items":{"$ref":"#/components/schemas/BotView"},"description":"Empty when the bot pass was skipped."},"readiness":{"type":"object","properties":{"overall":{"type":"integer","minimum":0,"maximum":100},"level":{"type":"integer","enum":[0,1,3,5]},"levelName":{"type":"string"},"levelNote":{"type":["string","null"]},"categories":{"type":"array","items":{"type":"object","properties":{"key":{"type":"string"},"label":{"type":"string"},"score":{"type":"integer"},"passed":{"type":"integer"},"total":{"type":"integer"},"checkCount":{"type":"integer"},"countInScore":{"type":"boolean"}}}},"checks":{"type":"object","description":"One entry per check, keyed by its name.","additionalProperties":{"$ref":"#/components/schemas/ReadinessCheck"}},"counted":{"type":"integer"},"passed":{"type":"integer"},"keyless":{"type":["string","null"],"description":"Why the authority checks do not apply, when the site's OpenAPI document declares every operation keyless; otherwise null."},"scoringNote":{"type":"string"},"nextActions":{"type":"array","items":{"type":"object","properties":{"key":{"type":"string"},"label":{"type":"string"}},"required":["key","label"]}},"botViews":{"type":"array","items":{"$ref":"#/components/schemas/BotView"}},"field":{"type":"object","properties":{"overall":{"type":["integer","null"]},"scoringNote":{"type":"string"},"components":{"type":"array","items":{"type":"object","properties":{"key":{"type":"string","enum":["identifiedFetch","sampledBots","usableBody","agentDoor"]},"label":{"type":"string"},"score":{"type":["integer","null"]},"detail":{"type":"string"}}}}}}},"description":"The agent-readiness score and the checks behind it."},"available":{"type":"boolean","description":"mode=cloudflare: false when Cloudflare's score could not be read, with error."},"score":{"type":"integer","description":"mode=cloudflare only: level times 20."},"levelName":{"type":["string","null"],"description":"mode=cloudflare only."},"source":{"type":"string","description":"mode=cloudflare only."},"sourceUrl":{"type":"string","format":"uri","description":"mode=cloudflare only."},"fromCache":{"type":"boolean","description":"mode=cloudflare only."},"error":{"type":"string","description":"mode=cloudflare only, when available is false."},"level":{"type":"integer","minimum":0,"maximum":5,"description":"mode=cloudflare only, 0-5."}},"required":["ok"],"description":"One public URL as a machine reads it. The page-derived fields are always present; discovery, wire, terms, agent, botViews and readiness appear when the discovery pass ran (see phases). With mode=cloudflare the body is ok, available, level, score, levelName, source, sourceUrl and fromCache instead."},"LensSummary":{"type":"object","properties":{"url":{"type":"string"},"finalUrl":{"type":"string"},"redirected":{"type":"boolean"},"status":{"type":["integer","null"]},"contentType":{"type":"string"},"elapsedMs":{"type":["integer","null"]},"truncated":{"type":"boolean"},"title":{"type":"string"},"wordCount":{"type":"integer"},"bytes":{"type":["integer","null"]},"parsedBytes":{"type":["integer","null"]},"parseTruncated":{"type":"boolean"},"readiness":{"type":["integer","null"]},"fieldScore":{"type":["integer","null"]},"level":{"type":["integer","null"]},"levelName":{"type":["string","null"]},"levelNote":{"type":["string","null"]},"tier":{"type":["string","null"],"description":"unknown or a spectrum tier when measured; null when discovery did not run."},"doors":{"type":["integer","null"]},"cost":{"type":["object","null"],"properties":{"tokens":{"type":"integer"},"usdPerRead":{"type":"number"},"model":{"type":"string"}}},"phases":{"$ref":"#/components/schemas/LensPhases"},"surfaces":{"type":["object","null"],"description":"Null when discovery did not run.","properties":{"llms":{"type":"boolean"},"markdown":{"type":"boolean"},"mcp":{"type":"boolean"},"agentCard":{"type":"boolean"},"apiCatalog":{"type":"boolean"}}}},"required":["url","finalUrl","status","phases"]},"LensComparison":{"type":"object","properties":{"ok":{"type":"boolean"},"comparedAt":{"type":"string","format":"date-time"},"left":{"$ref":"#/components/schemas/LensSummary"},"right":{"$ref":"#/components/schemas/LensSummary"},"changes":{"type":"array","items":{"type":"object","properties":{"field":{"type":"string"},"label":{"type":"string"},"before":{"type":["string","integer","boolean","null"]},"after":{"type":["string","integer","boolean","null"]}},"required":["field","before","after"]}},"discovery":{"type":"object","properties":{"left":{"type":"string","enum":["none","deferred","cached","shared","refused","live"]},"right":{"type":"string","enum":["none","deferred","cached","shared","refused","live"]}}}},"required":["ok","left","right","changes"]},"Census":{"type":"object","properties":{"ok":{"type":"boolean"},"roster":{"type":"integer"},"snapshots":{"type":"integer"},"firstYmd":{"type":["string","null"]},"lastYmd":{"type":["string","null"]},"lastSweep":{"description":"The most recent weekly sweep. Null when none is recorded; only error when it could not be read.","anyOf":[{"type":"null"},{"type":"object","properties":{"error":{"type":["string","null"]}},"required":["error"]},{"type":"object","properties":{"ymd":{"type":"string"},"roster":{"type":"integer"},"recorded":{"type":"integer"},"written":{"type":"integer"},"outcomes":{"type":"object","additionalProperties":{"type":"integer"},"description":"Hosts per outcome: dispatched, duplicate, dispatch_failed, written, cap, failed."},"unfinished":{"type":"array","items":{"type":"string"}},"problems":{"type":"array","items":{"type":"object","properties":{"host":{"type":"string"},"outcome":{"type":"string"},"detail":{"type":["string","null"]}}}}},"required":["ymd","roster","recorded","written","outcomes"]}]},"sites":{"type":"array","items":{"type":"object","properties":{"host":{"type":"string"},"url":{"type":"string"},"tier":{"type":"string"},"score":{"type":["number","null"]},"level":{"type":["integer","null"]},"doors":{"type":"integer"},"verdict":{"type":"string"},"delta":{"type":"integer"},"surfaces":{"type":"object","properties":{"llms":{"type":"boolean"},"md":{"type":"boolean"},"mcp":{"type":"boolean"},"agents":{"type":"boolean"},"jsonld":{"type":"boolean"},"webBotAuth":{"type":"boolean"}},"description":"Empty when the stored row could not be parsed."},"series":{"type":"array","items":{"type":"object","properties":{"ymd":{"type":"string"},"score":{"type":["number","null"]},"tier":{"type":"string"},"doors":{"type":"integer"}}}}}}}},"required":["ok","sites"]},"Track":{"type":"object","properties":{"id":{"type":"string"},"title":{"type":"string"},"artists_text":{"type":"string"},"spotify_url":{"type":"string","format":"uri"},"song_link_url":{"type":"string","format":"uri","description":"A song.link forwarder to the listener's own music service."},"duration_ms":{"type":["integer","null"]},"preview_url":{"type":["string","null"]},"is_explicit":{"type":"boolean"},"image_url":{"type":["string","null"]},"artists":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"spotify_url":{"type":"string"},"image_url":{"type":["string","null"]}}}}},"required":["id","title","song_link_url"]},"Tracks":{"type":"object","properties":{"playlist_id":{"type":"string"},"playlist_name":{"type":"string"},"tracks":{"type":"array","items":{"$ref":"#/components/schemas/Track"}},"fetched_at":{"type":"string","format":"date-time"},"error":{"type":"string","description":"Present, with an empty tracks list, when no playlist is set."}},"required":["tracks"]},"AroundReport":{"type":"object","properties":{"crawledBy":{"type":"string"},"crawledAt":{"type":"string","format":"date-time"},"signedWith":{"type":"string"},"count":{"type":"integer"},"results":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"url":{"type":"string"},"finalUrl":{"type":"string"},"status":{"type":"integer"},"title":{"type":"string"},"description":{"type":"string"},"ogImage":{"type":"string"},"server":{"type":"string"},"lastModified":{"type":"string","description":"The Last-Modified header as sent, empty when absent."},"contentType":{"type":"string"},"bodyHash":{"type":"string","description":"SHA-256 hex of the bytes read."},"bytesRead":{"type":"integer"},"truncated":{"type":"boolean"},"robots":{"type":"string","enum":["allow","disallow","undetermined"]},"robotsRule":{"type":"string"},"skipped":{"type":"string","enum":["robots"]},"error":{"type":"string"},"elapsedMs":{"type":"integer"}},"required":["name","url","elapsedMs"],"description":"A crawled page, a robots skip (skipped, robotsRule) or a failure (error)."}}},"required":["crawledAt","results"]},"Pending":{"type":"object","properties":{"pending":{"type":"boolean"},"note":{"type":"string"}},"required":["pending","note"],"description":"No snapshot exists yet."},"AroundChanges":{"type":"object","properties":{"ok":{"type":"boolean"},"available":{"type":"boolean"},"latestObservedAt":{"type":["string","null"]},"targetCount":{"type":"integer"},"note":{"type":"string"},"error":{"type":"string"},"changes":{"type":"array","items":{"type":"object","properties":{"target":{"type":"string"},"name":{"type":"string"},"observedAt":{"type":"string","format":"date-time"},"previousObservedAt":{"type":"string","format":"date-time"},"ageMs":{"type":"integer"},"severity":{"type":"string","enum":["high","medium","low"]},"changes":{"type":"array","items":{"type":"object","properties":{"field":{"type":"string","enum":["status","final_url","title","description","content_type","robots","skipped","error","content"]},"before":{"type":["string","integer","null"]},"after":{"type":["string","integer","null"]},"detail":{"type":"string","description":"content only, which carries no before or after."}},"required":["field"]}}}}}},"required":["ok","available","changes"]},"Availability":{"type":"object","properties":{"available":{"type":"boolean"},"stale":{"type":"boolean"},"source":{"type":"string","enum":["fresh","stale","live","none"]},"checkedAt":{"type":"string","format":"date-time"},"ageSeconds":{"type":["integer","null"]},"timezone":{"type":"string"},"bookingUrl":{"type":"string","format":"uri"},"error":{"type":"string"},"slots":{"type":"array","items":{"type":"object","properties":{"start":{"type":"string","format":"date-time"},"end":{"type":"string","format":"date-time"},"startMs":{"type":"integer"},"endMs":{"type":"integer"},"durationMinutes":{"type":"integer"}}}}},"required":["available","slots"]},"Ledger":{"type":"object","properties":{"ok":{"type":"boolean"},"via":{"type":"string","enum":["binding","token"]},"reason":{"type":"string","description":"Present when ok is false."},"binding_fallback":{"type":"string"},"error":{"type":"string","description":"A sentence, present when ok is false."},"code":{"type":"string","description":"not_configured or upstream_failed, present when ok is false."},"window_days":{"type":"integer"},"rate_usd":{"type":"number"},"note":{"type":"string"},"line_items":{"type":"array","items":{"type":"object","properties":{"bot":{"type":"string"},"owner":{"type":"string"},"kind":{"type":"string"},"hits":{"type":"integer"},"amountUsd":{"type":"number"}}}},"total_hits":{"type":"integer"},"total_usd":{"type":"number"},"cost":{"description":"What the site itself cost over the window, from Cloudflare billing.","anyOf":[{"type":"object","properties":{"available":{"type":"boolean"},"total_usd":{"type":"number"},"currency":{"type":"string"},"from":{"type":"string","format":"date"},"to":{"type":"string","format":"date"},"service_families":{"type":"array","items":{"type":"string"}},"note":{"type":"string"}},"required":["available","total_usd","currency"]},{"type":"object","properties":{"available":{"type":"boolean"},"reason":{"type":"string"}},"required":["available","reason"]}]}},"required":["ok"]},"PhotoManifest":{"type":"object","properties":{"photos":{"type":"array","items":{"type":"object","properties":{"stem":{"type":"string"},"full":{"type":"string"},"thumb_avif":{"type":"string"},"thumb_jpg":{"type":"string"},"thumb_small":{"type":"string"},"thumb_xs":{"type":["string","null"]},"size":{"type":"integer"},"uploaded":{"type":["string","null"]},"album":{"type":["string","null"]},"heif":{"type":["string","null"]}}}},"count":{"type":"integer"}},"required":["photos","count"]},"Resume":{"type":"object","properties":{"$schema":{"type":"string","format":"uri"},"meta":{"type":"object","properties":{"canonical":{"type":"string","format":"uri"},"version":{"type":"string"},"note":{"type":"string"}}},"basics":{"type":"object","properties":{"name":{"type":"string"},"email":{"type":"string","format":"email"},"url":{"type":"string","format":"uri"},"profiles":{"type":"array","items":{"type":"object","properties":{"network":{"type":"string"},"username":{"type":"string"},"url":{"type":"string","format":"uri"}},"required":["network","username"]}}},"required":["name"]},"work":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"position":{"type":"string"},"location":{"type":"string"},"startDate":{"type":"string","description":"YYYY-MM."},"endDate":{"type":"string","description":"YYYY-MM; absent for the current role."},"summary":{"type":"string"},"highlights":{"type":"array","items":{"type":"string"}}},"required":["name","position","startDate"]}},"education":{"type":"array","items":{"type":"object","properties":{"institution":{"type":"string"},"location":{"type":"string"},"area":{"type":"string"},"studyType":{"type":"string"},"score":{"type":"string"},"endDate":{"type":"string"}},"required":["institution"]}},"volunteer":{"type":"array","items":{"type":"object","properties":{"organization":{"type":"string"},"position":{"type":"string"},"location":{"type":"string"},"startDate":{"type":"string"},"endDate":{"type":"string"},"highlights":{"type":"array","items":{"type":"string"}}},"required":["organization","position"]}}},"required":["basics","work"],"description":"A JSON Resume document (jsonresume.org)."}},"headers":{"ServiceDesc":{"description":"Includes `</openapi.json>; rel=\"service-desc\"` (RFC 8631).","schema":{"type":"string"}}}}}