Before and after, on our own site
The obvious question about a security scanner is whether the people who built it use it. We pointed xlogs at xlogs.com, it found something real, we fixed it, and we re-scanned to confirm. Every number on this page is from an actual scan on 13 August 2026. Nothing here is an illustrative example.
The headline
Every check, both times
This is the coverage receipt from both scans, side by side. The point of showing the unchanged rows too is that a "clear" is only meaningful if you can see what was actually tested.
| Check | Before | After | What changed |
|---|---|---|---|
| Protective security headers | ! found | ✓ clear | Added a headers() block in next.config.mjs. |
| Email spoofing protection | ! found | ! found | Pending: add SPF and DMARC TXT records. |
| Database exposed to the public | – n/a | – n/a | Nothing to do. |
| Secret keys shipped to the browser | ✓ clear | ✓ clear | Nothing to do. |
| Original source code downloadable | ✓ clear | ✓ clear | Nothing to do. |
| Private files served publicly | ✓ clear | ✓ clear | Nothing to do. |
| Scripts from compromised CDNs | ✓ clear | ✓ clear | Nothing to do. |
| DNS pointing at something you lost | ✓ clear | ✓ clear | Nothing to do. |
What the fix actually was
The scan reported that Content-Security-Policy, X-Content-Type-Options and X-Frame-Options were missing. The fix was a headers block in our Next.js config. Three details are worth stating, because they are the kind of thing a scanner cannot tell you and a person has to decide:
- The CSP still allows inline scripts. The Next.js App Router injects inline bootstrap code, so a nonce-less policy needs it. We say so rather than claiming a stricter policy than we run.
- One page is deliberately still frameable. Our embeddable widget exists to be put in an iframe, so it keeps every protection except the frame blocks.
- One endpoint is deliberately still cacheable. The README badge is a public image meant to be cached; making it uncacheable would turn every page view into a fresh scan.
That is the honest shape of most security work. The finding is mechanical; the judgement is in the exceptions.
What we did not find
No exposed keys, no public source maps, no readable database, no private files served. Those rows were clear before and after. A scanner that only ever reports problems is not telling you much, which is why every xlogs scan shows what it checked and not just what it found.
We also ran a full internal security audit at the same time, which found two higher-severity issues in our own code that a live scan cannot see from outside: an unbounded decompression path and missing rate limits. Both are fixed. The write-up is in SECURITY_AUDIT.md in our repository, including what a live scan can and cannot reach.
