Skip to content
Auto-Escaping & XSS
step 1/5

Reading — step 1 of 5

Read

~1 min readVariables & Filters

Auto-Escaping & XSS

The web's #1 vulnerability: putting user data into HTML without escaping.

<p>User said: {{ comment }}</p>

If user typed: <script>alert("xss")</script>, that script runs in everyone's browser.

Auto-escape: by default, all variable output runs through HTML escape:

  • <&lt;
  • >&gt;
  • &&amp;
  • "&quot;
  • '&#39;
python

Order: & MUST be first (else &lt; becomes &amp;lt;).

SafeString marker: subclass of str. Engine knows: don't escape this.

python

When to use | safe:

  • Markdown converted to HTML by trusted lib.
  • Pre-rendered partials.
  • NOT for user input.

Context-aware escaping (Go's html/template):

  • HTML body: HTML escape.
  • HTML attribute: attribute escape.
  • JS string: JavaScript escape.
  • URL: percent encode.
  • CSS: CSS escape.
<a href="{{ url }}">{{ link_text }}</a>
<script>var x = "{{ js_var }}";</script>

Each context has different rules. Go's templates auto-detect; Jinja2 escapes uniformly (HTML).

Modern best practice:

  • Auto-escape ON by default.
  • Mark trusted with safe.
  • Audit safe usages — they're attack surfaces.
  • Validate user input at boundary.

XSS still tops OWASP. Always auto-escape unless explicitly trusted.

Discussion

Ask a question, share an insight, or help someone who’s stuck.

Sign in to post a comment or reply.

Loading…