Séparation des vues
Le problème : considérez ce gestionnaire (PHP)
$res = '<html><head><title>Bla</title><body><table>';
foreach ($array as $k => $v) {
$res .= "<tr><td>$k</td><td>$v</td></tr>";
}
return $res . '</table></body></html>';
- Confusion entre logique et présentation,
- Code difficile à lire et à organiser,
- Syntaxe très lourde (répétition de la variable
$res
), - Pas possible de colorier la syntaxe HTML dans un éditeur,
- Risques de sécurité…
Les templates naissent pour résoudre ces problèmes.
Templates
Un exemple de template (Twig)
<!DOCTYPE html>
<html>
<head>
<title>Blabla</title>
</head>
<body>
<h1>Bonjour {{ user }}</h1>
{% include 'content.html' %}
</body>
</html>
- La valeur de la variable
user
est remplacée pour{{ user }}
; - Le contenu de
content.html
est inséré dans la sortie ; - Tout le reste est renvoyé à l’identique.
Langages de templating
Les langanges de templating permettent, en général, de
- Remplacer des variables (
{{ var }}
) ; - Exécuter des tests (
{% if %}
) ; - Boucler sur des tableaux (
{% for %}
) ; - Inclure d’autres templates (
{% include %}
,{% block %}
,{% extends %}
) ; - Chaîner des transformations (
{{ var | upper | strip }}
) ; - Appliquer des opérateurs simples (mathématiques, logiques, comparaisons).
Quelques langages de templating
Twig (langage de templates par défaut de Silex)
Contexte : dictionnaire d’associations clé → valeur passé au template. Par exemple :
nom
→toto
users
→[titi, tutu, tata]
Substitution de variables, filtres
Hello {{ nom }}
Hello toto
Filtres
En majuscules : {{ nom | upper }}
Une liste : {{ users | join(', ') }}
{% filter upper %}
{{ nom }}
{% endfilter %}
En majuscules : TOTO
Une liste : titi, tutu, tata
TOTO
Contrôle
Conditionnel
{% if nom == 'toto' %}
Bonjour mon cher
{% else %}
Bonjour
{% endif %}
Bonjour mon cher
Boucle
{% for i in range(0, 3) %}
Utilisateur : {{ users[i] }}
{% endfor %}
{% for u in users %}
Utilisateur : {{ u }}
{% endfor %}
Utilisateur: titi
Utilisateur: tutu
Utilisateur: tata
Utilisateur: titi
Utilisateur: tutu
Utilisateur: tata
Modularité
Inclusion
{% include 'autre_template.html' %}
Macros
{% macro greet(nom) %}
Bonjour Mr {{ nom }}
{% endmacro %}
{% from "macros.html" import greet %}
{{ greet('toto') }}
Bonjour Mr toto
Héritage
Voici le template `main.html`
Les blocs sont affichés tels quels
{% block titre %}
Un titre quelconque
{% endblock %}
{% block pied %}
Copyright Pinco Pallino
{% endblock %}
Voici le template `main.html`
Les blocs sont affichés tels quels
Un titre quelconque
Copyright Pinco Pallino
{% extends 'main.html' %}
{% block titre %}
Remplace titre
{% endblock %}
Voici le template `main.html`
Les blocs sont affichés tels quels
Remplace titre
Copyright Pinco Pallino
Utiliser Twig: render
dans Silex
$app->register(new Silex\Provider\TwigServiceProvider(),
array('twig.path' => 'templates'));
$app->get('/', function(Application $app) {
return $app['twig']->render('hello.html', array(
'nom' => 'Toto'
));
});
dans Express (s’applique aussi à d’autres langages de templating)
var twig = require('twig');
app.set('views', 'templates'); // où trouver les templates
app.set('view engine', 'html'); // à quelle extension
app.engine('html', twig.__express); // associer twig
app.get('/', function(req, res) {
res.render('hello.html', { 'nom' : 'Toto' });
});
Échappement
- La programmation web comporte le melange de plusieurs langages de programmation : HTML, CSS, JavaScript, PHP, templates, SQL, …
- Chaque langage a ses caractères spéciaux. Par ex.:
<
,>
,&
,'
,"
Considérez ce gestionnaire
function(Request $req) {
return '<h1>' . $req->query->get('nom') . '</h1>';
}
Nom :
Les caractères <U , Z>
sont interprétés comme la balise <U>
.
Échappement HTML
HTML définit des séquences d’échappement pour ses caractères spéciaux, appelées character entities.
< |
> |
& |
" |
' |
< |
> |
& |
" |
' |
Ces remplacements sont appliqués automatiquement par
- La fonction
htmlspecialchars()
de PHP, - La fonction
$app->escape()
de Silex, - Twig et la majorité des autres moteurs de templates,
- Des modules de Node.js, comme escape-html.
ATTENTION : n’utiliser que pour du HTML !
- JSON : remplacer
'
→\'
,"
→\"
, - JavaScript : comme JSON, mais avec beaucoup de soin !
Échappement dans Twig
Les remplacements {{ var }}
sont échappés par défaut.
Désactiver l’échappement :
{% autoescape false %} {{ nom }} {% endautoescape %}
{{ nom | raw }}
Réactiver l’échappement :
{% autoescape 'html' %}{{ nom }}{% endautoescape %}
{% autoescape 'css' %}{{ nom }}{% endautoescape %}
{{ nom | escape }}
{{ nom | e }}
Nom :
Lectures
- La doc officielle de Twig (en anglais),
- L’introduction pour les designers (en anglais),
- Le tutoriel de Symfony (en français).