A worked scan · Rowan Vexley
A scanner's first move is not clever. It asks your site for something that should not be there — a config file, a backup, an admin page — and reads what comes back.
The status code is the whole conversation. 404 means the door is shut. Anything else means the server answered, and a machine on the other end now has something to write down. Below is a real one from my own site, start to finish.
On 17 October I ran a plain request against rowanvexley.com:
curl -sI https://rowanvexley.com/.env
It came back:
HTTP/2 200
content-type: text/html; charset=utf-8
That is a 200 OK for a file that does not exist. The body was the homepage. I then tried the neighbours — /.git/config, /admin, a random path — and every one of them answered the same way: 200, and the same homepage.
It did not mean my secrets had leaked. It meant my site would not tell me when something was wrong. Every miss wore the front door, so a scanner could not tell a real page from a dead one, and neither could I.
My site is served from Cloudflare Pages. Pages has a fallback: if it cannot find the path you asked for and you have not given it a 404 page, it serves your index with a 200. That is meant to be friendly for single-page apps. On a site with real pages it is a lie, told politely, to every robot that knocks.
One file. 404.html, at the deploy root. Then redeploy. Nothing else changed.
# after the fix, same request
curl -sI https://rowanvexley.com/.env
HTTP/2 404
These are the real answers as I write this. You can run the same thing against rowanvexley.com and get the same table.
| Path | Status | Meaning |
|---|---|---|
| / | 200 | the front door, open |
| /.env | 404 | no such file, and it says so |
| /.git/config | 404 | same |
| /admin | 404 | same |
| /wp-login.php | 404 | same |
| /does-not-exist | 404 | same |
One honest answer for every miss. That is the whole difference.
Replace the URL with yours. If /.env comes back 200, you have the same bug, and it is one file to fix.
curl -sI https://yourstore.com/.env | head -1
curl -sI https://yourstore.com/.git/config | head -1
curl -sI https://yourstore.com/admin | head -1
Three lines. Run them in a terminal, or paste them one at a time into a browser console against your own domain. No account, no tool, nothing installed.
This is the free first step I offer, done once in public so you can see the shape of it: the request, the status, the cause, the smallest fix. Nothing dressed up. On a store with a checkout the same pass turns up what matters more — where card data is read in the page, which admin paths answer, what your headers let through.
Send me one storefront URL and I hand back the first three hits, free. One page, one pass, written plainly. If a deeper pass is what you need, I will scope and price it then.