This isn't a penetration testing guide. It's the set of checks a developer can run from the browser, on a page they're already looking at, that catch the misconfigurations responsible for a large share of real-world front-end incidents.
Server-side security matters more. But server-side security is somebody's full-time job, and these checks are twenty minutes of yours.
1. Security headers
Six headers do most of the work. Read them in the Network panel on the document request, or with a tool that reads them for you.
| Header | Protects against | Reasonable value |
|---|---|---|
Content-Security-Policy | XSS, data injection | Start with default-src 'self' and widen deliberately |
Strict-Transport-Security | Protocol downgrade, cookie theft | max-age=31536000; includeSubDomains |
X-Content-Type-Options | MIME sniffing | nosniff |
X-Frame-Options | Clickjacking | DENY, or CSP frame-ancestors |
Referrer-Policy | URL leakage to third parties | strict-origin-when-cross-origin |
Permissions-Policy | Unwanted camera/mic/geolocation access | camera=(), microphone=(), geolocation=() |
Rather than scrolling the Network panel for each one, the Security Headers Checker in Web Developer Tools reports all six at once with present/missing status, and individual viewers give you the full value when you need it: CSP Viewer, HSTS Checker, Referrer Policy Viewer, Permissions Policy Viewer, X-Frame-Options Viewer and the cross-origin trio (COOP, COEP, CORP). Faster than scrolling the Network panel, and it works on pages behind a login where an external scanner can't reach.
About CSP specifically
A Content Security Policy is the highest-value header and the most work to get right. Two failure modes are common enough to name:
- A policy so permissive it does nothing.
script-src 'unsafe-inline' 'unsafe-eval' *is decoration. If you allow inline scripts, you've disabled the main protection CSP offers. - A policy so strict it breaks the site, which then gets removed entirely rather than fixed.
The way through is Content-Security-Policy-Report-Only. Deploy the policy you want in report-only mode, collect violations for a couple of weeks, fix what's genuinely needed, then enforce. Use nonces or hashes for the inline scripts you can't remove rather than reaching for 'unsafe-inline'.
Content-Security-Policy:
default-src 'self';
script-src 'self' 'nonce-r4nd0m' https://cdn.example.com;
style-src 'self' 'unsafe-inline';
img-src 'self' data: https:;
frame-ancestors 'none';
base-uri 'self';
form-action 'self';base-uri and form-action are frequently omitted and both close real attack paths.2. HTTPS, everywhere, properly
The padlock is the start, not the finish.
- 1HTTP redirects to HTTPS, on every route, with a 301
- 2HSTS is set with a long max-age, so the browser refuses HTTP before it even tries
- 3No mixed content — an
http://image or script on anhttps://page is either blocked or silently downgrades the security of the whole page - 4The certificate covers every hostname you use, including www and any subdomains
- 5Expiry is monitored. Automated renewal fails quietly more often than anyone expects
Mixed content is the one that hides. Passive mixed content (images, media) is often allowed with a warning; active mixed content (scripts, iframes, stylesheets) is blocked outright, which usually breaks a feature rather than producing a visible error. A Mixed Content Detector finds http:// resources on a secure page, Outline Non-Secure Elements marks them on the page itself, and SSL Certificate Information plus SSL Expiry Checker cover the certificate side.
3. Cookie flags
Three attributes, and a session cookie missing any of them is a finding:
Set-Cookie: session=abc123; HttpOnly; Secure; SameSite=Lax; Path=/; Max-Age=86400- `HttpOnly` — JavaScript can't read it, so an XSS can't steal the session
- `Secure` — never sent over plain HTTP
- `SameSite` —
Laxfor most things,Strictfor high-value actions,Noneonly withSecureand only when you genuinely need cross-site sending
Check them in DevTools' Application panel, or with WDT's Cookie Security Audit, which checks the flags across every cookie at once and reports which are missing what. The storage inspection guide covers the surrounding mechanics.
4. Exposed secrets
Front-end code ships to the client. Minification is not encryption, and a bundle is a text file.
What to search your built output for:
- API keys with write access, particularly cloud provider and payment keys
- Internal hostnames, admin URLs and staging endpoints
- Source maps deployed to production, which hand over your original source
- Comments containing credentials, TODOs about auth, or an engineer's debugging notes
- Environment variables that were bundled because they were prefixed for client exposure by mistake
A Secret Detector scans the page for strings matching common key formats. It's a first pass rather than a guarantee, but it's a first pass most sites have never run. Publishable keys (a Stripe pk_, a public analytics ID) are fine by design; the point is to confirm each exposed key is one that's meant to be public.
5. Third-party and supply-chain risk
Every script you load from someone else's domain runs with full access to your page: your DOM, your cookies (if not HttpOnly), your forms. If their CDN is compromised, so are you.
Three mitigations, in order of effort:
- 1
Count them
WDT's Third-party Domain Report and Detect Third-Party Scripts list every external domain the page contacts. Most teams are surprised by the number, particularly when a tag manager is loading things dynamically.
- 2
Add subresource integrity
An
integrityhash on external scripts and stylesheets means the browser refuses to run modified content. WDT's Resource Integrity Checker verifies which external resources have SRI and which don't. Note that SRI and a version-floating CDN URL are incompatible by design, which is a good reason to pin versions. - 3
Constrain them with CSP
A
script-srcallowlist means a compromised tag manager can't inject a script from an arbitrary domain. This is where CSP earns its keep.
Also check Access-Control-Allow-Origin on your own APIs. A wildcard combined with credentials is a misconfiguration browsers will reject, but a reflected-origin implementation that echoes whatever Origin it receives is worse and won't be rejected at all.

6. Forms and input handling
Client-side checks you can make from the browser:
- Login and payment forms post to HTTPS endpoints — check the
action, not just the page URL - Password fields are
type="password"and not sent in a URL query string - CSRF tokens are present on state-changing forms
autocomplete="off"isn't being used on password fields, which fights password managers and pushes people toward weaker passwords- File uploads restrict type client-side, while you confirm the server does too — client-side restriction is a UX feature, never a control
View Form Information lists every form with its method, action and fields; View Autocomplete-Off Fields reports where autocomplete has been disabled. Display Passwords reveals the contents of password fields, which is a testing convenience and also a reminder of how little a masked input actually protects.
7. Information disclosure
Small leaks that make an attacker's reconnaissance easier:
X-Powered-Byand a versionedServerheader — turn them off<meta name="generator">with a CMS version- Verbose error pages with stack traces or SQL fragments in production
- Directory listing enabled on an assets folder
.git,.env,.DS_Storeor backup files reachable over HTTP- Internal comments left in the HTML — the HTML Comments Viewer dumps all of them, which is worth doing once
None of these is a vulnerability on its own. Together they turn a blind attack into a targeted one, and the technology detection guide shows exactly how easy that reconnaissance is.
A twenty-minute pass
- 1Run a security header check and note what's missing
- 2Confirm HTTPS redirects and HSTS is set
- 3Scan for mixed content
- 4Check every cookie for
HttpOnly,SecureandSameSite - 5Look for tokens in
localStorage - 6List third-party domains and ask whether each is still needed
- 7Check external scripts for SRI hashes
- 8Search the bundle for exposed keys
- 9Confirm no source maps are deployed to production
- 10Turn off version-disclosing headers
For an external view of the same headers, securityheaders.com and Mozilla's Observatory both grade a public URL. They can't reach anything behind a login, which is where a browser-side check earns its place.
Cookie and token handling sits between security and client-side storage, and every header discussed here is read the same way as any other, covered in viewing HTTP headers in Chrome.