diff --git a/content/posts/2023/php/lightweight-template-engine-php/index.md b/content/posts/2023/php/lightweight-template-engine-php/index.md new file mode 100644 index 0000000..e375502 --- /dev/null +++ b/content/posts/2023/php/lightweight-template-engine-php/index.md @@ -0,0 +1,230 @@ +--- +title: "📃 Простой класс шаблонизатора на PHP" +date: 2023-10-05T06:12:03+03:00 +draft: false +tags: [php, tutorial] +--- + +![](splash.png) + +> Перевод: https://codeshack.io/lightweight-template-engine-php/ + +Класс шаблонизатора является лёгким, гибким, быстрым +и безопасным. Он компилирует шаблоны в оптимизированный PHP код. + +Ниже я предоставлю полный исходный код и примеры того, +как можно использовать класс шаблонизатора. + +# Зачем мне нужен шаблонизатор? + +The template engine keeps your design code away from your application code, +this reason alone is good practice and follows many design patterns. +Using a template engine is entirely up to you, if you prefer +to keep your code clean and tidy then using a template engine is ideal. + +If you're working with the MVC pattern then it is a good idea +to use a template engine. + +# Исходный код + +Create a new file and name it `Template.php` and add: +Создайте новый файл `Template.php` и вставьте в него следующий код: + +```php +' . PHP_EOL . $code); + } + return $cached_file; + } + + static function clearCache() { + foreach(glob(self::$cache_path . '*') as $file) { + unlink($file); + } + } + + static function compileCode($code) { + $code = self::compileBlock($code); + $code = self::compileYield($code); + $code = self::compileEscapedEchos($code); + $code = self::compileEchos($code); + $code = self::compilePHP($code); + return $code; + } + + static function includeFiles($file) { + $code = file_get_contents($file); + preg_match_all('/{% ?(extends|include) ?\'?(.*?)\'? ?%}/i', $code, $matches, PREG_SET_ORDER); + foreach ($matches as $value) { + $code = str_replace($value[0], self::includeFiles($value[2]), $code); + } + $code = preg_replace('/{% ?(extends|include) ?\'?(.*?)\'? ?%}/i', '', $code); + return $code; + } + + static function compilePHP($code) { + return preg_replace('~\{%\s*(.+?)\s*\%}~is', '', $code); + } + + static function compileEchos($code) { + return preg_replace('~\{{\s*(.+?)\s*\}}~is', '', $code); + } + + static function compileEscapedEchos($code) { + return preg_replace('~\{{{\s*(.+?)\s*\}}}~is', '', $code); + } + + static function compileBlock($code) { + preg_match_all('/{% ?block ?(.*?) ?%}(.*?){% ?endblock ?%}/is', $code, $matches, PREG_SET_ORDER); + foreach ($matches as $value) { + if (!array_key_exists($value[1], self::$blocks)) self::$blocks[$value[1]] = ''; + if (strpos($value[2], '@parent') === false) { + self::$blocks[$value[1]] = $value[2]; + } else { + self::$blocks[$value[1]] = str_replace('@parent', self::$blocks[$value[1]], $value[2]); + } + $code = str_replace($value[0], '', $code); + } + return $code; + } + + static function compileYield($code) { + foreach(self::$blocks as $block => $value) { + $code = preg_replace('/{% ?yield ?' . $block . ' ?%}/', $value, $code); + } + $code = preg_replace('/{% ?yield ?(.*?) ?%}/i', '', $code); + return $code; + } + +} +?> +``` + +Когда код проекта будет готов, не забудьте включить кеширование, +обновив переменные `$cache_enabled` и `$cache_path variables`. + +# Как использовать шаблонизатор + +Создайте новый файл `index.php` и вставьте в него следующий код: + +```php + +``` + +Создайте новый HTML файл `layout.html` и вставьте в него следующий код: + +```html + + + + {% yield title %} + + + + {% yield content %} + + +``` + +Это макет, который мы будем использовать для данного примера. + +Создайте новый HTML файл `index.html` и вставьте в него следующий код: + +```html +{% extends layout.html %} + +{% block title %}Home Page{% endblock %} + +{% block content %} +

Home

+

Welcome to the home page!

+{% endblock %} +``` + +Теперь откройте файл `index.php` и посмотрите на результат. + +Но что, если мы хотим использовать переменные в наших файлах шаблонов? +Просто измените код шаблона в `index.php` следующим образом: + +```php +Template::view('about.html', [ + 'title' => 'Home Page', + 'colors' => ['red','blue','green'] +]); +``` + +И используйте переменные таким образом: + +```html +{% extends layout.html %} + +{% block title %}{{ $title }}{% endblock %} + +{% block content %} +

Home

+

Welcome to the home page, list of colors:

+ +{% endblock %} +``` + +Чтобы обезопасить результат, вместо: `{{ $output }}` +необходимо использовать `{{{ $output }}}`. + +Для таких значений, будет применяться функция +[`htmlspecialchars`](https://www.php.net/manual/en/function.htmlspecialchars.php). + +Наследование блоков: + +```html +{% block content %} +@parent +

Extends content block!

+{% endblock %} +``` + +Импортировать дополнительные файлы шаблонов: + +```text +{% include forms.html %} +``` + +Чтобы очистить кеш, достаточно удалить все файлы в катоалоге `$cache_path` +или вызвать функцию `Template::clearCache();`` + +# Заключение + +Шаблонизатор очень полезен в больших проектах. +Он позволит отделить дизайн-код от кода приложения. + +Вы можете свободно использовать этот класс шаблонов в своих проектах. + + + +**Автор:** David Adams | **MIT License** diff --git a/content/posts/2023/php/lightweight-template-engine-php/splash.png b/content/posts/2023/php/lightweight-template-engine-php/splash.png new file mode 100644 index 0000000..05afd33 Binary files /dev/null and b/content/posts/2023/php/lightweight-template-engine-php/splash.png differ