Jinja ‒ шаблонизатор для Python. Использование Jinja2 во Flask

Шаблонизатор (template engine) ‒ это такая программа, которая, читая данные из одного источника (файла-шаблона), находит в нем специальные конструкции и согласно определенным правилам заменяет их на данные из другого источника. На выходе вы получаете готовый документ, где уже нет никаких "переменых" и "неизвестных", все данные определены и "жестко вшиты". Для генерации html-страниц существует много разных шаблонизаторов.

Фреймворк Flask включает в себя Jinja2 ‒ шаблонизатор, для которого в шаблонах используются элементы синтаксиса языка Python.

Когда мы вызываем функцию render_template и передаем ей имя файла, помимо прочего в дело вступает и Jinja-движок, пропуская через себя содержимое файла.

В наших двух html-файлах много общего. Будет правильным вынести это общее в отдельный файл, а в местах, где у каждого свое, подставлять это свое из других файлов.

Изменим файл base.html следующим образом:

<!DOCTYPE html>
<html lang="ru">
  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>{% block title %}Главная страница{% endblock %} | Основы биологии </title>
  </head>
  <body>
    {% block content %}
    <h1>О сайте "Основы биологии"</h1>
    <p>Описание в разработке</p>
    {% endblock %}
  </body>
</html>

Мы обрамили часть содержимого тайтла и основной контент документа специальными командами-тегами. В браузере, перезагрузив страницу, вы не увидите изменений. Более того, открыв там исходный код (Ctrl + U), заметите, что эти команды были подчистую вырезаны.

Файл plants.html изменим сильнее:

{% extends 'base.html' %}
 
{% block title %}Растения{% endblock %}
 
{% block content %}
    <h1>Растения</h1>
    <p>Общая характеристика растений</p>
{% endblock %}

С помощью команды extends реализуется наследование шаблонов. Родителем здесь выступает base.html. Файл plants.html наследует все его содержимое, то есть контент base.html вставляется в plants.html как есть. Но то, что находится внутри обозначенных в plants.html блоков, заменяется собой то, что находится в таких же блоках в base.html.

Часто внутри родительского файла в block-контейнерах нет содержимого. Следуя такой логике, файл base.html должен выглядеть так:

<!DOCTYPE html>
<html lang="ru">
  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>{% block title %}{% endblock %} | Основы биологии </title>
  </head>
  <body>
    {% block content %}{% endblock %}
  </body>
</html>

При этом для главной страницы сайта мы должны были бы создать другой файл, например, index.html, и заполнить его по аналогии с plants.html.

Обратим внимание, что если родительский файл содержит block-контейнер, который не используется в дочернем, то это не вызывает ошибки. Как и наоборот ‒ дочерний может содержать контейнер, которого нет в родительском. Подобное может иметь место при более сложном наследовании: файл выступает базовым шаблоном для нескольких других или дочерний файл в свою очередь является родителем для другого.

Когда в проекте используется база данных, то программа, которую мы пишем на Python, берет из нее данные и при вызове функции rander_template передает их в шаблон. Эти данные вставляются в указанных местах (между тегами HTML, внутри значений атрибутов HTML), которые как могут находиться внутри block-контейнеров, так и быть за их пределами.

При использовании базы данных сайт обычно имеет не так много шаблонов. Однако в нашем случае каждый шаблон ‒ это страница сайта. С помощью фреймворка Flask мы лишь облегчаем себе обслуживание сайта, убирая повторяющийся код в общий шаблон.

Такой вариант сайта удобнее для случая, когда:

Также у вас не будет таких возможностей, как извлечение определенных данных из всего множества статей, их обобщение, сортировка и т. п. Для небольших, выглядящих статично со стороны пользователей, сайтов обычно этого не требуется.

Вернемся к тому, что при вызове rander_template() в функцию можно передавать не только имя файла html-шаблона, а также данные для его заполнения в соответствующих местах. Будем передавать путь страницы. Перед этим в файл base.html перед тегом </head> добавим следующую строку:

<link rel="canonical" href="https://biology.su{{ address }}">

Здесь в двойных фигурных скобках указывается имя аргумента, который будет передаваться в функцию render_template. Значение аргумента будет подставлено вместо всей конструкции {{ address }}. Если в этот момент обновить страницу сайта, несмотря на то, что аргумент не передавался, ошибки не будет. Фреймворк уберет конструкцию. Однако если с переменной выполняются какие-то действия (что-то извлекается, складывается с чем-то), то возникнет ошибка.

В файле программы добавим соответствующий аргумент render_template() в одном из представлений:

@app.route('/plants')
def page():
    return render_template('plants.html', address='/plants')

Количество дополнительных именованных аргументов может быть любым.

Flask для начинающих




Все разделы сайта