Özel Filtreler Oluşturma
Filtreler, verileri doğrudan Latte şablonlarında biçimlendirmek ve değiştirmek için güçlü araçlardır.
Değişkenleri veya ifade sonuçlarını istenen çıktı biçimine dönüştürmek için boru (|
) sembolüyle temiz
bir sözdizimi sunarlar.
Filtreler Nedir?
Latte'deki filtreler esasen giriş değerini çıktı değerine dönüştürmek için özel olarak tasarlanmış PHP
fonksiyonlarıdır. Şablon ifadeleri ({...}
) içinde boru (|
) gösterimi kullanılarak
uygulanırlar.
Kolaylık: Filtreler, yaygın biçimlendirme görevlerini (tarihleri biçimlendirme, büyük/küçük harf değiştirme, kısaltma gibi) veya veri manipülasyonunu yeniden kullanılabilir birimlerde kapsüllemenizi sağlar. Şablonlarınızda karmaşık PHP kodunu tekrarlamak yerine, basitçe bir filtre uygulayabilirsiniz:
{* Kısaltma için karmaşık PHP yerine: *}
{$article->text|truncate:100}
{* Tarih biçimlendirme kodu yerine: *}
{$event->startTime|date:'Y-m-d H:i'}
{* Birden fazla dönüşüm uygulama: *}
{$product->name|lower|capitalize}
Okunabilirlik: Filtreleri kullanmak, dönüşüm mantığı filtre tanımına taşındığı için şablonları daha temiz ve sunuma daha odaklı hale getirir.
Bağlama Duyarlılık: Latte'deki filtrelerin önemli bir avantajı, bağlama duyarlı olma yetenekleridir. Bu, bir filtrenin çalıştığı içerik türünü (HTML, JavaScript, düz metin vb.) tanıyabileceği ve karşılık gelen mantığı veya kaçışı uygulayabileceği anlamına gelir; bu, özellikle HTML oluştururken güvenlik ve doğruluk için çok önemlidir.
Uygulama Mantığı ile Entegrasyon: Özel fonksiyonlar gibi, bir filtrenin arkasındaki PHP çağrılabilir nesnesi bir kapanış (closure), statik metot veya örnek metodu olabilir. Bu, filtrelerin gerekirse uygulama servislerine veya verilerine erişmesine olanak tanır, ancak ana amaçları giriş değerini dönüştürmek olarak kalır.
Latte varsayılan olarak zengin bir standart filtre seti sağlar. Özel filtreler, projenize özgü biçimlendirme ve dönüşümlerle bu seti genişletmenizi sağlar.
Birden fazla girişe dayalı mantık gerçekleştirmeniz gerekiyorsa veya dönüştürülecek birincil bir değeriniz yoksa, muhtemelen özel bir fonksiyon kullanmak daha uygundur. Karmaşık işaretleme oluşturmanız veya şablon akışını kontrol etmeniz gerekiyorsa, özel bir etiket düşünün.
Filtre Oluşturma ve Kaydetme
Latte'de özel filtreleri tanımlamanın ve kaydetmenin birkaç yolu vardır.
addFilter()
ile Doğrudan Kayıt
Filtre eklemenin en basit yolu, doğrudan Latte\Engine
nesnesinde addFilter()
yöntemini
kullanmaktır. Filtre adını (şablonda nasıl kullanılacağını) ve karşılık gelen PHP çağrılabilir nesnesini
belirtirsiniz.
$latte = new Latte\Engine;
// Argümansız basit filtre
$latte->addFilter('initial', fn(string $s): string => mb_substr($s, 0, 1) . '.');
// İsteğe bağlı argümanlı filtre
$latte->addFilter('shortify', function (string $s, int $len = 10): string {
return mb_substr($s, 0, $len);
});
// Dizi işleyen filtre
$latte->addFilter('sum', fn(array $numbers): int|float => array_sum($numbers));
Şablonda Kullanım:
{$name|initial} {* $name 'John' ise 'J.' yazdırır *}
{$description|shortify} {* Varsayılan uzunluk 10 kullanılır *}
{$description|shortify:50} {* Uzunluk 50 kullanılır *}
{$prices|sum} {* $prices dizisindeki öğelerin toplamını yazdırır *}
Argümanları Geçirme:
Borunun (|
) solundaki değer her zaman filtre fonksiyonuna ilk argüman olarak geçirilir. Şablonda iki
nokta üst üste (:
) işaretinden sonra belirtilen herhangi bir parametre, sonraki argümanlar olarak geçirilir.
{$text|shortify:30}
// shortify($text, 30) PHP fonksiyonunu çağırır
Uzantı ile Kayıt
Daha iyi organizasyon için, özellikle yeniden kullanılabilir filtre setleri oluştururken veya bunları paket olarak paylaşırken, önerilen yol bunları bir Latte uzantısı içinde kaydetmektir:
namespace App\Latte;
use Latte\Extension;
class MyLatteExtension extends Extension
{
public function getFilters(): array
{
return [
'initial' => $this->initial(...),
'shortify' => $this->shortify(...),
];
}
public function initial(string $s): string
{
return mb_substr($s, 0, 1) . '.';
}
public function shortify(string $s, int $len = 10): string
{
return mb_substr($s, 0, $len);
}
}
// Kayıt
$latte = new Latte\Engine;
$latte->addExtension(new App\Latte\MyLatteExtension);
Bu yaklaşım, filtre mantığınızı kapsüllenmiş ve kaydı basit tutar.
Filtre Yükleyici Kullanımı
Latte, addFilterLoader()
kullanarak bir filtre yükleyici kaydetmenize olanak tanır. Bu, Latte'nin derleme
sırasında herhangi bir bilinmeyen filtre adı için isteyeceği tek bir çağrılabilir callable'dır. Yükleyici, filtrenin PHP
çağrılabilir nesnesini veya null
döndürür.
$latte = new Latte\Engine;
// Yükleyici, filtre çağrılabilirlerini dinamik olarak oluşturabilir/alabilir
$latte->addFilterLoader(function (string $name): ?callable {
if ($name === 'myLazyFilter') {
// Burada pahalı bir başlatma hayal edin...
$service = get_some_expensive_service();
return fn($value) => $service->process($value);
}
return null;
});
Bu yöntem öncelikle çok pahalı başlatmaya sahip filtrelerin geç yüklenmesi için tasarlanmıştır. Ancak, modern bağımlılık enjeksiyonu uygulamaları genellikle geç servisleri daha verimli bir şekilde yönetir.
Filtre yükleyicileri karmaşıklık ekler ve genellikle addFilter()
ile doğrudan kayıt veya
getFilters()
kullanarak bir uzantı içinde kayıt lehine önerilmez. Filtre başlatmadaki performans sorunlarıyla
ilgili, başka türlü çözülemeyen ciddi, özel bir nedeniniz olmadıkça yükleyicileri kullanın.
Niteliklere Sahip Bir Sınıf Kullanan Filtreler
Filtreleri tanımlamanın başka bir zarif yolu, şablon
parametre sınıfınızdaki yöntemleri kullanmaktır. Yönteme sadece #[Latte\Attributes\TemplateFilter]
niteliğini ekleyin.
use Latte\Attributes\TemplateFilter;
class TemplateParameters
{
public function __construct(
public string $description,
// diğer parametreler...
) {}
#[TemplateFilter]
public function shortify(string $s, int $len = 10): string
{
return mb_substr($s, 0, $len);
}
}
// Nesneyi şablona geçirme
$params = new TemplateParameters(description: '...');
$latte->render('template.latte', $params);
Latte, TemplateParameters
nesnesi şablona geçirildiğinde bu nitelikle işaretlenmiş yöntemleri otomatik
olarak tanır ve kaydeder. Şablondaki filtre adı, yöntem adıyla aynı olacaktır (bu durumda shortify
).
{* Parametre sınıfında tanımlanan filtreyi kullanma *}
{$description|shortify:50}
Bağlamsal Filtreler
Bazen bir filtre, yalnızca giriş değerinden daha fazla bilgiye ihtiyaç duyar. Çalıştığı dizenin içerik türünü (örneğin HTML, JavaScript, düz metin) bilmesi veya hatta değiştirmesi gerekebilir. Bu, bağlamsal filtrelerin devreye girdiği yerdir.
Bağlamsal bir filtre, normal bir filtreyle aynı şekilde tanımlanır, ancak ilk parametresi
Latte\Runtime\FilterInfo
olarak tür ipucu verilmelidir. Latte bu imzayı otomatik olarak tanır ve filtreyi
çağırırken FilterInfo
nesnesini geçirir. Sonraki parametreler, filtre argümanlarını normal
şekilde alır.
use Latte\Runtime\FilterInfo;
use Latte\ContentType;
$latte->addFilter('money', function (FilterInfo $info, float $amount): string {
// 1. Giriş içerik türünü kontrol edin (isteğe bağlı, ancak önerilir)
// Null (değişken giriş) veya düz metne izin verin. HTML vb. üzerine uygulanırsa reddedin.
if (!in_array($info->contentType, [null, ContentType::Text], true)) {
$actualType = $info->contentType ?? 'mixed';
throw new \RuntimeException(
"|money filtresi uyumsuz içerik türü $actualType içinde kullanıldı. Beklenen metin veya null."
);
}
// 2. Dönüşümü gerçekleştirin
$formatted = number_format($amount, 2, '.', ',') . ' EUR';
$htmlOutput = '<i>' . htmlspecialchars($formatted) . '</i>'; // Doğru kaçışı sağlayın!
// 3. Çıktı içerik türünü bildirin
$info->contentType = ContentType::Html;
// 4. Sonucu döndürün
return $htmlOutput;
});
$info->contentType
, Latte\ContentType
'dan bir dize sabitidir (örneğin
ContentType::Html
, ContentType::Text
, ContentType::JavaScript
, vb.) veya filtre bir
değişkene ({$var|filter}
) uygulanırsa null
olur. Bu değeri giriş bağlamını kontrol etmek için
okuyabilir ve çıktı bağlamının türünü bildirmek için ona yazabilirsiniz.
İçerik türünü HTML olarak ayarlayarak, Latte'ye filtreniz tarafından döndürülen dizenin güvenli HTML olduğunu söylersiniz. Latte daha sonra bu sonuca varsayılan otomatik kaçışını uygulamaz. Bu, filtreniz HTML işaretlemesi oluşturuyorsa çok önemlidir.
Filtreniz HTML oluşturuyorsa, bu HTML'de kullanılan herhangi bir giriş verisini doğru şekilde
kaçmaktan siz sorumlusunuz (yukarıdaki htmlspecialchars($formatted)
çağrısında olduğu gibi). Bunu yapmamak
XSS güvenlik açıkları oluşturabilir. Filtreniz yalnızca düz metin döndürüyorsa, $info->contentType
ayarlamanız gerekmez.
Bloklardaki Filtreler
Bloklara uygulanan tüm filtreler bağlamsal olmalıdır. Bunun nedeni, bloğun içeriğinin, filtrenin farkında olması gereken tanımlanmış bir içerik türüne (genellikle HTML) sahip olmasıdır.
{block heading|money}1000{/block}
{* 'money' filtresi ikinci argüman olarak '1000' alır
ve $info->contentType ContentType::Html olacaktır *}
Bağlamsal filtreler, verilerin bağlamlarına göre nasıl işlendiği üzerinde güçlü bir kontrol sağlar, gelişmiş işlevlere olanak tanır ve özellikle HTML içeriği oluştururken doğru kaçış davranışını sağlar.