← Back to PHP Course | Chapter 15: Web Development | Lesson 2 of 12

PHP Template Engines

A template engine is like a fill-in-the-blanks page design kept apart from the code. Designers change how the page looks while programmers supply the information.
Syntax
php
$template = "Hello, {{ name }}!";
$output = str_replace("{{ name }}", htmlspecialchars($value), $template);   // escape output
echo $output;

What is a Template Engine?

A template engine keeps presentation markup separate from application logic, letting designers edit templates using simple placeholders without needing to understand the PHP that populates them.

Example: What is a Template Engine?

php
<?php
// Declare `$template`, set to "Hello, {{ name }}!"
$template = "Hello, {{ name }}!";
// Declare `$data` as an array: `["name" => "Alice"]`
$data = ["name" => "Alice"];
// Print `str_replace("{{ name }}", $data["name"], $template)` to the output
echo str_replace("{{ name }}", $data["name"], $template);
?>

Basic Variable Parsing

At its core, a template engine scans a template string for placeholders (like {{ name }}) and substitutes the corresponding variable's value, which is what keeps view files free of dense PHP control structures.

Example: Basic Variable Parsing

php
<?php
// Define the function `render` taking `$template`, `$data`
function render($template, $data) {
    // Loop over `$data`, binding each item to `$key => $value`
    foreach ($data as $key => $value) {
        // Declare `$template`, set to `str_replace("{{ $key }}", $value, $template)`
        $template = str_replace("{{ $key }}", $value, $template);
    }
    // Return `$template` from this function
    return $template;
}
// Print `render("Hi {{ name }}, you are {{ age }}", ["name" => "Alice", "age" => 30])` to the output
echo render("Hi {{ name }}, you are {{ age }}", ["name" => "Alice", "age" => 30]);
?>

Simulating Layout Inheritance

Layout inheritance lets a child template declare that it extends a shared parent layout and only override specific named blocks (like a page title or main content area), avoiding repeated header/footer markup in every view.

Example: Simulating Layout Inheritance

php
<?php
// Define the function `renderLayout` taking `$content`
function renderLayout($content) {
    // Return `"<html><body>$content</body></html>"` from this function
    return "<html><body>$content</body></html>";
}
// Declare `$pageContent`, set to "<h1>Home Page</h1>"
$pageContent = "<h1>Home Page</h1>";
// Print `renderLayout($pageContent)` to the output
echo renderLayout($pageContent);
?>

Safe Output Escaping

Because raw user data can contain malicious HTML or scripts, template engines escape variable output by default before printing it, closing off a major XSS attack surface automatically.

Example: Safe Output Escaping

php
<?php
// Define the function `render` taking `$template`, `$data`
function render($template, $data) {
    // Loop over `$data`, binding each item to `$key => $value`
    foreach ($data as $key => $value) {
        // Declare `$template`, set to `str_replace("{{ $key }}", htmlspecialchars($value), $template)`
        $template = str_replace("{{ $key }}", htmlspecialchars($value), $template);
    }
    // Return `$template` from this function
    return $template;
}
// Print `render("Comment: {{ text }}", ["text" => "<script>alert(1)</script>"])` to the output
echo render("Comment: {{ text }}", ["text" => "<script>alert(1)</script>"]);
?>

Modular Views

Splitting a layout into smaller included files -- a header, a footer, a nav bar -- keeps each piece focused and reusable across many pages, even without a full templating library.

Example: Modular Views

php
<?php
function header() { return "<header>Site Header</header>"; }
function footer() { return "<footer>Site Footer</footer>"; }
echo header() . "<main>Page content</main>" . footer();
?>
Related Topics
{# common_mistakes/chapter_summary/browser_support: on Hindi pages the view already swaps in the hi_ translation fields (or blanks these out if untranslated), so this renders correctly for both languages without a lang_code check here. #}
Common Mistakes
  1. Printing user data in a template without escaping it.
  2. Putting heavy logic in the template instead of the controller.
  3. Using a regular expression to fake a template engine when the input can break it.

Login to run this code

C/C++/Java/PHP execution requires a free account. Your code is saved — you'll land right back in the editor after logging in.