Why SPA security is different
Single Page Applications shift a lot of logic to the browser — which means the attack surface shifts too. Unlike traditional server-rendered apps, your SPA is running your code in an environment you don’t control. This changes how you need to think about XSS, CSRF, authentication, and data exposure.
Cross-Site Scripting (XSS)
XSS is the most common SPA vulnerability. It happens when an attacker injects malicious scripts into your app’s output. Modern frameworks like React escape output by default — but there are still ways to get burned.
- Never use
dangerouslySetInnerHTMLwith untrusted content - Sanitize any user-generated HTML with a library like
DOMPurify - Set a strict Content Security Policy (CSP) header
- Avoid storing sensitive data in
localStorage— it’s accessible to any script on the page
CSRF Protection
Cross-Site Request Forgery tricks authenticated users into making requests they didn’t intend. If your API uses cookie-based auth, you need CSRF protection.
- Use SameSite=Strict or SameSite=Lax on session cookies
- Validate the
OriginandRefererheaders server-side - If using Laravel, the built-in CSRF middleware handles this automatically for state-changing requests
Authentication strategies
The session-vs-JWT debate matters here. For SPAs consuming your own API, HttpOnly cookies with short-lived sessions are generally safer than storing JWTs in localStorage. See my related post on this topic.
If a JWT is stolen from localStorage, an attacker can use it indefinitely until it expires. A stolen HttpOnly cookie is much harder to extract via JavaScript.
Security headers
A hardened set of HTTP response headers goes a long way. Configure these at your CDN or server level:
Content-Security-Policy: default-src 'self'; script-src 'self'
X-Frame-Options: DENY
X-Content-Type-Options: nosniff
Referrer-Policy: strict-origin-when-cross-origin
Permissions-Policy: camera=(), microphone=(), geolocation=()
Dependency hygiene
Your app is only as secure as its weakest dependency. Run npm audit regularly, pin versions where possible, and audit third-party scripts before adding them. Supply chain attacks are increasingly common.
Security isn’t a feature you add at the end — it’s a mindset you apply throughout. Start with the basics above and you’ll be ahead of the vast majority of SPAs in production today.