Ravindra BagaleCourses & study guides Track your progress

Guides

What Is XSS (Cross-Site Scripting) and How to Prevent It

Cross-Site Scripting (XSS) is when an application sends untrusted input into a web page in a way that the browser treats it as active script or HTML. Attackers aim to run actions as the victim (steal sessions, deface pages, fake login forms). Prevent XSS with context-aware output encoding, strict Content-Security-Policy (CSP), HttpOnly cookies, validating input, and safe frameworks — this guide is prevention only and does not include working attack strings.

Friends! Website comment box, search box, profile name — user text shows on the page. If a junior developer mixes raw HTML/JS, XSS risk appears. Today impact + prevention: encoding, CSP, HttpOnly cookies. Working exploit payloads / attack scripts no — classroom defence only. Complements the SQL injection guide summary.

Quick answer

Prevention checklist (vertical):

  1. Encode/escape output for the context (HTML body, HTML attribute, JavaScript, URL) — never “trust” display of raw user text.
  2. Prefer frameworks that auto-escape templates by default; avoid dangerously-set-HTML APIs unless sanitised by a vetted library.
  3. Set a strong Content-Security-Policy that blocks unexpected inline scripts where possible.
  4. Mark session cookies HttpOnly (and Secure, SameSite as appropriate) so scripts cannot read them easily.
  5. Validate and length-limit input; treat validation as depth, not the only control.
  6. Use modern sanitiser libraries for rich-text fields that truly need limited HTML.
  7. Never invent “test payloads” against sites you do not own — use your own lab.

Safe mental model:

User text = data
Your page templates = structure
Keep data from becoming structure/script
Encode on OUTPUT for the right context
CSP + HttpOnly = seatbelts

What do I need before this guide?

How does XSS happen (conceptually, no payloads)?

Prevent XSS with encoding and CSP Unsafe pages mix user text into HTML as code. Safe pages encode output, use CSP and HttpOnly cookies. Unsafe User text → raw HTML Browser may run it Session risk Safe Encode on output CSP + HttpOnly Data stays data encode

Unsafe pages mix user text into HTML as code. Safe pages encode output, use CSP and HttpOnly cookies so data stays data.

Vertical story:

  1. The app accepts text (comment, name, search query, URL parameter).
  2. That text is later written into HTML without proper encoding for that spot.
  3. The browser interprets part of it as script or active markup.
  4. The script runs with the site’s origin privileges in the victim’s browser.
  5. Impact can include account misuse via session abuse, fake UI, or forcing actions the user did not intend.

Types you will hear in class (names only):

  1. Stored — bad data saved on the server and shown to others later.
  2. Reflected — bad data bounced in an immediate response (often via a crafted link).
  3. DOM-based — unsafe client-side JavaScript writes user data into the DOM.

Still no exploit strings — defenders fix sinks and policies.

Real incident (public lesson) — Magecart / British Airways style skimming (2018)

Public reporting on the British Airways incident (2018) and the wider Magecart-style campaigns described attackers injecting skimming code into web checkout flows so browsers sent payment details to criminal infrastructure. Separately, historical browser/social bugs such as the old TweetDeck XSS worm showed how script injection in a popular web UI can spread quickly among logged-in users.

Care-take bullets (prevention focus):

  1. Treat third-party scripts on payment pages as high risk — inventory and pin them.
  2. Deploy CSP to reduce unexpected script execution.
  3. Subresource Integrity (SRI) for known CDN scripts when feasible.
  4. Monitor for unauthorised changes to JavaScript on checkout hosts.
  5. Encode all user-controlled fields; never “innerHTML for convenience” on profiles.

Red Team vs Blue Team (high level)

Side High-level goal Blue focus
Red Team Find a page that reflects or stores input unsafely Output encoding, CSP, sanitizers
Red Team Abuse session if scripts can run as the user HttpOnly cookies, short sessions, XSS fix
Blue Team Stop data from becoming code Secure defaults in templates + reviews

No PoCs, no bypass lists.

How do I prevent XSS step by step?

Step 1 — Encode on output (the main habit)

  1. Decide the context: HTML text node, attribute, CSS, JS string, or URL.
  2. Use the standard encoder for that context provided by your language/framework.
  3. Do not invent a home-made strip of “bad characters” as your only defence.
  4. Example mindset for a LearnFast Academy Pune student portal: a student nickname is text, not HTML.
  5. Code review question: “Where does this string enter the DOM?”

Step 2 — Prefer safe templating defaults

  1. Keep auto-escaping on.
  2. Avoid APIs named like “raw HTML” / “dangerously set” unless a senior review and sanitiser approve.
  3. For React/Vue/Angular/Django/Rails/Laravel — read the framework’s XSS section once and follow it.
  4. Nashik exporter invoice note field: plain text is enough; rich HTML is rarely required.
  5. If you paste Stack Overflow snippets that disable escaping, stop and rewrite.

Step 3 — Content-Security-Policy (CSP) concepts

  1. CSP is an HTTP header (or meta) that tells the browser which script sources are allowed.
  2. Goal: even if a bug injects a tag, the browser refuses unauthorised script.
  3. Start in report-only mode in production if you fear breakage, then enforce.
  4. Reduce inline scripts; prefer nonces or hashes when you must keep some inline.
  5. CSP is defence in depth — still fix the encoding bug.

Step 4 — Cookies and sessions (HttpOnly and friends)

  1. Session cookies should be HttpOnly so document script cannot read them via trivial JS access.
  2. Add Secure on HTTPS sites.
  3. Use SameSite attributes appropriately to reduce some cross-site sending cases.
  4. Short session lifetime + logout + revoke align with Zero Trust thinking.
  5. XSS can still cause damage even with HttpOnly (actions as the user) — fixing XSS remains mandatory.

Step 5 — Input handling and rich text

  1. Validate length and type early.
  2. For markdown/rich text, run a well-known sanitiser allow-list — do not regex-remove tags yourself.
  3. Store the sanitised form; still encode when appropriate on output.
  4. File uploads are a different control plane (content type, storage outside web root) — do not confuse with XSS encoding.
  5. Admin-only fields still need encoding — admins get XSS’d too.

Step 6 — Everyday product examples

  1. Instagram-like comments: treat comment bodies as text; encode entities on display.
  2. Search boxes: reflected results must encode the query string in HTML.
  3. Error pages: do not echo raw URLs into scripts.
  4. GF/BF shared wishlist web app (student project): profile “bio” field is the classic homework XSS foot-gun — encode it.
  5. Jio recharge lookalike phishing pages are social engineering; XSS is a developer bug class — different fix, both matter.

Ravindra Bagale's Tip

💡 Many students say "I remove angle brackets so it is safe". Incomplete. Context-aware encoding + framework defaults + CSP. Copy-pasting attack strings as a "test" on production — ethics + law both problems. Use your own lab. In interviews talk prevention, not payload flex. Stay alert!

Quick vocabulary

  1. Output encoding — turning user text into safe display text for a context.
  2. CSP — browser policy for which scripts may run.
  3. HttpOnly — cookie flag that keeps the value away from page JavaScript.
  4. Sanitiser — allow-list cleaner for limited rich HTML when you truly need it.

Care-take prevention checklist

  1. Auto-escape templates enabled.
  2. No unchecked raw HTML sinks.
  3. Context-aware encoders on every user field.
  4. CSP deployed (report-only → enforce).
  5. Session cookies HttpOnly + Secure.
  6. Sanitiser allow-list for rich text only.
  7. Dependency and script inventory on checkout pages.
  8. Code review checklist item: “XSS sink?”

How do I fix common XSS prevention mistakes?

Ghabru naka 😅 — these are the usual ones:

Symptom Likely cause Fix
“We strip script tags” only Brittle filter Encode + CSP; use proper sanitiser
Framework escape off for one field Convenience Turn escape back on or sanitise correctly
Cookie stolen via script in old app Cookie not HttpOnly Set HttpOnly; fix XSS; revoke sessions
CSP breaks theme Inline scripts everywhere Nonces/hashes; move scripts to files
Markdown preview shows odd UI Unsanitised HTML Allow-list sanitiser before render

Try it at home

Open one web project you own. Write:

  1. One place user text is displayed:
  2. Does the template auto-escape? (yes/no/unsure)
  3. Are session cookies HttpOnly in your browser devtools?
  4. One CSP next step you will read in docs this week:

Do not test attack strings on third-party sites.

Got it? XSS = untrusted input becomes script/HTML in the page. Fix = output encoding, safe templates, CSP, HttpOnly cookies. Do not publish payloads — prevention habit. Next: how to secure home Wi‑Fi step-by-step.

Frequently asked questions

What is XSS?

When untrusted input is sent to a page so the browser treats it as active script or HTML.

What is the primary fix?

Context-aware output encoding and safe templating defaults.

What does CSP do?

It tells the browser which script sources may run, reducing damage if injection occurs.

Why HttpOnly cookies?

They stop trivial document-script access to session cookies; you must still fix XSS.

Does this guide include exploit strings?

No. It is prevention-focused for builders and defenders only.

Which OWASP lesson covers XSS here?

Cyber Part 11 — A03 Injection Cross-Site Scripting (XSS).