← CodeClarityLab Home
Browse by Category
+ added · updated 7d
← Back to glossary

Server-Side Template Injection (SSTI)

security CWE-1336 OWASP A3:2021 CVSS 9.8 PHP 5.0+ Advanced

Also Known As

Server-Side Template Injection template injection SSTI

TL;DR

User input is embedded directly into a server-side template, allowing arbitrary code execution on the server.

Explanation

SSTI occurs when an application passes unsanitised user data into a template engine (Twig, Smarty, Blade) which then evaluates it as template syntax. An attacker who discovers the injection point can escalate to full remote code execution by exploiting the template engine's built-in object access. In PHP, Twig in sandbox mode mitigates the risk; never pass raw user input to Environment::createTemplate() or render().

How It's Exploited

An attacker submits a template expression such as {{7*7}} in a search field. If the response shows 49, they know the template engine is evaluating input and can escalate to {{''.__class__.__mro__[2].__subclasses__()}} or similar gadget chains to execute OS commands.

Common Misconception

Template injection is just a read-only information disclosure issue. Most template engines (Twig, Smarty, Blade) expose functionality that allows full RCE when injection is possible — attackers can call system functions or traverse the object graph to execute arbitrary code.

Why It Matters

Server-side template injection is effectively remote code execution within the template engine's context — often providing access to the underlying OS through template sandbox escapes.

Common Mistakes

  • Passing user input as the template string to render() instead of as a variable to a fixed template.
  • Using Twig with autoescape disabled and reflecting user input into the template.
  • Not sandboxing template rendering when user-defined templates are a feature of the application.
  • Confusing output encoding (which prevents XSS) with template injection (which requires not including user input in the template structure).

Code Examples

✗ Vulnerable
$twig->render($userInput, $data);
✓ Fixed
$twig->render('fixed_template.html.twig', ['query' => htmlspecialchars($userInput)]);

Added 15 Mar 2026
Edited 22 Mar 2026
Views 20
Rate this term
No ratings yet
🤖 AI Guestbook educational data only
| |
Last 30 days
0 pings F 0 pings S 3 pings S 1 ping M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 2 pings S 0 pings M 0 pings T 1 ping W 0 pings T 0 pings F 0 pings S 1 ping S 1 ping M 1 ping T 0 pings W 0 pings T 0 pings F 0 pings S 1 ping S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S
No pings yet today
No pings yesterday
Amazonbot 8 Google 2 Unknown AI 2 Perplexity 1 ChatGPT 1 SEMrush 1
crawler 13 crawler_json 1 pre-tracking 1
DEV INTEL Tools & Severity
🔴 Critical ⚙ Fix effort: Medium
⚡ Quick Fix
Never render user input as a template string — pass data as template variables, not as the template itself; sandbox the template engine if user templates are required
📦 Applies To
PHP 5.0+ web laravel symfony twig
🔗 Prerequisites
🔍 Detection Hints
Twig::render($userInput) or eval with template string containing user data; user-controlled template path
Auto-detectable: ✓ Yes semgrep psalm
⚠ Related Problems
🤖 AI Agent
Confidence: High False Positives: Low ✗ Manual fix Fix: High Context: File Tests: Update
CWE-94

✓ schema.org compliant