For AI agents

Inkluso for AI agents

Most of this website is written for people. This page is for software that buys, compares or vets suppliers on someone else's behalf. It describes the five endpoints Inkluso opens to automated clients, exactly what they return, and how often you may call them.

What is open, and what is not

robots.txt disallows all of /api/ and then re-opens exactly five paths with Allow rules: the free scan, the accessibility-statement drafter, machine-readable offers, checkout and the order-status lookup. Nothing else under /api/ is meant for automated calls: the full scan and the report require operator credentials, and the remaining paths serve the website, payments and the customer account.

None of the five needs a key, a signup or a cookie. Requests and responses are JSON. The machine-readable version of this page is openapi.json (OpenAPI 3.1) and llms.txt. The machine-readable offer contract is available at /api/offers.json.

No language model writes the results

Findings come from axe-core, a deterministic rule engine, and the legal references from a fixed mapping table. Neither the report text nor the statement is generated by a language model. The same page therefore returns the same findings on two scans, and every violation carries "ai_generated": false.

The five endpoints

Free scan of a single page

POST https://inkluso.eu/api/scan/free

Free · 5 calls per hour per IP · homepage only

Checks the submitted address against WCAG 2.1 AA and maps the findings to the law selected by the lang field. The most severe violation comes back in full, with its legal reference; every other one appears in locked_violations as severity and instance count only.

  • A call takes roughly 30 seconds: the server launches a real browser and renders the page. Set a client timeout of at least 60 seconds.
  • The address must point at a public host. A missing scheme is completed to https://, and internal or loopback addresses are rejected with 422.
  • The scan_status field is the scan's own diagnosis. "bot_challenge" means the target site's WAF blocked the scanner, that is not a good grade, it is no grade at all.
  • Errors: 422 (invalid address, or nothing could be scanned), 429 (rate limit), 503 (scanner busy), 504 (scan exceeded the 300-second cap).
curl -sS -X POST https://inkluso.eu/api/scan/free \
     -H 'Content-Type: application/json' \
     --max-time 90 \
     -d '{"url": "https://example.cz", "lang": "en"}'

Accessibility statement draft

POST https://inkluso.eu/api/statement/draft

Free · 20 calls per minute per IP · nothing is stored

Assembles a draft accessibility statement from the details you send. No scan runs, nothing is stored, no email is sent and no account is created. The response has two fields: statement (a structured object) and text (the same document as plain text for a CMS).

  • conformance_status accepts only "partial", "none" or "not_assessed". "full" is deliberately not allowed: full conformance cannot be self-declared, only measured.
  • known_issues takes at most 20 items of at most 300 characters each; longer input is trimmed, not rejected.
  • The statement is the organisation's own declaration. Inkluso verifies none of the details, and the text says so explicitly.
  • Errors: 422 (invalid address, empty organisation name, disallowed conformance_status, malformed email), 429 (rate limit).
curl -sS -X POST https://inkluso.eu/api/statement/draft \
     -H 'Content-Type: application/json' \
     -d '{"organisation": "Vzor s.r.o.",
          "url": "https://example.cz",
          "lang": "en",
          "conformance_status": "partial",
          "known_issues": ["Two PDFs published before 2024 are not tagged."]}'

Order status

GET https://inkluso.eu/api/orders/{ref}

Free · 30 calls per hour per IP · every response carries X-Robots-Tag: noindex

Resolves an order reference to its fulfilment state, and once that finishes, to the report's address. The reference is minted when the order is created and is not the report token, that does not exist until fulfilment completes.

  • 404 {"detail": "Order not found"}: no such reference; stop asking.
  • 202 {"status": "pending"}: the order exists, fulfilment is still running.
  • 200 {"status": "fulfilled", "report_url": "/api/reports/{token}"}: done.
  • Fulfilment runs a scan of the whole site and renders a PDF, so count in minutes. At 30 calls per hour the practical ceiling is one poll every two minutes; one poll every five minutes is a safe pattern.
curl -sS -i https://inkluso.eu/api/orders/9f2c1d7a8b6e4f0c

HTTP/2 202
x-robots-tag: noindex

{"status": "pending"}

Buy an audit, or start monitoring

POST https://inkluso.eu/api/billing/checkout

Paid · 10 calls per minute per IP

Creates a Stripe Checkout session and returns its URL. Payment itself happens on Stripe, not here: no card details are ever sent to this endpoint. tier selects the product: scan_report is the one-time audit (from EUR 149 or the currency equivalent); monitor / monitor_annual is the recurring monitoring subscription; agency is contact-led (its price here is a floor anchor, not the marketed rate, use the sales-led flow instead); shoptet_audit is the one-time Shoptet e-shop audit (EUR 99 / 2 490 Kč / 449 zł; settlement currency follows lang).

  • consent must be true. This is a legal requirement, not a formality: the purchased tier is digital content/service delivered immediately, so the buyer must expressly waive the 14-day EU right of withdrawal. false or omitted returns 422 and no order is created. Do not send true on a human's behalf without their actual agreement.
  • The settlement currency follows lang: cs settles in CZK, pl in PLN, every other language (de, en) in EUR. This is not a converted figure, each currency has its own price list. The single source of truth is price_for_tier() in backend.billing.stripe.
  • An optional Idempotency-Key header: generate a fresh, unique value yourself for EVERY purchase intent (e.g. a UUID v4). The key is bound to your exact request (email, url, tier, lang): a repeat with the SAME request within 24 hours replays the SAME order_ref, checkout_url, amount and currency; the same key with DIFFERENT details returns 422. A key reused mid-flight returns 503, retry shortly. Never copy a key from documentation or from another request.
  • Errors: 422 (consent not true, invalid URL, or a missing/malformed field), 429 (rate limit), 503 (Idempotency-Key already in progress, or the payment provider is temporarily misconfigured), 500 (payment system unavailable).
curl -sS -X POST https://inkluso.eu/api/billing/checkout \
     -H 'Content-Type: application/json' \
     -H 'Idempotency-Key: ' \
     -d '{"email": "buyer@example.cz", "tier": "scan_report",
          "url": "https://example.cz", "lang": "en", "consent": true}'

Then poll GET /api/orders/{order_ref} above until it resolves to "fulfilled".

MCP server

The same four capabilities also exist as a native MCP server for Model Context Protocol clients (Claude, Cursor, and other agent runtimes), no HTTP glue needed:

Endpoint:  https://inkluso.eu/mcp        (Streamable HTTP, POST only, stateless)
Tools:     scan_accessibility, draft_accessibility_statement,
           start_audit_checkout, check_order_status
Auth:      none

Server card: /.well-known/mcp.json. Tool semantics mirror the HTTP endpoints exactly: same validation, same per-IP limits, same Idempotency-Key behaviour (passed as start_audit_checkout's idempotency_key argument), and the consent argument carries the same express-consent meaning described above. start_audit_checkout returns a Stripe-hosted URL the human pays on, the tool itself never takes payment. One difference from HTTP: the tools return report_url as an absolute URL, because an MCP caller has no origin to resolve a relative path against.

Agent skill (install): npx skills add maticijus/hexenkraft-agent-skills --skill inkluso-eaa-scan - https://skills.sh/maticijus/hexenkraft-agent-skills/inkluso-eaa-scan

Contact

Operator: HEXENKRAFT s.r.o., matic@hexenkraft.cz. Report a broken endpoint, a wrong legal mapping or a rate limit that blocks a legitimate integration to that address.