{"openapi":"3.1.0","info":{"title":"getReport API","version":"1.0.0","summary":"Run a website checkup and read the full report as JSON.","description":"Free and keyed. A key allows 100 new reports a day; cached results (the same page, device and location within 12 hours) are free and do not count. Every report is also a page at getreport.app/r/{id}.","contact":{"email":"hello@getreport.app","url":"https://getreport.app/api"}},"servers":[{"url":"https://api.getreport.app"}],"security":[{"apiKey":[]}],"tags":[{"name":"Reports","description":"Start a checkup and read the result."},{"name":"Exports","description":"The same report as PDF, Markdown, CSV or a badge."},{"name":"Service","description":"Public status of the service."},{"name":"Ownership","description":"Prove you control a domain with a DNS record, a meta tag or a file. No email, no account."}],"paths":{"/api/v1/reports":{"post":{"tags":["Reports"],"operationId":"createReport","summary":"Start a report, or get the cached one","description":"Returns 202 with the new id, or 200 when a report of the same page, device and location from the last 12 hours exists (cached) or is still running (coalesced). Poll GET /api/v1/reports/{id} until status is done, partial or failed; most reports take 20-60 s.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["url"],"properties":{"url":{"type":"string","maxLength":2048,"description":"The page to check. https:// is assumed when missing.","example":"https://example.com/pricing"},"device":{"type":"string","enum":["mobile","desktop"],"default":"mobile"},"force":{"type":"boolean","description":"Ignore the cache and run again. Counts against the quota."}}}}}},"responses":{"200":{"description":"A cached or already running report.","headers":{"X-RateLimit-Limit":{"description":"New reports this key may start in 24 hours.","schema":{"type":"integer"}},"X-RateLimit-Remaining":{"description":"New reports left in the current 24-hour window.","schema":{"type":"integer"}},"X-RateLimit-Reset":{"description":"Seconds until the oldest counted report leaves the window.","schema":{"type":"integer"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateResult"}}}},"202":{"description":"A new report was queued.","headers":{"X-RateLimit-Limit":{"description":"New reports this key may start in 24 hours.","schema":{"type":"integer"}},"X-RateLimit-Remaining":{"description":"New reports left in the current 24-hour window.","schema":{"type":"integer"}},"X-RateLimit-Reset":{"description":"Seconds until the oldest counted report leaves the window.","schema":{"type":"integer"}},"Location":{"description":"The report URL.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateResult"}}}},"400":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"401":{"description":"The key is not valid (INVALID_API_KEY).","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"403":{"description":"The site asked not to be checked, or checks from your address are paused (SITE_BLOCKED, CLIENT_BLOCKED).","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"422":{"description":"The address is private or cannot be reached (PRIVATE_ADDRESS, UNREACHABLE).","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Daily quota used (RATE_LIMITED_KEY), or the site was checked 5 times in the last hour (RATE_LIMITED_HOST). Wait Retry-After seconds.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}},"headers":{"X-RateLimit-Limit":{"description":"New reports this key may start in 24 hours.","schema":{"type":"integer"}},"X-RateLimit-Remaining":{"description":"New reports left in the current 24-hour window.","schema":{"type":"integer"}},"X-RateLimit-Reset":{"description":"Seconds until the oldest counted report leaves the window.","schema":{"type":"integer"}},"Retry-After":{"schema":{"type":"integer"}}}}}}},"/api/v1/reports/{id}":{"get":{"tags":["Reports"],"operationId":"getReport","summary":"Read a report","description":"The full report: scores, every module with its findings, the plain-language fix for each, and links to the HTML page, PDF and badge. The same JSON as getreport.app/r/{id}.json.","security":[],"parameters":[{"name":"id","in":"path","required":true,"description":"Report id, 10 letters and digits.","schema":{"type":"string","pattern":"^[0-9A-Za-z]{10}$"},"example":"PINUz7tvTi"}],"responses":{"200":{"description":"The report.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Report"}}}},"404":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"410":{"description":"Removed at the site owner’s request.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/reports/{id}/events":{"get":{"tags":["Reports"],"operationId":"reportEvents","summary":"Follow a running report (server-sent events)","description":"A text/event-stream with one event per module status change and a final `report` event. Use it instead of polling.","security":[],"parameters":[{"name":"id","in":"path","required":true,"description":"Report id, 10 letters and digits.","schema":{"type":"string","pattern":"^[0-9A-Za-z]{10}$"},"example":"PINUz7tvTi"}],"responses":{"200":{"description":"The event stream.","content":{"text/event-stream":{}}}}}},"/api/v1/compare":{"post":{"tags":["Reports"],"operationId":"compare","summary":"Start reports for 2-5 sites at once","description":"One report per site, each cached and counted like POST /api/v1/reports.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["urls"],"properties":{"urls":{"type":"array","minItems":2,"maxItems":5,"items":{"type":"string"}},"device":{"type":"string","enum":["mobile","desktop"],"default":"mobile"}}}}}},"responses":{"200":{"description":"One item per site: its report id, or the error for that site."},"400":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"401":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/domains/{host}":{"get":{"tags":["Reports"],"operationId":"domainHistory","summary":"Scores over time for a site","description":"Finished reports and crawls for the host, newest first: date, device and scores, crawl page and issue counts, plus whether the domain is verified and indexed (never the verification token). Report and crawl ids come only with the verified owner's grant in `x-owner-grant`.","security":[],"parameters":[{"name":"host","in":"path","required":true,"schema":{"type":"string"},"example":"example.com"}],"responses":{"200":{"description":"The history."},"400":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/domains/{host}/verify":{"post":{"tags":["Ownership"],"operationId":"startVerification","summary":"The token for a domain and the three ways to publish it","description":"Returns the TXT record, the meta tag and the file to publish. The token stays the same for the domain.","security":[],"parameters":[{"name":"host","in":"path","required":true,"schema":{"type":"string"},"example":"example.com"}],"responses":{"200":{"description":"Token and instructions."},"400":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/domains/{host}/verify/check":{"post":{"tags":["Ownership"],"operationId":"checkVerification","summary":"Look for the token and verify the domain for 12 months","description":"Checks DNS, then the meta tag on the home page, then /.well-known/getreport.txt. On success the answer carries an owner grant for the settings call; 422 lists what was tried.","security":[],"parameters":[{"name":"host","in":"path","required":true,"schema":{"type":"string"},"example":"example.com"}],"responses":{"200":{"description":"Verified, with an owner grant."},"422":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/domains/{host}/plugin-key":{"post":{"tags":["Ownership"],"operationId":"pluginKey","summary":"Verify the domain and get an API key that may check this site only","description":"Used by the getReport WordPress plugin when you click Connect: the same check as verify/check (the plugin publishes the token from verify first), then a key limited to this site and its www twin, 20 new reports a day. The key is shown once; reconnecting revokes the earlier one.","security":[],"parameters":[{"name":"host","in":"path","required":true,"schema":{"type":"string"},"example":"example.com"}],"responses":{"200":{"description":"Verified, with the key."},"422":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"503":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/domains/{host}/settings":{"put":{"tags":["Ownership"],"operationId":"domainSettings","summary":"Let search engines index the reports of a verified domain","description":"Needs the owner grant from the check in the x-owner-grant header, and a verification that has not run out.","security":[],"parameters":[{"name":"host","in":"path","required":true,"schema":{"type":"string"},"example":"example.com"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["indexOptIn"],"properties":{"indexOptIn":{"type":"boolean"}}}}}},"responses":{"200":{"description":"The new status."},"403":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"503":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/reports/{id}/pdf":{"get":{"tags":["Exports"],"operationId":"reportPdf","summary":"The report as a PDF","security":[],"parameters":[{"name":"id","in":"path","required":true,"description":"Report id, 10 letters and digits.","schema":{"type":"string","pattern":"^[0-9A-Za-z]{10}$"},"example":"PINUz7tvTi"}],"responses":{"200":{"description":"The PDF.","content":{"application/pdf":{}}},"404":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/api/v1/reports/{id}/fixes.{format}":{"get":{"tags":["Exports"],"operationId":"reportFixes","summary":"The fixes as a Markdown checklist or a CSV","description":"Markdown pastes into a GitHub issue; the CSV imports into Trello or Jira.","security":[],"parameters":[{"name":"id","in":"path","required":true,"description":"Report id, 10 letters and digits.","schema":{"type":"string","pattern":"^[0-9A-Za-z]{10}$"},"example":"PINUz7tvTi"},{"name":"format","in":"path","required":true,"schema":{"type":"string","enum":["md","csv"]}}],"responses":{"200":{"description":"The checklist.","content":{"text/markdown":{},"text/csv":{}}},"404":{"description":"An error as RFC 9457 problem details, with a machine-readable `code`.","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/badge/{host}.svg":{"get":{"tags":["Exports"],"operationId":"badge","summary":"A score badge for a README or website","description":"The latest overall score, or one module’s. Cached for 24 hours.","security":[],"parameters":[{"name":"host","in":"path","required":true,"schema":{"type":"string"},"example":"example.com"},{"name":"module","in":"query","schema":{"type":"string","enum":["overall","speed","seo","security","a11y","schema","social","practices"],"default":"overall"}}],"responses":{"200":{"description":"The badge.","content":{"image/svg+xml":{}}}}}},"/api/v1/status":{"get":{"tags":["Service"],"operationId":"status","summary":"Queue depth, worker health and today’s speed-test quota","security":[],"responses":{"200":{"description":"The status."}}}}},"components":{"securitySchemes":{"apiKey":{"type":"http","scheme":"bearer","description":"Authorization: Bearer <key>. Keys start with gr_. Request one at hello@getreport.app."}},"schemas":{"Problem":{"type":"object","properties":{"type":{"type":"string"},"title":{"type":"string"},"status":{"type":"integer"},"detail":{"type":"string"},"code":{"type":"string","example":"RATE_LIMITED_KEY"},"retryAfterSec":{"type":"integer"}}},"CreateResult":{"type":"object","required":["id","status","cached","coalesced"],"properties":{"id":{"type":"string","example":"PINUz7tvTi"},"status":{"type":"string","enum":["queued","running","done","partial","failed"]},"cached":{"type":"boolean","description":"A finished report from the last 12 hours."},"coalesced":{"type":"boolean","description":"Joined a report that is still running."}}},"Scores":{"type":"object","description":"Scores 0-100 per module and overall; null when the module did not run.","properties":{"overall":{"type":["integer","null"]},"grade":{"type":["string","null"],"enum":["A","B","C","D","F",null]},"speed":{"type":["integer","null"]},"seo":{"type":["integer","null"]},"security":{"type":["integer","null"]},"a11y":{"type":["integer","null"]},"schema":{"type":["integer","null"]},"social":{"type":["integer","null"]},"practices":{"type":["integer","null"]}}},"Finding":{"type":"object","properties":{"checkId":{"type":"string","example":"meta-description-present"},"module":{"type":"string","enum":["speed","seo","security","a11y","schema","social","practices"]},"severity":{"type":"string","enum":["fail","warn","pass","info"]},"points":{"type":"number","description":"Points this finding takes off the module score."},"title":{"type":"string"},"why":{"type":"string","description":"Why it matters, in plain words."},"fix":{"type":"array","items":{"type":"string"},"description":"Steps to fix it."},"technical":{"type":["string","null"]},"items":{"type":"array","items":{"type":"string"},"description":"Affected URLs or elements."},"learnUrl":{"type":"string"},"outcome":{"type":"boolean","description":"True for a measured result (LCP, Total Blocking Time …) rather than something to do."}}},"TopFix":{"allOf":[{"$ref":"#/components/schemas/Finding"},{"type":"object","properties":{"rank":{"type":"integer"},"points":{"type":"number","description":"Estimated gain across the report: its own points plus its share of the outcomes it improves."},"evidence":{"type":["string","null"],"description":"One short line: the outcomes it improves, or the files it names."}}}]},"Module":{"type":"object","properties":{"module":{"type":"string","enum":["speed","seo","security","a11y","schema","social","practices"]},"label":{"type":"string"},"status":{"type":"string","enum":["waiting","running","done","failed","skipped"]},"score":{"type":["integer","null"]},"summary":{"type":["string","null"]},"findings":{"type":"array","items":{"$ref":"#/components/schemas/Finding"}},"data":{"type":["object","null"],"description":"Module measurements (metrics, headers, tech…)."}}},"Report":{"type":"object","properties":{"id":{"type":"string"},"url":{"type":"string"},"finalUrl":{"type":["string","null"]},"domain":{"type":"string"},"device":{"type":"string","enum":["mobile","desktop"]},"status":{"type":"string","enum":["queued","running","done","partial","failed"]},"scores":{"$ref":"#/components/schemas/Scores"},"createdAt":{"type":"string","format":"date-time"},"finishedAt":{"type":["string","null"],"format":"date-time"},"modules":{"type":"array","items":{"$ref":"#/components/schemas/Module"}},"topFixes":{"type":"array","items":{"$ref":"#/components/schemas/TopFix"}},"links":{"type":"object","properties":{"html":{"type":"string"},"json":{"type":"string"},"pdf":{"type":"string"},"badge":{"type":"string"}}}}}}}}