Bac à sable

Latte possède une forteresse blindée directement sous le capot. Il s'agit du mode sandbox, une fonctionnalité importante qui protège les applications utilisant des modèles provenant de sources non fiables. Par exemple, lorsqu'ils sont modifiés par les utilisateurs eux-mêmes.

Le mode bac à sable veille à ce que le sable ne sorte pas de la boîte. Ainsi, il offre un accès limité aux balises, filtres, fonctions, méthodes, etc. Comment cela fonctionne-t-il ? Nous définissons simplement ce que nous voulons autoriser dans le modèle. Au début, tout est interdit et nous accordons progressivement des permissions :

Le code suivant permet au modèle d'utiliser les balises {block}, {if}, {else} et {=} (cette dernière est une balise pour imprimer une variable ou une expression) et tous les filtres :

$policy = new Latte\Sandbox\SecurityPolicy;
$policy->allowTags(['block', 'if', 'else', '=']);
$policy->allowFilters($policy::All);

$latte->setPolicy($policy);

Nous pouvons également autoriser l'accès aux fonctions, méthodes ou propriétés globales des objets :

$policy->allowFunctions(['trim', 'strlen']);
$policy->allowMethods(Nette\Security\User::class, ['isLoggedIn', 'isAllowed']);
$policy->allowProperties(Nette\Database\Row::class, $policy::All);

N'est-ce pas incroyable ? Vous pouvez tout contrôler à un niveau très bas. Si le modèle tente d'appeler une fonction non autorisée ou d'accéder à une méthode ou une propriété non autorisée, il lève l'exception Latte\SecurityViolationException.

Créer des politiques à partir de zéro, lorsque tout est interdit, peut ne pas être pratique, vous pouvez donc commencer à partir d'une base sûre :

$policy = Latte\Sandbox\SecurityPolicy::createSafePolicy();

Cela signifie que toutes les balises standard sont autorisées, sauf contentType, debugbreak, dump, extends, import, include, layout, php, sandbox, snippet, snippetArea, templatePrint, varPrint, widget. Tous les filtres standard sont également autorisés, à l'exception de datastream, noescape et nocheck. Enfin, l'accès aux méthodes et aux propriétés de l'objet $iterator est également autorisé.

Les règles s'appliquent au modèle que nous insérons avec la nouvelle balise {sandbox} avec la nouvelle balise. Il s'agit d'un modèle semblable à {include}, mais qui active le mode “sandbox” et ne transmet pas de variables externes :

{sandbox 'untrusted.latte'}

Ainsi, la mise en page et les pages individuelles peuvent utiliser toutes les balises et variables comme auparavant, les restrictions ne seront appliquées qu'au modèle untrusted.latte.

Certaines violations, comme l'utilisation d'une balise ou d'un filtre interdit, sont détectées au moment de la compilation. D'autres, comme l'appel de méthodes non autorisées d'un objet, au moment de l'exécution. Le modèle peut également contenir d'autres bogues. Afin d'éviter qu'une exception ne soit levée à partir du modèle sandboxé, ce qui perturbe l'ensemble du rendu, vous pouvez définir votre propre gestionnaire d'exception, qui, par exemple, se contente de l'enregistrer.

Si nous voulons activer le mode sandbox directement pour tous les modèles, c'est facile :

$latte->setSandboxMode();