Agency Plan Required

AcuityScan API

Programmatic access to the full Site+ Scan (350+ checks) and every individual module. JSON in, JSON out. One header for auth, one body field for the domain, one cap (250 requests/day per account).

API + MCP access is an Agency-plan feature ($99/mo or $1,000/yr).

Free and Pro can read these docs, but only Agency accounts can mint a token. See pricing →

Quickstart

From zero to a scan in four steps.

  1. 1Upgrade to Agency. The API surface is Agency-only. See plans →
  2. 2Mint your token in /settings → API Token. One active token per account — copy it the moment we show it, because we hash it on save and can't recover the plaintext.
  3. 3Send the token as a Bearer header (or x-api-key — pick whichever your client likes).
  4. 4Call an endpoint with a JSON body. All POST endpoints take { "domain": "..." }.

First call

curl -X POST https://acuityscan.com/api/v1/scan \
  -H "Authorization: Bearer asc_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{"domain":"example.com"}'

Authentication

Every request must carry a valid API token. Two headers are accepted — pick whichever fits your client. You can only have one active token at a time, and the plaintext is only visible at creation; if you lose it, revoke and mint a fresh one in /settings.

Authorization: Bearer asc_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

— or —

x-api-key: asc_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

Keys are bound to your account, not to any one IP — use them from any host. Your plan tier is re-checked on every request, so a downgrade demotes API access immediately (even on previously-minted tokens). Revoke the token in /settings if it leaks.

Rate limit

250 requests / 24 h per Agency account.The window is a rolling 24 hours from your oldest in-window call.

When you exceed:

HTTP/1.1 429 Too Many Requests

{ "error": "API daily cap reached (250/day). Resets at 2026-05-14T...Z.",
  "code": "rate_limit",
  "used": 250,
  "cap": 250,
  "resetAt": "2026-05-14T..." }

Need more? Email support@acuityscan.com with your use case.

Endpoints

All endpoints return JSON. All POST bodies take a domain field. Base URL: https://acuityscan.com.

POST/api/v1/scan

Run a full Site+ Scan

Runs all 8 modules in parallel and returns the complete result. Synchronous — typical 30s, up to 5 min on heavy sites (the perf module uses real Lighthouse).

curl -X POST https://acuityscan.com/api/v1/scan \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
GET/api/v1/scan/latest?domain=example.com

Get your most recent saved scan

Returns the latest scan you've saved for this domain. Useful for daily-check jobs that want to avoid burning a fresh scan if recent data will do.

curl https://acuityscan.com/api/v1/scan/latest?domain=example.com \
  -H "Authorization: Bearer asc_live_xxx"
POST/api/v1/tools/email

Email deliverability check

SPF, DKIM, DMARC, MX, BIMI, MTA-STS, TLSRPT, PTR, 77 blacklists, Google/Yahoo bulk-sender compliance.

curl -X POST https://acuityscan.com/api/v1/tools/email \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/dns

DNS health check

A/AAAA/MX/TXT/NS/SOA/CAA/DS records, DNSSEC validation, TTL analysis, nameserver redundancy, propagation across 20 global resolvers.

curl -X POST https://acuityscan.com/api/v1/tools/dns \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/ssl

SSL/TLS + threat audit

Certificate chain + expiry, TLS protocol + cipher suites, Google Safe Browsing, security headers, HSTS preload, exposed files.

curl -X POST https://acuityscan.com/api/v1/tools/ssl \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/performance

Desktop + mobile performance

Real Google PageSpeed Insights (Lighthouse) for desktop AND mobile, Core Web Vitals, TTFB, compression, CDN detection, 60+ tech-stack detections.

curl -X POST https://acuityscan.com/api/v1/tools/performance \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/seo

Technical SEO

Title + meta description, heading hierarchy, canonical, OG, Twitter, robots.txt, sitemap.xml, schema.org, viewport, alt text, internal links.

curl -X POST https://acuityscan.com/api/v1/tools/seo \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/accessibility

WCAG 2.1 AA accessibility

Full axe-core audit at desktop 1280×800 and mobile 375×812, merged and deduped. Plus 38+ custom HTML checks. Boots a headless Chromium per call.

curl -X POST https://acuityscan.com/api/v1/tools/accessibility \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/privacy

Privacy + cookies

28+ tracker detection, cookie consent banner, pre-consent violations, privacy-policy + CCPA link presence, Consent Mode v2, mixed content.

curl -X POST https://acuityscan.com/api/v1/tools/privacy \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'
POST/api/v1/tools/mobile

Mobile + UX

Viewport meta, tap targets, font size, form input types, PWA features, intrusive interstitials, responsive images, horizontal overflow.

curl -X POST https://acuityscan.com/api/v1/tools/mobile \
  -H "Authorization: Bearer asc_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "domain": "example.com" }'

When the target site refuses our scanner

Many real-world sites are behind a WAF or bot manager (Cloudflare, Akamai, Imperva, DataDome, etc.) that challenges automated traffic with a JavaScript test before letting it through to the origin. Our scanner can't solve that challenge, so the modules that need to read the page's HTML can't complete.

The response still returns 200 OK. The top-level blocked object tells you which modules were affected and how bad the block was. overallScore is either a partial average (modules that ran) or null depending on severity.

severitywhenoverallScore
noneNo WAF block detectedFull weighted average
partial≤ 25% of weight blockedPartial average over modules that ran
major> 25% of weight blockednull
{
  "domain": "example.com",
  "overallScore": null,
  "moduleResults": { ... },
  "blocked": {
    "detected": true,
    "severity": "major",
    "vendor": "Cloudflare",
    "affectedModules": ["seo", "privacy", "mobile"],
    "affectedWeight": 0.30,
    "message": "Cloudflare blocked our scanner from reading..."
  }
}

Recommended client code: branch on result.blocked.severity. For major, don't treat overallScore as comparable to other scans (it's null). For partial, surface the message and treat the score as a partial audit. Individual moduleResults[id].blocked carries per-module vendor + reason if you need fine-grained detail.

Error codes

Every error response carries { error, code }. Thecode is the machine tag; branch on it.

StatusCodeMeaning
401missingNo Authorization or x-api-key header sent.
401invalid_formatToken doesn't start with asc_live_.
401unknownToken isn't in our database — likely typo'd or never existed.
401revokedToken was revoked in /settings.
403downgradedAccount is no longer on the Agency plan. Upgrade to re-enable.
400invalid_domainDomain shape rejected. Use "example.com", no protocol or path.
400unsafe_targetDomain resolved to a private/internal IP. SSRF guard refused the scan.
429rate_limitAccount hit 250 requests/day. Resets 24 h after the oldest in-window call.
500internalScanner crashed. Check status page; if persistent, contact support.

Use AcuityScan from your AI client

We ship an open-source Model Context Protocol server that wraps every endpoint above as an MCP tool. Drop it into Claude Desktop, Cursor, or Continue and ask in plain English: “run a full AcuityScan on stripe.com.”

Claude Desktop

Edit ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) or %APPDATA%\Claude\claude_desktop_config.json (Windows):

{
  "mcpServers": {
    "acuityscan": {
      "command": "npx",
      "args": ["-y", "@acuityscan/mcp"],
      "env": {
        "ACUITYSCAN_API_KEY": "asc_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
      }
    }
  }
}

Cursor, Continue, and other MCP clients use the same command / args / env shape. Full setup guides in the repo.

github.com/AcuityScan/mcp

Ready to ship?

Upgrade to Agency and the key UI unlocks. First scan takes one curl call.