Erstellung eigener Funktionen

Fügen Sie einfach eigene Hilfsfunktionen zu Latte-Templates hinzu. Rufen Sie PHP-Logik direkt in Ausdrücken für Berechnungen, den Zugriff auf Dienste oder die Generierung dynamischer Inhalte auf, was Ihre Templates sauber und leistungsstark hält.

Was sind Funktionen?

Funktionen in Latte ermöglichen es Ihnen, den Satz von Funktionen zu erweitern, die innerhalb von Ausdrücken in Templates ({...}) aufgerufen werden können. Sie können sie sich als benutzerdefinierte PHP-Funktionen vorstellen, die nur innerhalb Ihrer Latte-Templates verfügbar sind. Dies bringt mehrere Vorteile mit sich:

Bequemlichkeit: Sie können Hilfslogik definieren (wie Berechnungen, Formatierungen oder den Zugriff auf Anwendungsdaten) und sie mit einer einfachen, bekannten Funktionssyntax direkt im Template aufrufen, genauso wie Sie strlen() oder date() in PHP aufrufen würden.

{var $userInitials = initials($userName)} {* z.B. 'J. D.' *}

{if hasPermission('article', 'edit')}
    <a href="...">Bearbeiten</a>
{/if}

Keine Verschmutzung des globalen Raums: Im Gegensatz zur Definition einer echten globalen Funktion in PHP existieren Latte-Funktionen nur im Kontext des Template-Renderings. Sie müssen den globalen PHP-Namensraum nicht mit Helfern belasten, die nur für Templates spezifisch sind.

Integration mit Anwendungslogik: Das PHP-Callable hinter einer Latte-Funktion kann alles sein – eine anonyme Funktion, eine statische Methode oder eine Instanzmethode. Das bedeutet, dass Ihre Funktionen in Templates problemlos auf Anwendungsdienste, Datenbanken, Konfigurationen oder jede andere benötigte Logik zugreifen können, indem sie Variablen erfassen (im Fall von anonymen Funktionen) oder Dependency Injection verwenden (im Fall von Objekten). Das obige Beispiel hasPermission demonstriert dies deutlich, da es wahrscheinlich im Hintergrund einen Autorisierungsdienst aufruft.

Überschreiben nativer Funktionen (optional): Sie können sogar eine Latte-Funktion mit demselben Namen wie eine native PHP-Funktion definieren. Im Template wird anstelle der ursprünglichen Funktion Ihre eigene Version aufgerufen. Dies kann nützlich sein, um ein template-spezifisches Verhalten bereitzustellen oder eine konsistente Verarbeitung sicherzustellen (z. B. sicherstellen, dass strlen immer Multibyte-sicher ist). Verwenden Sie diese Funktion mit Vorsicht, um Missverständnisse zu vermeiden.

Standardmäßig erlaubt Latte den Aufruf aller nativen PHP-Funktionen (sofern nicht durch die Sandbox eingeschränkt). Eigene Funktionen erweitern diese integrierte Bibliothek um die spezifischen Bedürfnisse Ihres Projekts.

Wenn Sie nur einen einzelnen Wert transformieren, ist möglicherweise die Verwendung eines eigene Filter geeigneter.

Erstellung und Registrierung von Funktionen

Ähnlich wie bei Filtern gibt es mehrere Möglichkeiten, eigene Funktionen zu definieren und zu registrieren.

Direkte Registrierung über addFunction()

Die einfachste Methode ist die Verwendung von addFunction() am Latte\Engine-Objekt. Sie geben den Namen der Funktion (wie sie im Template erscheinen wird) und das entsprechende PHP-Callable an.

$latte = new Latte\Engine;

// Einfache Hilfsfunktion
$latte->addFunction('initials', function (string $name): string {
	preg_match_all('#\b\w#u', $name, $m);
	return implode('. ', $m[0]) . '.';
});

Verwendung im Template:

{var $userInitials = initials($userName)}

Die Argumente der Funktion im Template werden direkt in derselben Reihenfolge an das PHP-Callable übergeben. PHP-Funktionalitäten wie Typ-Hints, Standardwerte und variable Parameter (...) funktionieren wie erwartet.

Registrierung über eine Erweiterung

Für eine bessere Organisation und Wiederverwendbarkeit registrieren Sie Funktionen innerhalb einer Latte Erweiterung. Dieser Ansatz wird für komplexere Anwendungen oder gemeinsam genutzte Bibliotheken empfohlen.

namespace App\Latte;

use Latte\Extension;
use Nette\Security\Authorizator;

class MyLatteExtension extends Extension
{
	public function __construct(
		// Angenommen, der Authorizator-Dienst existiert
		private Authorizator $authorizator,
	) {
	}

	public function getFunctions(): array
	{
		// Registrierung von Methoden als Latte-Funktionen
		return [
			'hasPermission' => $this->hasPermission(...),
		];
	}

	public function hasPermission(string $resource, string $action): bool
	{
		return $this->authorizator->isAllowed($resource, $action);
	}
}

// Registrierung (angenommen, $container enthält den DIC)
$extension = $container->getByType(App\Latte\MyLatteExtension::class);
$latte = new Latte\Engine;
$latte->addExtension($extension);

Dieser Ansatz zeigt anschaulich, wie in Latte definierte Funktionen durch Objektmethoden unterstützt werden können, die ihre eigenen Abhängigkeiten haben können, die vom Dependency Injection Container Ihrer Anwendung oder einer Factory verwaltet werden. Dies hält die Logik Ihrer Templates mit dem Kern der Anwendung verbunden und bewahrt gleichzeitig eine übersichtliche Organisation.

Funktionen unter Verwendung einer Klasse mit Attributen

Genau wie Filter können Funktionen als Methoden in Ihrer Template-Parameterklasse mithilfe des Attributs #[Latte\Attributes\TemplateFunction] definiert werden.

use Latte\Attributes\TemplateFunction;

class TemplateParameters
{
	public function __construct(
		public string $userName,
		// weitere Parameter...
	) {}

	// Diese Methode wird als {initials(...)} im Template verfügbar sein
	#[TemplateFunction]
	public function initials(string $name): string
	{
		preg_match_all('#\b\w#u', $name, $m);
		return implode('. ', $m[0]) . '.';
	}
}

// Übergabe des Objekts an das Template
$params = new TemplateParameters(userName: 'John Doe', /* ... */);
$latte->render('template.latte', $params);

Latte entdeckt und registriert automatisch Methoden, die mit diesem Attribut gekennzeichnet sind, wenn das Parameterobjekt an das Template übergeben wird. Der Name der Funktion im Template entspricht dem Namen der Methode.

{* Verwendung der in der Parameterklasse definierten Funktion *}
{var $inits = initials($userName)}

Kontextsensitive Funktionen?

Im Gegensatz zu Filtern gibt es kein direktes Konzept von “kontextsensitiven Funktionen”, die ein Objekt ähnlich FilterInfo erhalten würden. Funktionen arbeiten innerhalb von Ausdrücken und benötigen typischerweise keinen direkten Zugriff auf den Rendering-Kontext oder Informationen zum Inhaltstyp auf die gleiche Weise wie Filter, die auf Blöcke angewendet werden.

Version: 3.0