Skip to content

TwigRendererInterface

Alexander Saal edited this page Aug 7, 2025 · 2 revisions

TwigRendererInterface

Why do we use Twig as a template engine instead of Handlebars? Because Twig is the flexible, fast, modern and secure template engine for PHP. JobRouter uses Twig itself, so we decided to provide the use of Twig in the SDK as well. If you want to learn more about Twig you can use the Twig documentation.

The example shown here only serves to illustrate how you can use Twig in your own application.

The structure can be as follows.

SDK Interfaces TwigRendererInterface Example

On the one hand, we have a templates directory and, within the template directory, an authorized components directory in the template directory. Both directories contain, in this example, only one Twig template. If you wish, you can add more Twig templates.

On the one hand an templates/index.html.twig file, which is used as an entry point and a templates/authorized/_user.html.twig as a Twig component, which can then be integrated in the templates/index.html.twig via {% include 'authorized/_user.html.twig' %}. The additional specification of with context only causes the context variable $templateVariables to be passed to templates/authorized/_user.html.twig. The values of the context variable can then be accessed within the templates/authorized/_user.html.twig.

Interface & Methods

interface TwigRendererInterface
{
    /**
     * Disables the auto_reload option.
     */
    public function disableAutoReload(): void;

    /**
     * Enables the auto_reload option.
     *
     * <b>Important:</b>
     * This method allows you to make changes to the Twig template during development without clearing the
     * cache. Using this method will cause Twig to regenerate the template again.
     *
     * So be careful!
     */
    public function enableAutoReload(): void;

    /**
     * Enables the strict_variables option.
     */
    public function enableStrictVariables(): void;

    /**
     * Disables the strict_variables option.
     */
    public function disableStrictVariables(): void;

    /**
     * Set the absolute template cache path.
     *
     * <b>Important:</b>
     * It is important that this method is executed after calling enableAutoReload(), otherwise the
     * revalidation / recompilation of the template will not take effect.
     *
     * This is only necessary if you want to separate the cache folder from JobRouter. By default, the template
     * cache path is located under \<jobrouter-path\>/cache/symfony/prod/twig
     *
     * @param string $path The absolute path to the compiled templates
     */
    public function setTemplateCachePath(string $path): void;

    /**
     * Set paths where to look for templates
     *
     * @param string|array $paths A path or an array of paths where to look for templates
     * @param string|null $rootPath The root path common to all relative paths (null for getcwd())
     *
     * @throws \Twig\Error\LoaderError When the template path cannot be found
     */
    public function setTemplatePath(string|array $paths = [], ?string $rootPath = null): void;

    /**
     * Renders a template.
     *
     * @param string $fileName The template file name
     * @param array $context The optional template variables
     *
     * @throws \Twig\Error\LoaderError When the template cannot be found
     * @throws \Twig\Error\SyntaxError When an error occurred during compilation
     * @throws \Twig\Error\RuntimeError When an error occurred during rendering
     */
    public function render(string $fileName, array $context = []): string;
}

Usage

The index.php is the entry point of your application.

use JobRouter\Sdk\Template\TwigRendererInterface;
use JobRouter\Sdk\UserManagerInterface;

These two lines are PHP use statements, and they are part of a PHP file that belongs to a object-oriented PHP project using the JobRouter SDK. These lines allow you to work with:

  • TwigRendererInterface for rendering templates.
  • UserManagerInterface for managing or accessing user-related data.

They're just bringing those interfaces into the current file's namespace so you don't need to write the full path every time you refer to them.


use JobRouter\Sdk\Template\TwigRendererInterface;

This imports the TwigRendererInterface interface from the JobRouter\Sdk\Template namespace. It is responsible for rendering Twig templates in the JobRouter SDK context. By importing this interface, it can be used to render templates via dependency injection.


use JobRouter\Sdk\UserManagerInterface;

This imports the UserManagerInterface interface from the JobRouter\Sdk namespace. It defines methods that relate to user management, such as retrieving user data, roles or authorizations.


return function (UserManagerInterface $userManagerInterface, TwigRendererInterface $twigRenderer): void {

The main return closure. This returns a function that is used as a callable - the two interfaces are passed here as a dependency injection.


    $twigRenderer->setTemplatePath('templates', __DIR__);

    //$twigRenderer->enableAutoReload();
    //$twigRenderer->enableStrictVariables();

    /*$twigRenderer->setTemplateCachePath(
        __DIR__ . DIRECTORY_SEPARATOR . 'templates' . DIRECTORY_SEPARATOR . 'cache',
    );*/

Sets the base path for your Twig templates to a templates directory relative to this file. By default the auto reloading and strict variables are disabled.

Commented-out options show support for:

  • Auto-reloading templates on changes
  • Enforcing strict variable rules
  • Caching rendered templates

    $templateVariables = [
        'authorized' => [],
    ];

Initializing the $templateVariables array with a key named 'authorized', and setting it to an empty array as a default value. This approach avoids undefined index errors when the template tries to access authorized, since it's always set - even if empty or with an error.


    try {
        $user = $userManagerInterface->getCurrentUser();

Tries to retrieve the currently authenticated user. Then it extracts all available user info like name, email, department, custom fields, and even role membership (isInJobFunction('Administrator')). If something goes wrong, a fallback with 'error' => true is set.


        $templateVariables['authorized'] = [
            'error' => false,
            'userName' => $user->getUsername(),
            'preName' => $user->getPreName(),
            'lastName' => $user->getLastName(),
            'fullName' => $user->getFullName(),
            'email' => $user->getEmail(),
            'userDefined1' => $user->getUserDefined1(),
            'userDefined2' => $user->getUserDefined2(),
            'userDefined3' => $user->getUserDefined3(),
            'userDefined4' => $user->getUserDefined4(),
            'userDefined5' => $user->getUserDefined5(),
            'supervisor' => $user->getSupervisor(),
            'department' => $user->getDepartment(),
            'phone' => $user->getPhone(),
            'fax' => $user->getFax(),
            'language' => $user->getLanguage(),
            'dateFormat' => $user->getDateFormat(),
            'decimalSeparator' => $user->getDecimalSeparator(),
            'thousandsSeparator' => $user->getThousandsSeparator(),
            'timezone' => $user->getTimezone(),
            'jobFunctions' => $user->getJobFunctions(),
            'inJobFunctions' => $user->isInJobFunction('Administrator') === false ? 'no (Administrator)' : 'yes (Administrator)',
            'userProfile' => $user->getUserProfile(),
            'avatarUrl' => $user->getAvatarUrl(),
        ];

It's a detailed snapshot of the currently logged-in user and retrieved from the JobRouter\Sdk\UserManagerInterface (via $userManagerInterface->getCurrentUser()), assigning each relevant method's return value to a key in the authorized array. This block builds a structured array of user data that gets passed to the Twig template under the key authorized. It's a detailed snapshot of the currently logged-in user.


    } catch (\Throwable) {
        $templateVariables['authorized'] = [
            'error' => true,
        ];
    }

This catch block is a fallback mechanism. It's triggered if any error or exception occurs while attempting to fetch the current user via $userManagerInterface->getCurrentUser().


    $result = $twigRenderer->render('index.html.twig', $templateVariables);
    echo $result;

Renders the template index.html.twig with the prepared $templateVariables and outputs it. You can find the complete example under PHP.

Twig

<!DOCTYPE html>
<html lang="de">
<head>
    <title>SDK Example to demonstrate the TwigRendererInterface and the UserManagerInterface!</title>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport" content="width=device-width, initial-scale=1"/>
    <meta name="robots" content="noindex,nofollow">
    <meta name="referrer" content="no-referrer">
    <meta name="referrer" content="never">
</head>
<body>
<h1 style="color: #fc0">SDK Example to demonstrate the TwigRendererInterface and the UserManagerInterface!</h1>
{% include 'authorized/_user.html.twig' with _context %}
</body>
</html>

This example from templates/index.html.twig shows how Twig can be used to integrate another Twig template with a given context.

{% if not authorized.error %}
    <h3 style="color: #59aa6e;">Authorized user is "{{ authorized.userName }}"!</h3>
    <pre>UserName: {{ authorized.userName }}</pre>
    <pre>Current User PreName: {{ authorized.preName }}</pre>
    <pre>Current User LastName: {{ authorized.lastName }}</pre>
    <pre>Current User FullName: {{ authorized.fullName }}</pre>
    <pre>Current User Email: {{ authorized.email }}</pre>
    <pre>Current User UserDefined1: {{ authorized.userDefined1 }}</pre>
    <pre>Current User UserDefined2: {{ authorized.userDefined2 }}</pre>
    <pre>Current User UserDefined3: {{ authorized.userDefined3 }}</pre>
    <pre>Current User UserDefined4: {{ authorized.userDefined4 }}</pre>
    <pre>Current User UserDefined5: {{ authorized.userDefined5 }}</pre>
    <pre>Current User Supervisor: {{ authorized.supervisor }}</pre>
    <pre>Current User Department: {{ authorized.department }}</pre>
    <pre>Current User Phone: {{ authorized.phone }}</pre>
    <pre>Current User Fax: {{ authorized.fax }}</pre>
    <pre>Current User Language: {{ authorized.language }}</pre>
    <pre>Current User DateFormat: {{ authorized.dateFormat }}</pre>
    <pre>Current User DecimalSeparator: {{ authorized.decimalSeparator }}</pre>
    <pre>Current User ThousandsSeparator: {{ authorized.thousandsSeparator }}</pre>
    <pre>Current User Timezone: {{ authorized.timezone }}</pre>
    <pre>Current User JobFunctions: {{ authorized.jobFunctions|join(',') }}</pre>
    <pre>User Is in JobFunction: {{ authorized.inJobFunctions }}</pre>
    <pre>Current User UserProfile: {{ authorized.userProfile }}</pre>
    <pre>Current User AvatarUrl: {{ authorized.avatarUrl }}</pre>
    <img src="/{{ authorized.avatarUrl }}" width="100"/>
{% else %}
    <h3 style="color: #f44;">You are currently not logged in to JobRouter!</h3>;
{% endif %}

This example from templates/authorized/_user.html.twig shows how Twig can be used as a component contained in templates/index.html.twig. Since we have passed the context to this template, we can directly access the context variable authorized.

PHP

<?php

use JobRouter\Sdk\Template\TwigRendererInterface;
use JobRouter\Sdk\UserManagerInterface;

return function (UserManagerInterface $userManagerInterface, TwigRendererInterface $twigRenderer): void {
    // Use this method to specify the path name for your templates. The second parameter defines where the template
    // directory should be searched for. If the second parameter is not specified, the same directory where the index.php
    // is located is searched for.
    //
    // This method must be called so that the Twig templates can be found; if this method is not used, JobRouter searches
    // for this template directory in the main directory.
    $twigRenderer->setTemplatePath('templates', __DIR__);

    // This method allows you to make changes to the Twig template during development without clearing the
    // cache. Using this method will cause Twig to regenerate the template again. So be careful!
    //$twigRenderer->enableAutoReload();

    // This method can be used to validate variables in templates. This means that if we have forgotten to
    // define a variable, we can't access it via the Twig template.
    //$twigRenderer->enableStrictVariables();

    // It is important that this method is executed after calling enableAutoReload(), otherwise the
    // revalidation / recompilation of the template will not take effect.
    //
    // This method sets the absolute template cache path. This is only necessary if you want to separate the cache
    // folder from JobRouter. By default, the template cache path is located under <jobrouter-path>/cache/symfony/prod/twig
    /*$twigRenderer->setTemplateCachePath(
        __DIR__ . DIRECTORY_SEPARATOR . 'templates' . DIRECTORY_SEPARATOR . 'cache',
    );*/

    // Define the variable context to use in the twig template
    $templateVariables = [
        'authorized' => [],
    ];

    try {
        $user = $userManagerInterface->getCurrentUser();

        $templateVariables['authorized'] = [
            'error' => false,
            'userName' => $user->getUsername(),
            'preName' => $user->getPreName(),
            'lastName' => $user->getLastName(),
            'fullName' => $user->getFullName(),
            'email' => $user->getEmail(),
            'userDefined1' => $user->getUserDefined1(),
            'userDefined2' => $user->getUserDefined2(),
            'userDefined3' => $user->getUserDefined3(),
            'userDefined4' => $user->getUserDefined4(),
            'userDefined5' => $user->getUserDefined5(),
            'supervisor' => $user->getSupervisor(),
            'department' => $user->getDepartment(),
            'phone' => $user->getPhone(),
            'fax' => $user->getFax(),
            'language' => $user->getLanguage(),
            'dateFormat' => $user->getDateFormat(),
            'decimalSeparator' => $user->getDecimalSeparator(),
            'thousandsSeparator' => $user->getThousandsSeparator(),
            'timezone' => $user->getTimezone(),
            'jobFunctions' => $user->getJobFunctions(),
            'inJobFunctions' => $user->isInJobFunction('Administrator') === false ? 'nein (Administrator)' : 'ja (Administrator)',
            'userProfile' => $user->getUserProfile(),
            'avatarUrl' => $user->getAvatarUrl(),
        ];
    } catch (\Throwable) {
        $templateVariables['authorized'] = [
            'error' => true,
        ];
    }

    // Render the given twig template with above defined context variables
    $result = $twigRenderer->render('index.html.twig', $templateVariables);

    // Output the complete rendered twig template with the context variables
    echo $result;
};
Clone this wiki locally