Glossary
What is XSS (Cross-Site Scripting): a flaw that runs an attacker's script in another user's browser
XSS (Cross-Site Scripting) makes an attacker's script run in another user's browser, leading to session theft and page tampering. The three types (stored/reflected/DOM), how it works, and the main defense (output escaping, framework auto-escaping, CSP) — explained defensively, without attack steps.
XSS is when text typed into a form runs as a script on someone else's screen. Here's how it works and how to reliably prevent it (no attack steps).
The three types
XSS splits by "how the malicious string reaches execution."
| Type | How it's planted |
|---|---|
| Stored | Saved in a post/profile and runs for everyone who views it (most dangerous) |
| Reflected | A URL parameter is reflected straight back into the page; runs for whoever clicks the link |
| DOM-based | No server round-trip — client-side JS handles input unsafely |
Why it's dangerous (how it works)
The browser runs any <script> in the page as "legitimate code." If an attacker's string lands as HTML in the page, the browser can't tell it from real code.
The damage is "everything that page can do." If RCE is the most severe flaw on the server side, XSS is the most severe on the client (user) side.
Defense: escape on output
XSS is prevented at output, not input. The moment you render a value, convert it so it can't be interpreted as HTML.
Escape on output (most important)
When rendering user-supplied values, convert < > & " ' to HTML entities — using the right method for the context (HTML body, attribute, JS, URL).
Don't disable your framework's auto-escaping
React/Vue/templates auto-escape by default. Just avoid raw-HTML injection (dangerouslySetInnerHTML, v-html) and you prevent most XSS.
Defense in depth with CSP
Content-Security-Policy lets the browser block scripts you didn't allow, limiting damage even if something slips through.
Protect cookies
Mark session cookies HttpOnly so JS can't read them. Even if an XSS gets through, the damage is smaller.
This site's view: the best defense is not disabling the safety features yourself
Modern frameworks default to safe. Most XSS appears the moment a developer deliberately disables auto-escaping to "inject raw HTML." If you truly must allow HTML, run it through a proven sanitizer, not your own string handling. "Disabling safety for convenience" is the biggest risk.
How XSS differs from attacks it is confused with
XSS is often mixed up with CSRF, which has a similar name, and with SQL injection, which is also a case of input being treated as instructions. The difference is what runs, and where.
| Attack | What happens, and where | Main defense |
|---|---|---|
| XSS | The attacker's script runs in the user's browser as part of the real page | Escaping on output, CSP |
| CSRF | The user's logged-in session is used to send a request they did not intend. No script needs to run | CSRF tokens, SameSite cookies |
| SQL injection | Input is interpreted on the server as part of an SQL statement | Placeholders |
| Clickjacking | The real page is layered invisibly so the user clicks it without knowing | CSP frame-ancestors |
Note that XSS also defeats CSRF defenses. Once a script runs inside the page, it can read the CSRF token on that page too (the OWASP CSRF guide gives the same warning).
A real example: XSS in a screen opened by staff
In 2026, Instructure, the company behind the Canvas learning management system, said an intrusion started with XSS. According to the company, the attacker used a free account to submit a support ticket containing malicious code, and when a support agent opened it, an XSS flaw was exploited to gain elevated privileges inside Canvas (→ the Canvas (Instructure) data breach).
The lesson is that XSS is not only a problem for public pages. Support, contact and admin screens that show text sent from outside to your own staff carry more risk, because the accounts that open them have more power.
XSS is still among the most common weaknesses. In MITRE's "CWE Top 25" (the 25 most dangerous software weaknesses), published in December 2025, XSS (CWE-79) ranked first. In September 2024, the US agencies CISA and FBI also issued an alert asking software makers to eliminate XSS from their products.
How to check your own site
You do not need to try attack strings. Start with these four checks.
Find places that insert raw HTML
Search your code for dangerouslySetInnerHTML, v-html, innerHTML and document.write, and check whether any user-supplied value can reach them. If it can, render it as text instead, or pass it through a proven sanitizer.
Check whether CSP is sent
Use the Security Headers Check to see whether Content-Security-Policy is present and what it allows. Allowing 'unsafe-inline' greatly weakens it against XSS. To write a new one, draft it with the CSP Builder and run it in Report-Only mode (which only reports violations) first.
Check your session cookie flags
In the browser's developer tools (Application → Cookies), confirm that the session cookie has HttpOnly and Secure. The site audit also checks cookie flags.
Include admin and support screens
Check that internal screens showing text from outside (ticket bodies, file names, display names) are escaped to the same standard as public pages.
Sources (primary)
- OWASP, "Cross Site Scripting Prevention Cheat Sheet" — cheatsheetseries.owasp.org (escaping per output context, safe framework defaults)
- MITRE, "2025 CWE Top 25 Most Dangerous Software Weaknesses" (December 2025) — cwe.mitre.org (CWE-79 ranked first)
- CISA and FBI, "Secure by Design Alert: Eliminating Cross-Site Scripting Vulnerabilities" (September 17, 2024) — cisa.gov
- OWASP, "Cross-Site Request Forgery Prevention Cheat Sheet" — cheatsheetseries.owasp.org (XSS can bypass CSRF defenses)
- IPA, "How to Secure Your Web Site" — ipa.go.jp (Japanese)
Read next
- Glossary: What is CSRF · What is RCE · What is a JWT (a token often stolen via XSS)
- Defense in depth: security headers are not a list to stack (CSP narrows what an XSS can do)
- Basics: Security basics
Classification
CWE classifies the types of weakness behind vulnerabilities; MITRE ATT&CK classifies attacker techniques. Both are maintained by MITRE and widely used to label vulnerability reports and detection rules.
CWE (weakness type)
CWE™: Copyright © 2006–2026, The MITRE Corporation. CWE is a trademark of The MITRE Corporation. The MITRE Corporation hereby grants you a non-exclusive, royalty-free license to use CWE for research, development, and commercial purposes. Any copy you make for such purposes is authorized on the condition that you reproduce MITRE’s copyright designation and this license in any such copy. CWE Terms of Use
FAQ
QWhat happens with XSS?
An attacker's script runs in the victim's browser as part of the real page. That can mean session theft (impersonated login), reading input, defacing the page, or auto-running other actions.
QWhat's the top defense against XSS?
Escaping on output: when you render user-supplied values, convert them so they aren't interpreted as HTML. React/Vue templates do this by default, so the biggest win is to not disable that auto-escaping (avoid dangerouslySetInnerHTML, etc.). Add CSP for defense in depth.
QIs sanitizing on input enough?
Usually not. The reliable defense is escaping per output context (HTML body, attribute, JS, URL). Input filters alone leak via context mismatches. Only when you must allow HTML, run it through a trusted sanitizer.
QWhy is it called XSS and not CSS?
The initials of Cross-Site Scripting are CSS, but that clashes with CSS (Cascading Style Sheets), the language that styles web pages. So 'Cross' is written as X, and XSS became the standard abbreviation.
QIf I deploy CSP, do I still need other XSS defenses?
Yes. CSP (Content-Security-Policy) is a second layer that limits the damage when escaping slips. A CSP that allows 'unsafe-inline' loses much of its value against XSS. Escaping on output stays the foundation; CSP sits on top of it.
QIf my cookies are HttpOnly, is XSS no longer a concern?
It reduces the damage but does not remove it. HttpOnly only stops scripts from reading the cookie. A script running through XSS can still send requests as the user from inside the page and read whatever the page shows. HttpOnly limits the damage; it does not prevent XSS.