{
  "_sample": "SAMPLE: generated for illustration on 2026-10-30 from an offline FIXTURE site (fictional business, fictional DNS).",
  "schema": "site-report/1",
  "generated_at": "2026-10-30T06:38:14.486Z",
  "target": {
    "url": "https://acme-bakery.example/",
    "final_url": "https://acme-bakery.example/",
    "host": "acme-bakery.example",
    "domain": "acme-bakery.example"
  },
  "scope": {
    "areas": [
      "seo",
      "security_passive",
      "links",
      "email_auth",
      "ai_readiness"
    ],
    "max_pages": 10,
    "audience": "agency",
    "format": "all",
    "brand": {
      "name": "Acme Digital",
      "logo_url": "https://brand.example/logo.png",
      "logo_embedded": true
    }
  },
  "summary": {
    "areas": {
      "seo": {
        "health": "poor",
        "score": 38,
        "findings": 12,
        "critical": 0,
        "high": 1,
        "partial": true
      },
      "security_passive": {
        "health": "poor",
        "score": 48,
        "findings": 10,
        "critical": 0,
        "high": 2,
        "partial": false
      },
      "links": {
        "health": "good",
        "score": 88,
        "findings": 2,
        "critical": 0,
        "high": 0,
        "partial": false
      },
      "email_auth": {
        "health": "needs_work",
        "score": 78,
        "findings": 4,
        "critical": 0,
        "high": 1,
        "partial": false
      },
      "ai_readiness": {
        "health": "good",
        "score": 88,
        "findings": 3,
        "critical": 0,
        "high": 1,
        "partial": false
      }
    },
    "top_priorities": [
      {
        "finding_id": "F01",
        "title": "No /llms.txt.",
        "area": "ai_readiness",
        "severity": "high",
        "priority": "P1",
        "effort": "S"
      },
      {
        "finding_id": "F02",
        "title": "No DMARC record.",
        "area": "email_auth",
        "severity": "high",
        "priority": "P1",
        "effort": "S"
      },
      {
        "finding_id": "F03",
        "title": "Missing strict-transport-security.",
        "area": "security_passive",
        "severity": "high",
        "priority": "P1",
        "effort": "S"
      },
      {
        "finding_id": "F04",
        "title": "Plain HTTP does not redirect to HTTPS.",
        "area": "security_passive",
        "severity": "high",
        "priority": "P1",
        "effort": "S"
      },
      {
        "finding_id": "F05",
        "title": "No meta description (3 of 4 pages checked).",
        "area": "seo",
        "severity": "high",
        "priority": "P1",
        "effort": "S"
      }
    ],
    "counts": {
      "critical": 0,
      "high": 5,
      "medium": 13,
      "low": 11,
      "info": 2
    },
    "executive_summary": "We read 4 pages of acme-bakery.example and checked SEO, Security (passive), Links, Email authentication, AI readiness on 2026-10-30, using passive, read-only requests. We found 31 issues: 5 high, 13 medium, 11 low, 2 info. Start with: No /llms.txt; No DMARC record; Missing strict-transport-security. By area: SEO poor (38/100), Security (passive) poor (48/100), Links good (88/100), Email authentication needs work (78/100), AI readiness good (88/100). 1 check could not run or was skipped; they are listed under coverage and nothing was assumed for them. This is a point-in-time, passive assessment, not a penetration test."
  },
  "findings": [
    {
      "id": "F01",
      "area": "ai_readiness",
      "title": "No /llms.txt.",
      "severity": "high",
      "priority": "P1",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "AI assistants have no short summary of the site and its key pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/llms.txt",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "file",
          "detail": "No /llms.txt for AI assistants."
        },
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/llms.txt",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "file",
          "detail": "No /llms.txt.",
          "value": {
            "present": false,
            "links": 0
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Publish /llms.txt (llmstxt.org): an H1 with the site name, a one-paragraph summary and Markdown links to the key pages.",
        "where": "Files at the web root of the site.",
        "example": "https://acme-bakery.example/llms.txt:\n# Site name\n> One-paragraph summary of what the business offers.\n\n## Key pages\n- [Services](https://acme-bakery.example/services): what we do\n- [Contact](https://acme-bakery.example/contact): how to reach us"
      },
      "verify": "curl -s https://acme-bakery.example/llms.txt   (starts with \"# \")",
      "sources": [
        "seo-page",
        "agent-readiness"
      ],
      "owner_role": "developer",
      "check_key": "no_llms_txt"
    },
    {
      "id": "F02",
      "area": "email_auth",
      "title": "No DMARC record.",
      "severity": "high",
      "priority": "P1",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Anyone can send email that claims to be from this domain and receivers have no policy to reject it.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-scan-lite",
          "url": null,
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "dns",
          "detail": "No DMARC record.",
          "value": {
            "name": "_dmarc.acme-bakery.example",
            "record": null
          }
        },
        {
          "source": "email-auth",
          "url": null,
          "observed_at": "2026-10-30T06:38:14.427Z",
          "kind": "dns",
          "detail": "No DMARC record.",
          "value": {
            "name": "_dmarc.acme-bakery.example",
            "record": null
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Publish TXT _dmarc.acme-bakery.example: \"v=DMARC1; p=none; rua=mailto:dmarc@acme-bakery.example\" then move to quarantine/reject.",
        "where": "DNS zone of acme-bakery.example (at the DNS host).",
        "example": "_dmarc.acme-bakery.example.  TXT \"v=DMARC1; p=none; rua=mailto:dmarc@acme-bakery.example\"   (then p=quarantine, then p=reject)"
      },
      "verify": "dig TXT _dmarc.acme-bakery.example +short",
      "sources": [
        "security-scan-lite",
        "email-auth"
      ],
      "owner_role": "dns_admin",
      "check_key": "no_dmarc"
    },
    {
      "id": "F03",
      "area": "security_passive",
      "title": "Missing strict-transport-security.",
      "severity": "high",
      "priority": "P1",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "The first visit (or a typed http:// link) can be downgraded to plain HTTP by an attacker on the network.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ (HTTP 200) had no strict-transport-security header.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ had no strict-transport-security header.",
          "value": null
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Add Strict-Transport-Security: max-age=31536000; includeSubDomains",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "Strict-Transport-Security: max-age=31536000; includeSubDomains"
      },
      "verify": "curl -sI https://acme-bakery.example/ | grep -i strict-transport-security",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "hsts_missing"
    },
    {
      "id": "F04",
      "area": "security_passive",
      "title": "Plain HTTP does not redirect to HTTPS.",
      "severity": "high",
      "priority": "P1",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "http://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "http",
          "detail": "Plain HTTP does not redirect to HTTPS.",
          "value": "no redirect (HTTP 200)"
        },
        {
          "source": "security-scan-lite",
          "url": "http://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "http",
          "detail": "Plain HTTP does not redirect to HTTPS.",
          "value": "no redirect (HTTP 200)"
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Send a 301 from http:// to https:// for every path.",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "http://acme-bakery.example/* -> 301 -> https://acme-bakery.example/*"
      },
      "verify": "curl -sI http://acme-bakery.example/   (expect 301 and Location: https://...)",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "no_http_redirect"
    },
    {
      "id": "F05",
      "area": "seo",
      "title": "No meta description (3 of 4 pages checked).",
      "severity": "high",
      "priority": "P1",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Search engines and AI tools write their own snippet; click-through usually drops.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "No meta description.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/about",
          "observed_at": "2026-10-30T06:38:14.415Z",
          "kind": "html",
          "detail": "No meta description.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/contact",
          "observed_at": "2026-10-30T06:38:14.422Z",
          "kind": "html",
          "detail": "No meta description.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "html",
          "detail": "No meta description."
        }
      ],
      "pages": [
        "https://acme-bakery.example/",
        "https://acme-bakery.example/about",
        "https://acme-bakery.example/contact"
      ],
      "fix": {
        "summary": "Add a 70-160 character meta description that summarises the page.",
        "where": "Page templates / CMS page settings.",
        "example": "<meta name=\"description\" content=\"One or two sentences (70-160 characters) that say what this page offers and for whom.\">"
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page",
        "agent-readiness"
      ],
      "owner_role": "content",
      "check_key": "missing_meta_description"
    },
    {
      "id": "F06",
      "area": "security_passive",
      "title": "No X-Frame-Options or CSP frame-ancestors (clickjacking).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Other sites can frame these pages and trick visitors into clicks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "No X-Frame-Options header and no frame-ancestors directive in the response from https://acme-bakery.example/.",
          "value": {
            "x-frame-options": null,
            "content-security-policy": null
          }
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "No X-Frame-Options header and no frame-ancestors directive in the response from https://acme-bakery.example/.",
          "value": {
            "x-frame-options": null,
            "content-security-policy": null
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Add X-Frame-Options: SAMEORIGIN or CSP frame-ancestors 'self'.",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "Content-Security-Policy: frame-ancestors 'self'   (or X-Frame-Options: SAMEORIGIN)"
      },
      "verify": "curl -sI https://acme-bakery.example/ | grep -iE \"x-frame-options|frame-ancestors\"",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "clickjacking"
    },
    {
      "id": "F07",
      "area": "security_passive",
      "title": "Missing x-content-type-options.",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ (HTTP 200) had no x-content-type-options header.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ had no x-content-type-options header.",
          "value": null
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Add X-Content-Type-Options: nosniff",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "X-Content-Type-Options: nosniff"
      },
      "verify": "curl -sI https://acme-bakery.example/ | grep -i x-content-type-options",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "xcto_missing"
    },
    {
      "id": "F08",
      "area": "seo",
      "title": "1 JSON-LD block(s) do not parse as JSON.",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "structured-data",
          "url": "https://acme-bakery.example/contact",
          "observed_at": "2026-10-30T06:38:14.422Z",
          "kind": "html",
          "detail": "JSON-LD parse errors.",
          "value": [
            "Expected double-quoted property name in JSON at position 78 (line 1 column 79)"
          ]
        }
      ],
      "pages": [
        "https://acme-bakery.example/contact"
      ],
      "fix": {
        "summary": "Fix the JSON syntax of the ld+json block (validate with validator.schema.org).",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the structured-data check) after the change and confirm this finding is gone.",
      "sources": [
        "structured-data"
      ],
      "owner_role": "developer",
      "check_key": "invalid_json_ld"
    },
    {
      "id": "F09",
      "area": "seo",
      "title": "No canonical link (3 of 4 pages checked).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "No canonical link.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/about",
          "observed_at": "2026-10-30T06:38:14.415Z",
          "kind": "html",
          "detail": "No canonical link.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/contact",
          "observed_at": "2026-10-30T06:38:14.422Z",
          "kind": "html",
          "detail": "No canonical link.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "html",
          "detail": "No canonical link."
        }
      ],
      "pages": [
        "https://acme-bakery.example/",
        "https://acme-bakery.example/about",
        "https://acme-bakery.example/contact"
      ],
      "fix": {
        "summary": "Add <link rel=\"canonical\"> pointing to the preferred URL.",
        "where": "Page templates / CMS page settings.",
        "example": "<link rel=\"canonical\" href=\"https://acme-bakery.example/this-page/\">"
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page",
        "agent-readiness"
      ],
      "owner_role": "developer",
      "check_key": "missing_canonical"
    },
    {
      "id": "F10",
      "area": "seo",
      "title": "Page titles are too short or too long (2 of 4 pages checked).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "Title is 11 characters.",
          "value": "Acme Bakery",
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/about",
          "observed_at": "2026-10-30T06:38:14.415Z",
          "kind": "html",
          "detail": "Title is 77 characters.",
          "value": "About Acme Bakery - family bakers since 1987 in George Town, Penang, Malaysia",
          "status_code": 200
        }
      ],
      "pages": [
        "https://acme-bakery.example/",
        "https://acme-bakery.example/about"
      ],
      "fix": {
        "summary": "Aim for roughly 30-60 characters with the main topic first.",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page"
      ],
      "owner_role": "content",
      "check_key": "title_length"
    },
    {
      "id": "F11",
      "area": "email_auth",
      "title": "No DKIM key found at 30 common selectors (it may use a custom selector).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Affects whether others can send email that looks like it comes from this domain, and whether real mail is delivered.",
      "basis": "inferred",
      "basis_note": "Only 30 common DKIM selectors were queried; a custom selector would not be seen, so DKIM may exist.",
      "evidence": [
        {
          "source": "security-scan-lite",
          "url": null,
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "dns",
          "detail": "No DKIM key found at 30 common selectors (it may use a custom selector).",
          "value": {
            "name": "<selector>._domainkey.acme-bakery.example",
            "selectors_checked": 30,
            "selectors_found": []
          }
        },
        {
          "source": "email-auth",
          "url": null,
          "observed_at": "2026-10-30T06:38:14.427Z",
          "kind": "dns",
          "detail": "No DKIM key found at 30 common selectors (it may use a custom selector).",
          "value": {
            "name": "<selector>._domainkey.acme-bakery.example",
            "selectors_checked": 30,
            "selectors_found": []
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Enable DKIM signing at your mail provider and publish its key.",
        "where": "DNS zone of acme-bakery.example (at the DNS host)."
      },
      "verify": "dig TXT <selector>._domainkey.acme-bakery.example +short   (selector from your mail provider)",
      "sources": [
        "security-scan-lite",
        "email-auth"
      ],
      "owner_role": "dns_admin",
      "check_key": "dkim_not_found"
    },
    {
      "id": "F12",
      "area": "links",
      "title": "2 of 8 links checked on the home page are broken.",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Visitors and crawlers hit dead ends; link value is wasted.",
      "basis": "observed",
      "evidence": [
        {
          "source": "broken-links",
          "url": "https://acme-bakery.example/old-page",
          "observed_at": "2026-10-30T06:38:14.462Z",
          "kind": "http_status",
          "detail": "Linked from https://acme-bakery.example/; answered HTTP 404.",
          "status_code": 404
        },
        {
          "source": "broken-links",
          "url": "https://dead-supplier.example/catalog",
          "observed_at": "2026-10-30T06:38:14.462Z",
          "kind": "http_status",
          "detail": "Linked from https://acme-bakery.example/; failed (dns_not_found)."
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Fix each target or 301-redirect it, and update the links.",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the broken-links check) after the change and confirm this finding is gone.",
      "sources": [
        "broken-links"
      ],
      "owner_role": "content",
      "check_key": "broken_links"
    },
    {
      "id": "F13",
      "area": "links",
      "title": "A page linked from the home page answers HTTP 404.",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Visitors and crawlers hit dead ends; link value is wasted.",
      "basis": "observed",
      "evidence": [
        {
          "source": "page-fetch",
          "url": "https://acme-bakery.example/old-page",
          "observed_at": "2026-10-30T06:38:14.465Z",
          "kind": "http_status",
          "detail": "https://acme-bakery.example/old-page answered HTTP 404.",
          "status_code": 404
        }
      ],
      "pages": [
        "https://acme-bakery.example/old-page"
      ],
      "fix": {
        "summary": "Fix the page or 301-redirect it, and update the links that point to it.",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the page-fetch check) after the change and confirm this finding is gone.",
      "sources": [
        "page-fetch"
      ],
      "owner_role": "content",
      "check_key": "crawled_page_error"
    },
    {
      "id": "F14",
      "area": "seo",
      "title": "No XML sitemap found (robots.txt or /sitemap.xml).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "New and deep pages are discovered more slowly.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/sitemap.xml",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "file",
          "detail": "No XML sitemap found (robots.txt or /sitemap.xml)."
        },
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "file",
          "detail": "No XML sitemap found (robots.txt Sitemap: line or /sitemap.xml).",
          "value": {
            "found": false,
            "url": null,
            "urls": null,
            "in_robots_txt": false
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Publish /sitemap.xml and reference it in robots.txt.",
        "where": "Page templates / CMS page settings.",
        "example": "https://acme-bakery.example/sitemap.xml  +  robots.txt line: Sitemap: https://acme-bakery.example/sitemap.xml"
      },
      "verify": "curl -sI https://acme-bakery.example/sitemap.xml   (200, XML)",
      "sources": [
        "seo-page",
        "agent-readiness"
      ],
      "owner_role": "developer",
      "check_key": "no_sitemap"
    },
    {
      "id": "F15",
      "area": "seo",
      "title": "No JSON-LD structured data (2 of 4 pages checked).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "No eligibility for rich results; machines get less certain facts about the business.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/about",
          "observed_at": "2026-10-30T06:38:14.415Z",
          "kind": "html",
          "detail": "No JSON-LD structured data.",
          "value": [],
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/menu",
          "observed_at": "2026-10-30T06:38:14.421Z",
          "kind": "html",
          "detail": "No JSON-LD structured data.",
          "value": [],
          "status_code": 200
        }
      ],
      "pages": [
        "https://acme-bakery.example/about",
        "https://acme-bakery.example/menu"
      ],
      "fix": {
        "summary": "Add schema.org JSON-LD (Organization/LocalBusiness/Article/Product as fits).",
        "where": "Page templates / CMS page settings.",
        "example": "<script type=\"application/ld+json\">{\"@context\":\"https://schema.org\",\"@type\":\"Organization\",\"name\":\"...\",\"url\":\"https://acme-bakery.example/\",\"logo\":\"https://acme-bakery.example/logo.png\"}</script>"
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page"
      ],
      "owner_role": "developer",
      "check_key": "no_structured_data"
    },
    {
      "id": "F16",
      "area": "seo",
      "title": "JSON-LD missing required properties: LocalBusiness (address).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "structured-data",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "JSON-LD items with missing required properties.",
          "value": [
            {
              "type": [
                "LocalBusiness"
              ],
              "missing_required": [
                "address"
              ]
            }
          ]
        }
      ],
      "pages": [
        "https://acme-bakery.example/"
      ],
      "fix": {
        "summary": "Add the required properties so the markup is eligible for rich results (validate with validator.schema.org or Google's Rich Results Test).",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the structured-data check) after the change and confirm this finding is gone.",
      "sources": [
        "structured-data"
      ],
      "owner_role": "developer",
      "check_key": "structured_data_missing_required"
    },
    {
      "id": "F17",
      "area": "security_passive",
      "title": "Missing content-security-policy.",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "L",
        "hours": "1-3 days"
      },
      "impact": "No browser-enforced limit on which scripts may run if an injection bug exists.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ (HTTP 200) had no content-security-policy header.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ had no content-security-policy header.",
          "value": null
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Add a Content-Security-Policy (start with default-src 'self' and loosen as needed; report-only first).",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "Content-Security-Policy-Report-Only: default-src 'self'; img-src 'self' data: https:; script-src 'self'; style-src 'self' 'unsafe-inline'; frame-ancestors 'self'\n(start in Report-Only, then switch to Content-Security-Policy)"
      },
      "verify": "curl -sI https://acme-bakery.example/ | grep -i content-security-policy",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "csp_missing"
    },
    {
      "id": "F18",
      "area": "seo",
      "title": "Thin content: few words of visible text (2 of 4 pages checked).",
      "severity": "medium",
      "priority": "P3",
      "effort": {
        "size": "L",
        "hours": "1-3 days"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "Only about 120 words of visible text.",
          "value": 120,
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/contact",
          "observed_at": "2026-10-30T06:38:14.422Z",
          "kind": "html",
          "detail": "Only about 90 words of visible text.",
          "value": 90,
          "status_code": 200
        },
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "measurement",
          "detail": "Only about 120 words of text on the page.",
          "value": {
            "word_count": 120,
            "markdown_chars": 671,
            "scripts": 1
          }
        }
      ],
      "pages": [
        "https://acme-bakery.example/",
        "https://acme-bakery.example/contact"
      ],
      "fix": {
        "summary": "Add useful content that answers the visitor's question.",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page",
        "agent-readiness"
      ],
      "owner_role": "content",
      "check_key": "thin_content"
    },
    {
      "id": "F19",
      "area": "email_auth",
      "title": "No TLS-RPT.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects whether others can send email that looks like it comes from this domain, and whether real mail is delivered.",
      "basis": "observed",
      "evidence": [
        {
          "source": "email-auth",
          "url": null,
          "observed_at": "2026-10-30T06:38:14.427Z",
          "kind": "dns",
          "detail": "No TLS-RPT.",
          "value": {
            "name": "acme-bakery.example"
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Optional: publish _smtp._tls TXT \"v=TLSRPTv1; rua=mailto:...\"",
        "where": "DNS zone of acme-bakery.example (at the DNS host).",
        "example": "_smtp._tls.acme-bakery.example.  TXT \"v=TLSRPTv1; rua=mailto:tls-reports@acme-bakery.example\""
      },
      "verify": "dig TXT _smtp._tls.acme-bakery.example +short",
      "sources": [
        "email-auth"
      ],
      "owner_role": "dns_admin",
      "check_key": "no_tls_rpt"
    },
    {
      "id": "F20",
      "area": "security_passive",
      "title": "Cookie PHPSESSID is missing Secure, HttpOnly, SameSite.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "Cookie PHPSESSID is missing Secure, HttpOnly, SameSite.",
          "value": [
            {
              "name": "PHPSESSID",
              "secure": false,
              "httponly": false,
              "samesite": null
            }
          ]
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Set Secure; HttpOnly (unless JS needs it); SameSite=Lax on cookies.",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "Set-Cookie: session=...; Secure; HttpOnly; SameSite=Lax"
      },
      "verify": "Re-run this report (or the security-headers check) after the change and confirm this finding is gone.",
      "sources": [
        "security-headers"
      ],
      "owner_role": "developer",
      "check_key": "cookie_flags"
    },
    {
      "id": "F21",
      "area": "security_passive",
      "title": "Missing permissions-policy.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ (HTTP 200) had no permissions-policy header.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ had no permissions-policy header.",
          "value": null
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Add a Permissions-Policy that disables unused features (camera=(), microphone=(), geolocation=()).",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "Permissions-Policy: camera=(), microphone=(), geolocation=()"
      },
      "verify": "curl -sI https://acme-bakery.example/ | grep -i permissions-policy",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "permissions_policy_missing"
    },
    {
      "id": "F22",
      "area": "security_passive",
      "title": "Missing referrer-policy.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ (HTTP 200) had no referrer-policy header.",
          "value": null,
          "status_code": 200
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "The response from https://acme-bakery.example/ had no referrer-policy header.",
          "value": null
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Add Referrer-Policy: strict-origin-when-cross-origin",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "Referrer-Policy: strict-origin-when-cross-origin"
      },
      "verify": "curl -sI https://acme-bakery.example/ | grep -i referrer-policy",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "referrer_policy_missing"
    },
    {
      "id": "F23",
      "area": "security_passive",
      "title": "server discloses a version (Apache/2.4.41 (Ubuntu)).",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "server discloses a version (Apache/2.4.41 (Ubuntu)).",
          "value": "Apache/2.4.41 (Ubuntu)"
        },
        {
          "source": "security-scan-lite",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "server discloses a version (Apache/2.4.41 (Ubuntu)).",
          "value": "Apache/2.4.41 (Ubuntu)"
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Remove the version from the server header.",
        "where": "Response headers: Apache config or .htaccess (Header always set ...)."
      },
      "verify": "Re-run this report (or the security-headers check) after the change and confirm this finding is gone.",
      "sources": [
        "security-headers",
        "security-scan-lite"
      ],
      "owner_role": "developer",
      "check_key": "version_disclosure_server"
    },
    {
      "id": "F24",
      "area": "security_passive",
      "title": "x-powered-by discloses a version (PHP/7.4.3).",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how well visitors and their browsers are protected against common web attacks.",
      "basis": "observed",
      "evidence": [
        {
          "source": "security-headers",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.449Z",
          "kind": "header",
          "detail": "x-powered-by discloses a version (PHP/7.4.3).",
          "value": "PHP/7.4.3"
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Remove the version from the x-powered-by header.",
        "where": "Response headers: Apache config or .htaccess (Header always set ...)."
      },
      "verify": "Re-run this report (or the security-headers check) after the change and confirm this finding is gone.",
      "sources": [
        "security-headers"
      ],
      "owner_role": "developer",
      "check_key": "version_disclosure_x-powered-by"
    },
    {
      "id": "F25",
      "area": "seo",
      "title": "Meta description is 47 characters.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/menu",
          "observed_at": "2026-10-30T06:38:14.421Z",
          "kind": "html",
          "detail": "Meta description is 47 characters.",
          "value": "Breads, cakes and pastries baked every morning.",
          "status_code": 200
        }
      ],
      "pages": [
        "https://acme-bakery.example/menu"
      ],
      "fix": {
        "summary": "Aim for roughly 70-160 characters.",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page"
      ],
      "owner_role": "content",
      "check_key": "meta_description_length"
    },
    {
      "id": "F26",
      "area": "seo",
      "title": "HTML is not compressed (4 of 4 pages checked).",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "header",
          "detail": "The HTML of https://acme-bakery.example/ was sent without Content-Encoding (gzip/br).",
          "value": null
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/about",
          "observed_at": "2026-10-30T06:38:14.415Z",
          "kind": "header",
          "detail": "The HTML of https://acme-bakery.example/about was sent without Content-Encoding (gzip/br).",
          "value": null
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/menu",
          "observed_at": "2026-10-30T06:38:14.421Z",
          "kind": "header",
          "detail": "The HTML of https://acme-bakery.example/menu was sent without Content-Encoding (gzip/br).",
          "value": null
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/contact",
          "observed_at": "2026-10-30T06:38:14.422Z",
          "kind": "header",
          "detail": "The HTML of https://acme-bakery.example/contact was sent without Content-Encoding (gzip/br).",
          "value": null
        }
      ],
      "pages": [
        "https://acme-bakery.example/",
        "https://acme-bakery.example/about",
        "https://acme-bakery.example/menu",
        "https://acme-bakery.example/contact"
      ],
      "fix": {
        "summary": "Enable gzip or brotli.",
        "where": "Response headers: Apache config or .htaccess (Header always set ...).",
        "example": "nginx: gzip on; (or brotli)  /  Apache: AddOutputFilterByType DEFLATE text/html"
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page"
      ],
      "owner_role": "developer",
      "check_key": "no_compression"
    },
    {
      "id": "F27",
      "area": "seo",
      "title": "No Open Graph tags (4 of 4 pages checked).",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "No Open Graph tags.",
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/about",
          "observed_at": "2026-10-30T06:38:14.415Z",
          "kind": "html",
          "detail": "No Open Graph tags.",
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/menu",
          "observed_at": "2026-10-30T06:38:14.421Z",
          "kind": "html",
          "detail": "No Open Graph tags.",
          "status_code": 200
        },
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/contact",
          "observed_at": "2026-10-30T06:38:14.422Z",
          "kind": "html",
          "detail": "No Open Graph tags.",
          "status_code": 200
        },
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "html",
          "detail": "Open Graph is missing (title, description, image missing)."
        }
      ],
      "pages": [
        "https://acme-bakery.example/",
        "https://acme-bakery.example/about",
        "https://acme-bakery.example/menu",
        "https://acme-bakery.example/contact"
      ],
      "fix": {
        "summary": "Add og:title, og:description, og:image for link previews.",
        "where": "Page templates / CMS page settings.",
        "example": "<meta property=\"og:title\" content=\"...\"><meta property=\"og:description\" content=\"...\"><meta property=\"og:image\" content=\"https://acme-bakery.example/og.png\">"
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page",
        "agent-readiness"
      ],
      "owner_role": "content",
      "check_key": "open_graph_incomplete"
    },
    {
      "id": "F28",
      "area": "email_auth",
      "title": "No MTA-STS.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Affects whether others can send email that looks like it comes from this domain, and whether real mail is delivered.",
      "basis": "observed",
      "evidence": [
        {
          "source": "email-auth",
          "url": null,
          "observed_at": "2026-10-30T06:38:14.427Z",
          "kind": "dns",
          "detail": "No MTA-STS.",
          "value": {
            "name": "acme-bakery.example"
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Optional hardening: publish MTA-STS to enforce TLS for inbound mail.",
        "where": "DNS zone of acme-bakery.example (at the DNS host)."
      },
      "verify": "dig TXT _mta-sts.acme-bakery.example +short",
      "sources": [
        "email-auth"
      ],
      "owner_role": "dns_admin",
      "check_key": "no_mta_sts"
    },
    {
      "id": "F29",
      "area": "seo",
      "title": "2 of 2 images have no alt attribute.",
      "severity": "low",
      "priority": "P4",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Affects how search engines crawl, understand and show these pages.",
      "basis": "observed",
      "evidence": [
        {
          "source": "seo-page",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.413Z",
          "kind": "html",
          "detail": "2 of 2 images have no alt attribute.",
          "status_code": 200
        }
      ],
      "pages": [
        "https://acme-bakery.example/"
      ],
      "fix": {
        "summary": "Add short descriptive alt text (empty alt=\"\" only for decorative images).",
        "where": "Page templates / CMS page settings.",
        "example": "<img src=\"team.jpg\" alt=\"Our team at the Penang office\">   (alt=\"\" only for decorative images)"
      },
      "verify": "Re-run this report (or the seo-page check) after the change and confirm this finding is gone.",
      "sources": [
        "seo-page"
      ],
      "owner_role": "content",
      "check_key": "images_missing_alt"
    },
    {
      "id": "F30",
      "area": "ai_readiness",
      "title": "robots.txt blocks AI training crawlers: GPTBot.",
      "severity": "info",
      "priority": "P4",
      "effort": {
        "size": "S",
        "hours": "0.5-2 h"
      },
      "impact": "Affects whether AI assistants and answer engines can read, understand and cite the site.",
      "basis": "observed",
      "evidence": [
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/robots.txt",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "robots",
          "detail": "robots.txt blocks AI training crawlers: GPTBot.",
          "value": {
            "GPTBot": false,
            "ClaudeBot": true,
            "Google-Extended": true,
            "Applebot-Extended": true,
            "CCBot": true,
            "Meta-ExternalAgent": true,
            "Bytespider": true,
            "Amazonbot": true
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Fine if intended: this only opts out of model training, not AI search answers.",
        "where": "Page templates / CMS page settings."
      },
      "verify": "Re-run this report (or the agent-readiness check) after the change and confirm this finding is gone.",
      "sources": [
        "agent-readiness"
      ],
      "owner_role": "developer",
      "check_key": "ai_training_bots_blocked"
    },
    {
      "id": "F31",
      "area": "ai_readiness",
      "title": "No agent discovery files (/.well-known/x402, /.well-known/mcp.json, /.well-known/agent-card.json, /openapi.json).",
      "severity": "info",
      "priority": "P4",
      "effort": {
        "size": "M",
        "hours": "2-8 h"
      },
      "impact": "Affects whether AI assistants and answer engines can read, understand and cite the site.",
      "basis": "observed",
      "evidence": [
        {
          "source": "agent-readiness",
          "url": "https://acme-bakery.example/",
          "observed_at": "2026-10-30T06:38:14.460Z",
          "kind": "file",
          "detail": "No agent discovery files (/.well-known/x402, /.well-known/mcp.json, /.well-known/agent-card.json, /openapi.json).",
          "value": {
            "x402": false,
            "mcp": false,
            "agent_card": false,
            "openapi": false
          }
        }
      ],
      "pages": [],
      "fix": {
        "summary": "Only needed if you offer an API or agent service: publish the matching discovery file so agents can find and pay for it.",
        "where": "Files at the web root of the site."
      },
      "verify": "Re-run this report (or the agent-readiness check) after the change and confirm this finding is gone.",
      "sources": [
        "agent-readiness"
      ],
      "owner_role": "developer",
      "check_key": "no_agent_discovery"
    }
  ],
  "implementation_plan": {
    "phases": [
      {
        "id": "this_week",
        "title": "Quick wins (this week)",
        "items": [
          {
            "finding_id": "F01",
            "title": "No /llms.txt.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F02",
            "title": "No DMARC record.",
            "owner_role": "dns_admin",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F03",
            "title": "Missing strict-transport-security.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": [
              "F04"
            ]
          },
          {
            "finding_id": "F04",
            "title": "Plain HTTP does not redirect to HTTPS.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F05",
            "title": "No meta description (3 of 4 pages checked).",
            "owner_role": "content",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F06",
            "title": "No X-Frame-Options or CSP frame-ancestors (clickjacking).",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F07",
            "title": "Missing x-content-type-options.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          }
        ]
      },
      {
        "id": "next_30_days",
        "title": "Next 30 days",
        "items": [
          {
            "finding_id": "F08",
            "title": "1 JSON-LD block(s) do not parse as JSON.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F09",
            "title": "No canonical link (3 of 4 pages checked).",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F10",
            "title": "Page titles are too short or too long (2 of 4 pages checked).",
            "owner_role": "content",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F11",
            "title": "No DKIM key found at 30 common selectors (it may use a custom selector).",
            "owner_role": "dns_admin",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          },
          {
            "finding_id": "F12",
            "title": "2 of 8 links checked on the home page are broken.",
            "owner_role": "content",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          },
          {
            "finding_id": "F13",
            "title": "A page linked from the home page answers HTTP 404.",
            "owner_role": "content",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          },
          {
            "finding_id": "F14",
            "title": "No XML sitemap found (robots.txt or /sitemap.xml).",
            "owner_role": "developer",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          },
          {
            "finding_id": "F15",
            "title": "No JSON-LD structured data (2 of 4 pages checked).",
            "owner_role": "developer",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          },
          {
            "finding_id": "F16",
            "title": "JSON-LD missing required properties: LocalBusiness (address).",
            "owner_role": "developer",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          }
        ]
      },
      {
        "id": "later",
        "title": "Later",
        "items": [
          {
            "finding_id": "F17",
            "title": "Missing content-security-policy.",
            "owner_role": "developer",
            "effort": "L",
            "hours": "1-3 days",
            "depends_on": []
          },
          {
            "finding_id": "F18",
            "title": "Thin content: few words of visible text (2 of 4 pages checked).",
            "owner_role": "content",
            "effort": "L",
            "hours": "1-3 days",
            "depends_on": []
          },
          {
            "finding_id": "F19",
            "title": "No TLS-RPT.",
            "owner_role": "dns_admin",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": [
              "F28"
            ]
          },
          {
            "finding_id": "F20",
            "title": "Cookie PHPSESSID is missing Secure, HttpOnly, SameSite.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F21",
            "title": "Missing permissions-policy.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F22",
            "title": "Missing referrer-policy.",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F23",
            "title": "server discloses a version (Apache/2.4.41 (Ubuntu)).",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F24",
            "title": "x-powered-by discloses a version (PHP/7.4.3).",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F25",
            "title": "Meta description is 47 characters.",
            "owner_role": "content",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F26",
            "title": "HTML is not compressed (4 of 4 pages checked).",
            "owner_role": "developer",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F27",
            "title": "No Open Graph tags (4 of 4 pages checked).",
            "owner_role": "content",
            "effort": "S",
            "hours": "0.5-2 h",
            "depends_on": []
          },
          {
            "finding_id": "F28",
            "title": "No MTA-STS.",
            "owner_role": "dns_admin",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          },
          {
            "finding_id": "F29",
            "title": "2 of 2 images have no alt attribute.",
            "owner_role": "content",
            "effort": "M",
            "hours": "2-8 h",
            "depends_on": []
          }
        ]
      }
    ],
    "roles": {
      "developer": "web developer / hosting",
      "content": "content editor",
      "dns_admin": "whoever manages the DNS zone"
    },
    "note": "Order within a phase: priority, then effort. \"depends_on\" lists findings to fix first."
  },
  "needs_human_review": [
    {
      "topic": "Links not checked (robots.txt)",
      "why": "1 link(s) on the home page were not requested because robots.txt disallows them for our crawler.",
      "area": "links"
    },
    {
      "topic": "No DKIM key found at 30 common selectors (it may use a custom selector).",
      "why": "Inferred, not directly measured: Only 30 common DKIM selectors were queried; a custom selector would not be seen, so DKIM may exist.",
      "finding_id": "F11",
      "area": "email_auth"
    },
    {
      "topic": "robots.txt blocks AI training crawlers: GPTBot.",
      "why": "Blocking AI training crawlers is a legitimate business choice; confirm the policy with the site owner before changing it.",
      "finding_id": "F30",
      "area": "ai_readiness"
    },
    {
      "topic": "Page not crawled: https://acme-bakery.example/private/admin",
      "why": "robots.txt disallows it for our crawler (not requested). If it should be assessed, allow the audit crawler for it in robots.txt, or check it by hand.",
      "area": "seo",
      "url": "https://acme-bakery.example/private/admin"
    },
    {
      "topic": "Check failed: page-fetch (https://acme-bakery.example/old-page)",
      "why": "target_http_error: https://acme-bakery.example/old-page answered HTTP 404.. Nothing was assumed for it.",
      "area": "seo"
    }
  ],
  "coverage": {
    "pages": {
      "max_pages": 10,
      "discovered_from": "internal links on the home page (same host, robots.txt checked before any request)",
      "crawled": [
        {
          "url": "https://acme-bakery.example/",
          "status": 200,
          "response_ms": 2
        },
        {
          "url": "https://acme-bakery.example/about",
          "status": 200,
          "response_ms": 3
        },
        {
          "url": "https://acme-bakery.example/menu",
          "status": 200,
          "response_ms": 2
        },
        {
          "url": "https://acme-bakery.example/contact",
          "status": 200,
          "response_ms": 1
        }
      ],
      "blocked_by_robots": [
        {
          "url": "https://acme-bakery.example/private/admin",
          "reason": "robots.txt disallows it for our crawler (not requested)"
        }
      ],
      "failed": [
        {
          "url": "https://acme-bakery.example/old-page",
          "reason": "target_http_error"
        }
      ],
      "not_crawled_over_limit": 0
    },
    "checks": [
      {
        "id": "canonical:0",
        "tool": "canonical-check",
        "area": "seo",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 1
      },
      {
        "id": "canonical:1",
        "tool": "canonical-check",
        "area": "seo",
        "target": "https://acme-bakery.example/about",
        "status": "ok",
        "ms": 0
      },
      {
        "id": "canonical:2",
        "tool": "canonical-check",
        "area": "seo",
        "target": "https://acme-bakery.example/menu",
        "status": "ok",
        "ms": 1
      },
      {
        "id": "canonical:3",
        "tool": "canonical-check",
        "area": "seo",
        "target": "https://acme-bakery.example/contact",
        "status": "ok",
        "ms": 0
      },
      {
        "id": "home",
        "tool": "page-fetch",
        "area": "seo",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 22
      },
      {
        "id": "page:1",
        "tool": "page-fetch",
        "area": "seo",
        "target": "https://acme-bakery.example/about",
        "status": "ok",
        "ms": 5
      },
      {
        "id": "page:2",
        "tool": "page-fetch",
        "area": "seo",
        "target": "https://acme-bakery.example/menu",
        "status": "ok",
        "ms": 3
      },
      {
        "id": "page:3",
        "tool": "page-fetch",
        "area": "seo",
        "target": "https://acme-bakery.example/contact",
        "status": "ok",
        "ms": 3
      },
      {
        "id": "page:4",
        "tool": "page-fetch",
        "area": "seo",
        "target": "https://acme-bakery.example/old-page",
        "status": "failed",
        "ms": 2,
        "reason": "target_http_error",
        "message": "https://acme-bakery.example/old-page answered HTTP 404."
      },
      {
        "id": "seo-page:0",
        "tool": "seo-page",
        "area": "seo",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 10
      },
      {
        "id": "seo-page:1",
        "tool": "seo-page",
        "area": "seo",
        "target": "https://acme-bakery.example/about",
        "status": "ok",
        "ms": 9
      },
      {
        "id": "seo-page:2",
        "tool": "seo-page",
        "area": "seo",
        "target": "https://acme-bakery.example/menu",
        "status": "ok",
        "ms": 4
      },
      {
        "id": "seo-page:3",
        "tool": "seo-page",
        "area": "seo",
        "target": "https://acme-bakery.example/contact",
        "status": "ok",
        "ms": 4
      },
      {
        "id": "structured:0",
        "tool": "structured-data",
        "area": "seo",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 1
      },
      {
        "id": "structured:1",
        "tool": "structured-data",
        "area": "seo",
        "target": "https://acme-bakery.example/about",
        "status": "ok",
        "ms": 0
      },
      {
        "id": "structured:2",
        "tool": "structured-data",
        "area": "seo",
        "target": "https://acme-bakery.example/menu",
        "status": "ok",
        "ms": 0
      },
      {
        "id": "structured:3",
        "tool": "structured-data",
        "area": "seo",
        "target": "https://acme-bakery.example/contact",
        "status": "ok",
        "ms": 0
      },
      {
        "id": "security-headers",
        "tool": "security-headers",
        "area": "security_passive",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 26
      },
      {
        "id": "security-scan-lite",
        "tool": "security-scan-lite",
        "area": "security_passive",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 26
      },
      {
        "id": "broken-links",
        "tool": "broken-links",
        "area": "links",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 39
      },
      {
        "id": "email-auth",
        "tool": "email-auth",
        "area": "email_auth",
        "target": "acme-bakery.example",
        "status": "ok",
        "ms": 4
      },
      {
        "id": "agent-readiness",
        "tool": "agent-readiness",
        "area": "ai_readiness",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 37
      },
      {
        "id": "tech-stack",
        "tool": "tech-stack",
        "area": "context",
        "target": "https://acme-bakery.example/",
        "status": "ok",
        "ms": 20
      }
    ],
    "areas_checked": [
      "seo",
      "security_passive",
      "links",
      "email_auth",
      "ai_readiness"
    ],
    "areas_not_checked": [],
    "engines": {
      "seo_engine": "not used (off or not available)",
      "safe_scan": "not used (off or not available)",
      "deep_active_scan": "never used by this product"
    },
    "limitations": [
      "Passive and read-only: plain GET/HEAD requests and public DNS lookups, as a browser or crawler would make. No login, no form submission, no active or intrusive testing.",
      "Point-in-time: results describe what the site served when observed_at says; sites change.",
      "Up to 10 page(s), found from the home page's internal links; pages behind JavaScript navigation, logins or not linked from the home page are not seen.",
      "robots.txt is obeyed: disallowed pages are listed, not fetched.",
      "Security headers and TLS are read from our server; a CDN or firewall may answer differently in other regions.",
      "DKIM is looked up at 30 common selectors only.",
      "Response times are single measurements from one location."
    ],
    "not_a_guarantee": "This report is not a penetration test, security certification, legal or compliance opinion, and does not promise rankings, traffic or security. Absence of a finding does not prove absence of a problem."
  },
  "site_context": {
    "technologies": [
      {
        "name": "Apache",
        "category": "Web server",
        "version": "2.4.41"
      },
      {
        "name": "PHP",
        "category": "Language",
        "version": "7.4.3"
      }
    ],
    "server": "Apache/2.4.41 (Ubuntu)",
    "generator": null,
    "note": "Detected from one page's HTML and response headers (signatures, not guesses). Absence of a technology is not proof it is unused."
  },
  "meta": {
    "white_label": true,
    "duration_ms": 114,
    "checks_ok": 22,
    "checks_failed": 1
  },
  "deliverables": {}
}