Reading the report
Every crawl writes an HTML report next to its JSON file: one file you can open in any browser, email to a client or keep. It is built as a work queue. The first screen answers "what is wrong, how bad is it, and what do I do first", and everything below it is there when you need the detail.
The header and the grade
The top of the report names the site, the date of the crawl, how many pages Raptor crawled, how long it took, and whether it ran the pages' JavaScript.
Beside that is the grade: a letter, the score out of 100 and the grade's name. In Raptor's voice the names are Apex predator (A), Healthy pack (B), Limping (C), Wounded (D) and Fossilised (F). A report in the plain voice shows the plain verdict instead, such as "Good".
Under the headline, one sentence says what costs the most points. A line of counts follows: how many findings there are to fix, by priority; how many pages have something to fix; how many Notes there are; and how many checks passed. A finding is one check that found something, however many pages it found it on, so "12 to fix" means twelve problems, not twelve affected URLs.
Anything that limits what the crawl could see, such as stopping at the page limit or pages that could not be fetched, appears as a blue line under the grade.
How is this calculated?
Open "How is this calculated?" to see where the points went. The score starts at 100, and each kind of problem takes off points up to a limit for that kind: broken pages, pages with major defects, site-level problems and minor issues. The table shows how many points each kind took and whether it hit its limit. Below it is the rule that orders the findings. How scoring works explains both in full.
A crawl saved by an older version of Raptor was scored by older rules, so its breakdown would not add up to its score. The report says so instead of showing one.
Fix first
Fix first lists up to six fixes, most important first: by priority (Fix now, High, Medium, Low) and then by the points each fix would win back. Each card shows, without a click:
- the priority, a plain title with the count built in, and its reach: "Every page — fix once" when
one change in a template fixes it everywhere, "/blog/ pages" when it sits in one section,
"Versions of /blog" when it is on one page's query-string versions (such as
/blog?category=seo), or the number of pages; - the points fixing it alone would win back, and the share of indexable pages it affects (indexable pages are the ones search engines are allowed to list);
- What we found, Why it matters and How to fix;
- one real example: the page's title over its address, with the measured detail;
- Copy fix brief and "Show all N pages".
When two or more findings affect exactly the same pages, they share one card, because one change usually fixes them together. The card lists the others under "Also on these pages".
All findings
Every finding is in one list, in the same order as Fix first. The strip of six areas above it follows the order a search engine meets a site: can it be reached, can it be indexed, is it unique, can it be found, is it well described, and is it fast and safe. Click an area to show only its findings; an area with nothing wrong says "Clear". You can also filter by priority, by reach, and by typing part of a finding's title.
Open a finding to see its three blocks, its example and its affected pages.
Affected pages
A finding's affected pages are grouped by folder first ("/blog/ 33", "/industry/ 21") so you can see where a problem lives before you read a list. Click a folder to show only its pages. The list shows each page's title over its address, 25 at a time, with the detail Raptor measured on the right. When every page shares the same detail, it is said once above the list instead of on every row. Click a page to open its details.
Copy URLs copies the address of every affected page, and Download CSV saves them as a
spreadsheet with the page title, folder and detail, whichever folder you are looking at. A cell
that would start a spreadsheet formula (with =, +, - or @) gets a leading apostrophe, so a
hostile page title cannot run as a formula when a client opens the file.
Notes, passed checks and checks not run
Three groups sit closed at the end of the list:
- Notes are things worth knowing that are often deliberate, such as pages that name another page as their main version, or pages kept out of search on purpose. They cost no points.
- Checks passed lists every check that found nothing, by area.
- Not checked lists the checks this crawl could not run, and why: they need PageSpeed data, pages rendered in a browser, the site's sitemaps, or its robots.txt.
Pages and the side panel
The Pages table lists every crawled page with its title, address, status code, whether search engines may list it, its findings, word count and response time. Search by address or title, filter by status or to pages with findings, and click a column heading to sort.
Click a page, here or anywhere else in the report, to open its side panel: its facts (status, depth, words, response time, and how many links on the page point within the site and how many point elsewhere; these are links on the page, not links to it), every finding and Note on it, its main heading, its description, its preferred address (its canonical URL), any redirects that led to it and the structured data it declares. "Open live page" opens the page itself in a new tab.
Site structure
The structure tree shows the site folder by folder, with how many pages each folder holds and how
many of them have something to fix. A page with a query string, such as /blog?category=seo, is
its own page in the tree.
About this crawl
The last section says what this crawl could not see (JavaScript it did not run, speed it did not measure, URLs it could not fetch and why), the settings it ran with, how the pages answered, and the exact command that runs the same crawl again, with Copy command.
Keyboard and links
| Key | What it does |
|---|---|
| ⌘K or Ctrl-K | Search findings and pages. It lists the first 8 findings and 12 pages that match and says how many more there are. Arrow keys move, Enter opens, Esc closes. |
j and k | Move down and up the findings list. Enter opens or closes the finding you are on. |
| Esc | Close search or the page panel. |
The report also takes two kinds of link, so you can point a colleague at one thing:
crawl.html#finding=<check id>opens that finding, for examplecrawl.html#finding=content.exact_duplicate. Each finding shows its check id.crawl.html#page=<address>opens a page's panel, for examplecrawl.html#page=/blog/x. In an address with a query string, the?,=and&are written as%3F,%3Dand%26:#page=/blog%3Fcategory%3Dseo. Clicking a page in the report puts its link in the address bar.
The sun and moon button switches between light and dark, and the report remembers your choice. Otherwise it follows your system.
Sharing and printing
- Copy fix brief copies one finding as a short Markdown task, ready to paste into Claude Code, Linear, Jira or an email: what was found, where, why it matters, how to fix it, and up to 25 affected addresses with the true total.
- Copy all fixes copies every finding to fix as one brief, most important first.
- Copy URLs and Download CSV export every affected address of one finding.
- Save as PDF: print the report from your browser (File, Print, Save as PDF). The printout is a clean summary: the header, the grade, Fix first in full, one line for every other finding and every Note, the crawl's limits and the footer. Buttons, filters, Pages and Structure are left out, and it always prints in the light theme, whatever theme you are reading in.
Large crawls
The report holds every crawled page, with nothing left out, so a finding's affected pages are always complete and Copy URLs and Download CSV are exact. Only the per-page details are capped at 100 per finding; when a finding has more, the report says so, and the exports still list every address. A 20,000-page report is about 6 MB, and up to about 9 MB when nearly every page has findings. It opens in well under a second and scrolls smoothly, because the Pages table only builds the rows you can see.
Opening it elsewhere
The report makes no network requests: its fonts and data are inside the file, so it works offline and tells no one you opened it. It also carries its own security policy (a Content-Security-Policy in its head) that lets only its own scripts run and loads nothing from the network, so text copied from a crawled page can never act as code, even if a future bug let some through unescaped.
A report downloaded from the REST API comes with a strict security policy that blocks its scripts. The first screen, every finding with its what, why and how, Notes and About still read in full, and the embedded fonts still load, but the filters, the affected-page lists, the Pages table, the structure tree and search need scripts. Open the downloaded file directly in a browser to use them.
Customising the report
An agency can put its own name, logo, colour and contact line on the reports Raptor writes. You
set this once, in a small text file called brand.toml, and every crawl uses it, including the
crawls the REST API and the MCP server run.
Where Raptor looks
For raptor crawl, Raptor uses the first of these that applies:
--no-brand: the plain Raptor brand, whatever else is set.--brand <FILE>: that file. Setting theRAPTOR_BRANDenvironment variable to a path does the same. If the file does not exist, the crawl stops.brand.tomlin Raptor's home folder, if it exists:~/.raptor/brand.toml, or~/raptor/brand.tomlon Windows. IfRAPTOR_HOMEis set, Raptor looks in that folder instead.- Otherwise, the Raptor brand.
raptor serve (the REST API and the MCP server) takes no brand flags. It reads RAPTOR_BRAND, or
the home folder's brand.toml, once when it starts, so restart it after you edit the file.
An example
agency_name = "Ravana Solutions"
logo = "ravana-logo.svg"
accent = "#1F4E79"
accent_dark = "#8AB8E6"
contact_line = "Questions? hello@ravanasolutions.com"
contact_url = "https://www.ravanasolutions.com/contact"
voice = "raptor"
mascot = trueEvery key is optional. Leave one out and the report keeps Raptor's choice for it.
| Key | What it sets | Limit |
|---|---|---|
agency_name | Your name on the report. It is also the logo's alt text, the words a screen reader says in place of the image | 80 characters, one line |
logo | Your logo. The path is relative to the folder brand.toml is in | An SVG or PNG file of 256 KB or less |
accent | Your brand colour on the light theme | A colour written as #RRGGBB |
accent_dark | Your brand colour on the dark theme. Without it, Raptor tries accent on the dark theme too | A colour written as #RRGGBB |
contact_line | A line of contact details, such as how to reach you | 160 characters, one line |
contact_url | The web address the contact line links to. With no contact_line, the address itself is shown | An http:// or https:// address |
voice | How the report's headlines and empty states speak: raptor is playful, plain is not | raptor or plain |
mascot | Whether the raptor drawing appears when there is nothing to fix or something went wrong | true or false |
What stops a crawl, and what only warns
A report with half of a client's brand on it is worse than no report. So when the file is wrong, the crawl stops before it fetches a single page. It exits with code 1 and an error that names the file and the key:
error: brand.toml: accent: "green" is not a #RRGGBB colourRaptor refuses:
- a file it cannot read, that is not valid TOML, that has a key it does not know (usually a typo), or that has a value of the wrong kind, such as a number where text belongs;
- an
accentoraccent_darkthat is not written as#RRGGBB; - a logo that is missing, is not an SVG or PNG file, or is over 256 KB;
- an SVG logo that could run code or load something from the internet. Raptor reads the file the
way a browser does, so a prefix such as
<s:script>or an escaped character does not hide anything. It refuses a logo:- with a
<script>,<foreignObject>,<iframe>,<object>,<embed>or<handler>element; - with an
on…=attribute such asonload=, or asrcdoc=attribute; - with a
javascript:address anywhere, or an animation (<set>or<animate>) that changes a link or anon…attribute; - with a link (
href,srcor CSSurl(…)) to anything other than a part of the same file or an image embedded asdata:image/; - that defines its own XML entities (a
<!DOCTYPE …[ … ]>block), which can hide code, or that is not well-formed XML;
- with a
- a
contact_urlthat is not anhttp://orhttps://address; - a value over its limit.
A colour that is hard to read does not stop the crawl. Raptor measures the contrast between your accent and each background of that theme, and asks for at least 4.5:1. That is the level the WCAG accessibility guidelines set for ordinary text. Button text on the accent, in white or near-black, must reach 4.5:1 as well. A theme that falls short keeps Raptor green, and the crawl carries on with a warning that gives the measured contrast:
warning: brand.toml: #C8E6C9 reaches only 1.21:1 against the light background #F6F3ED, below the 4.5:1 text needs, so the light theme uses Raptor greenThe light and dark themes are checked separately, so a pale accent can still be used on the dark theme.
What your accent changes
Your accent takes the place of Raptor's brand colour only: links, the main button and the keyboard focus ring. The green that marks a passing check or a healthy score stays Raptor's, so it means the same thing in every report. "Made with Raptor" in the footer and the small Raptor logo always appear and cannot be turned off.
Voice and mascot
voice = "plain" swaps Raptor's playful lines, such as "Hunt complete. 125 pages tracked down in
31s.", for plain ones, such as "Crawl complete: 125 pages in 31s." The findings read the same in
both voices: they are always plain. mascot = false hides the raptor drawing.
MCP panels
The panels Claude shows inside a conversation ignore your logo, accent and agency name, because the
apps that host them do not allow logo headers in panels. They do follow voice and mascot. The
text summaries the MCP tools return always use the plain voice.
If raptor serve cannot use the brand file, it still starts, logs the error, and writes reports
with the Raptor brand until the file is fixed.