Track your learning. ❹ Make your own Learning Log, and keep a list of the topics you're learning about. Whenever you learn something new about a topic, make an entry summarizing what you've learned. ❺ role="button">Register »
❻ {% endblock page_header %} В точке мы сообщаем Django о том, что далее следует определение содержимого блока page_header . Элемент jumbotron представляет собой обычный элемент div , к которому применяется набор стилевых директив. Селектор jumbotron применяет эту группу стилевых директив из библиотеки Bootstrap к элементу. Внутри элемента jumbotron содержатся три элемента. Первый — короткое сообще- ние Track your learning , которое дает новым посетителям представление о том, что делает Learning Log. Класс h1 является заголовком первого уровня, а с селектором display-3 заголовок становится более тонким и высоким . В точке включается более длинное сообщение с дополнительной информацией о том, что пользователь может сделать со своим дневником. Вместо простой текстовой ссылки мы создаем кнопку , которая предлагает поль- зователю зарегистрировать свою учетную запись Learning Log. Это та же ссылка, что и в заголовке, но кнопка выделяется на фоне страницы и показывает пользователю, что необходимо сделать для того, чтобы приступить к работе над проектом. В резуль- тате применения селекторов получается крупная кнопка, представляющая желаемое действие. Код » является сущностью HTML, представляющей две правые угло- вые скобки ( >> ). В точке блок page_header закрывается. Контент на эту страницу добавляться не будет, поэтому определять блок content на этой странице не нужно. Теперь страница выглядит так, как на рис. 20.1. Она смотрится намного лучше по сравнению с проектом без применения оформления. Оформление страницы входа Мы усовершенствовали внешний вид страницы входа, но формы входа изменения пока не коснулись. Приведем внешний вид формы в соответствие с остальными элементами страницы: 462 Глава 20 • Оформление и развертывание приложения login.html {% extends "learning_logs/base.html" %} ❶ {% load bootstrap4 %} ❷ {% block page_header %} Log in to your account. {% endblock page_header %} {% block content %} ❸ {% endblock content %} В точке в шаблон загружаются шаблонные теги bootstrap4 . В точке опреде- ляется блок page_header , который описывает, для чего нужна страница. Обратите внимание: блок {% if form.errors %} удален из шаблона; django-bootstrap4 управ- ляет ошибками формы автоматически. В точке добавляется атрибут , после чего при отображении фор- мы используется шаблонный тег {% bootstrap_form %} ; он заменяет тег {{ form. as_p }} , используемый в главе 19. Шаблонный тег {% booststrap_form %} вставляет правила в стиле Bootstrap в отдельные элементы формы при ее построении. В точ- Рис. 20.2. Страница входа, оформленная с использованием Bootstrap Оформление приложения Learning Log 463ке открывается шаблонный тег bootstrap4 {% buttons %} , который добавляет стилевое оформление Bootstrap к кнопкам. На рис. 20.2 показана форма входа так, как она выглядит сейчас. Страница стала намного чище, ее оформление последовательно, а предназначение предельно ясно. Попробуйте выполнить вход с неверным именем пользователя или паролем; вы увидите, что даже сообщения об ошибках следуют тому же стилю оформления и хорошо интегрируются с сайтом в целом. Оформление страницы со списком тем А теперь позаботимся о том, чтобы страницы для просмотра информации также были выдержаны в том же стиле. Начнем со страницы со списком тем: topics.html {% extends "learning_logs/base.html" %} ❶ {% block page_header %} Topics {% endblock page_header %} {% block content %} {% for topic in topics %} ❷ {{ topic }}
{% empty %} No topics have been added yet. {% endfor %}
❸ Add new topic {% endblock content %} Тег {% load bootstrap4 %} не нужен, потому что в этом файле не используются никакие шаблонные теги bootstrap4 . Заголовок Topics перемещается в блок page_header , и вместо простого абзацного тега ему назначается оформление за- головка . Каждая тема оформляется как элемент , чтобы она выводилась чуть более крупным шрифтом на странице ; то же самое делается со ссылкой добавления новой темы . Оформление записей на странице темы Страница темы содержит больше контента, чем большинство страниц, поэтому над ней придется потрудиться. Чтобы записи визуально выделялись, мы воспользу- емся панелями Bootstrap. Панель (card) представляет собой элемент div с заранее определенным гибким стилем и идеально подходит для отображения записей темы:
464 Глава 20 • Оформление и развертывание приложения topic.html {% extends 'learning_logs/base.html' %} ❶ {% block page_header %} {{ topic }} {% endblock page_header %} {% block content %} Add new entry {% for entry in entries %} ❷ ❸ {{ entry.date_added|date:'M d, Y H:i' }} ❹ edit entry
❺ {{ entry.text|linebreaks }} {% empty %} There are no entries for this topic yet. {% endfor %} {% endblock content %} Сначала тема размещается в блоке page_header . Затем удаляется структура неупорядоченного списка, использовавшаяся ранее в этом шаблоне. Вместо того чтобы превращать каждую запись в элемент списка, мы создаем в точке элемент с селектором card . Он имеет два вложенных элемента: первый предназначен для хранения временной метки и ссылки для редактирования, а второй — для хранения тела записи. Первый элемент в панели представляет собой заголовок — элемент с селек- тором card-header . Заголовок панели содержит дату создания записи и ссылку для ее редактирования. Ссылка edit_entry заключается в тег
, чтобы она была чуть меньше временной метки . Второй элемент представляет собой div с селектором card-body , который размещает текст записи в простом поле на карте. Обратите внимание: код Django для включения информации на страницу не изменился; изменились только элементы, влияющие на внешний вид страницы. На рис. 20.3 изображена страница темы с новым оформлением. Функциональность приложения Learning Log не изменилась, но приложение выглядит более привле- кательно и заманчиво для пользователя. ПРИМЕЧАНИЕ Если вы хотите использовать другой шаблон Bootstrap, действуйте в той же последовательности, которая уже использовалась в этой главе . Скопируйте шаблон в base .html и измените элементы, содержащие контент, чтобы шаблон отобра- жал информацию вашего проекта . Затем воспользуйтесь средствами индивидуального стилевого оформления Bootstrap для оформления содержимого каждой страницы .
Развертывание Learning Log 465 Рис. 20.3. Страница темы с оформлением Bootstrap УПРАЖНЕНИЯ 20.1. Другие формы: мы применили стили Bootstrap к странице login . Внесите аналогич- ные изменения в другие страницы на базе форм: new_topic , new_entry , edit_entry и register 20.2. Стилевое оформление Blog: используйте Bootstrap для стилевого оформления про- екта Blog из главы 19. Развертывание Learning Log После того как проекту был придан профессиональный вид, мы развернем его на реальном сервере, чтобы любой пользователь с подключением к интернету мог работать с приложением. Мы воспользуемся Heroku — веб-платформой, позволя- ющей управлять развертыванием веб-приложений. Создание учетной записи Heroku Чтобы создать учетную запись, откройте сайт https://heroku .com/ и щелкните на одной из регистрационных ссылок. Учетные записи создаются бесплатно, и Heroku предоставляет бесплатный уровень для тестирования проектов в реальных условиях. ПРИМЕЧАНИЕ На бесплатном уровне Heroku существуют свои ограничения (напри- мер, количество приложений, которые можно развернуть, и частота посещения прило- жения пользователями) . Впрочем, эти ограничения достаточно либеральны, чтобы вы могли потренироваться в развертывании приложений без каких-либо затрат .
466 Глава 20 • Оформление и развертывание приложения Установка инструментария Heroku CLI Чтобы развернуть проект на серверах Heroku и управлять им, вам понадобятся инструменты из пакета Heroku Command Line Interface (CLI). Чтобы установить новейшую версию Heroku CLI, откройте сайт https://devcenter .heroku .com/articles/ heroku-cli/ и выполните указания для своей операционной системы. В них содержит- ся либо однострочная терминальная команда, либо программа установки, которую вы можете загрузить и запустить. Установка необходимых пакетов Вам также придется установить три пакета, упрощающих работу проектов Django на реальных серверах. В активной виртуальной среде введите следующие команды: (ll_env)learning_log$ pip install psycopg2==2.7.*(ll_env)learning_log$ pip install django-heroku(ll_env)learning_log$ pip install gunicornПакет psycopg2 необходим для управления базой данных, используемой Heroku. Пакет django-heroku почти полностью управляет конфигурацией, необходимой нашему приложению для нормальной работы на серверах Heroku. К этой категории относится управление базой данных и хранение статических файлов, при котором они будут правильно предоставляться по запросу. Пакет gunicorn — сервер, спо- собный предоставлять доступ к приложениям в реальной среде. Создание файла requirements .txt Heroku необходимо знать, от каких пакетов зависит наш проект, поэтому мы вос- пользуемся pip для построения файла со списком. Оставаясь в активной виртуаль- ной среде, введите следующую команду: (ll_env)learning_log$ pip freeze > requirements.txtКоманда freeze приказывает pip записать имена всех пакетов, в настоящее время установленных в системе, в файл requirements .txt . Откройте файл requirements .txt и просмотрите пакеты и номера версий, установленных в вашей системе: requirements.txtdj-database-url==0.5.0 Django==2.2.0 django-bootstrap4==0.0.7 django-heroku==0.3.1 gunicorn==19.9.0 psycopg2==2.7.7 pytz==2018.9 sqlparse==0.2.4 whitenoise==4.1.2 Развертывание Learning Log 467 Приложение Learning Log уже зависит от восьми разных пакетов с конкретными номерами версий, поэтому для его правильной работы требуется конкретная кон- фигурация среды. (Мы установили четыре из этих пакетов вручную, а четыре были установлены автоматически как зависимости этих пакетов.) При развертывании Learning Log Heroku устанавливает все пакеты, перечислен- ные в requirements .txt , и создает среду с теми же пакетами, которые мы используем локально. По этой причине разработчик может быть уверен в том, что развернутый проект будет работать точно так же, как в его локальной системе. Вы поймете, насколько это полезно, когда начнете строить и вести в своей системе несколько разных проектов. ПРИМЕЧАНИЕ Если пакет включен в список в вашей системе, но номер версии отли- чается от показанного, используйте версию, установленную в вашей системе . Назначение исполнительной среды Python Если вы не укажете версию Python, то Heroku будет использовать собственную версию Python по умолчанию. Убедитесь в том, что Heroku использует ту же вер- сию Python, которая установлена у вас. В активной виртуальной среде введите команду python --version : (ll_env)learning_log$ python --version Python 3.7.2 В этом примере я использую Python 3.7.2. Создайте новый файл с именем runtime . txt в одном каталоге с файлом manage .py и введите следующую команду: runtime.txt python-3.7.2 Этот файл должен содержать одну строку с версией Python, заданной точно в по- казанном формате: python в нижнем регистре, затем дефис и номер версии из трех частей. ПРИМЕЧАНИЕ Если вы получите сообщение об ошибке, в котором сказано, что запра- шиваемая исполнительная среда Python недоступна, откройте страницу https://devcenter . heroku .com/categories/language support/ и найдите ссылку Specifying a Python Runtime . Про- смотрите текст статьи, найдите доступные варианты исполнительной среды и выберите тот вариант, который ближе всего к вашей версии Python . Изменение файла settings .py для Heroku Затем в конец файла settings .py необходимо добавить раздел для определения на- строек, предназначенных конкретно для среды Heroku:
468 Глава 20 • Оформление и развертывание приложения settings.py# Мои настройки LOGIN_URL = 'users:login' # Настройки Heroku import django_heroku django_heroku.settings(locals()) Здесь импортируется модуль django_heroku и вызывается функция settings() . Эта функция изменяет некоторые настройки, которые должны иметь определенные значения для среды Heroku. Создание файла Procfile для запуска процессов Файл Procfile сообщает Heroku, какие процессы должны запускаться для правиль- ной работы проекта. Это однострочный файл, который должен быть сохранен под именем Procfile (символ P верхнего регистра, без расширения) в одном каталоге с файлом manage .py Содержимое Procfile выглядит так: Procfileweb: gunicorn learning_log.wsgi --log-file - Эта строка приказывает Heroku использовать для приложения сервер gunicorn , а при запуске приложения загрузить настройки из файла learning_log/wsgi .py . Флаг log-file сообщает Heroku, какие события должны регистрироваться в журнале. Использование Git для управления файлами проекта Как упоминалось в главе 17, Git — программа контроля версий, которая позволяет создать «мгновенный снимок» состояния кода проекта при реализации каждой новой функции. Это позволяет легко вернуться к последнему работоспособному состоянию проекта при возникновении каких-либо проблем (например, если в ходе работы над новой функцией была случайно внесена ошибка). Если в вашем проекте используется Git, это означает, что вы можете работать над новой функциональностью, не беспокоясь о том, чтобы ничего не нарушить. Раз- вертывая проект на сервере, вы должны убедиться в том, что вы развертываете работоспособную версию проекта. Если вы захотите больше узнать о Git и контроле версий, обращайтесь к приложению Г. Установка Git Возможно, пакет Git уже установлен в вашей системе. Чтобы проверить это, от- кройте новое терминальное окно и введите команду git --version : Развертывание Learning Log 469 (ll_env)learning_log$ git --version git version 2.17.0 Если вы получите сообщение об ошибке, обращайтесь к инструкциям по установке Git в приложении Г. Настройка Git Git следит за тем, кто внес изменения в проект, даже в том случае, если над про- ектом работает только один человек. Для этого Git необходимо знать ваше имя пользователя и адрес электронной почты. Имя пользователя ввести обязательно, но ничто не мешает вам ввести вымышленный адрес электронной почты для учеб- ных проектов: (ll_env)learning_log$ git config --global user.name "ehmatthes" (ll_env)learning_log$ git config --global user.email "eric@example.com" Если вы забудете об этом шаге, Git запросит у вас необходимую информацию при первом закреплении. Игнорирование файлов Нам не нужно, чтобы система Git отслеживала все файлы в проекте, поэтому мы прикажем Git игнорировать некоторые файлы. Создайте файл с именем .gitignore в папке с файлом manage .py . Обратите внимание: имя файла начинается с точки, а файл не имеет расширения. Содержимое .gitignore выглядит так: .gitignore ll_env/ __pycache__/ *.sqlite3 Мы приказываем Git игнорировать весь каталог ll_env , потому что можем автома- тически воссоздать его в любой момент. Также в системе контроля не отслежива- ется каталог __pycache__ с файлами .pyc , которые создаются автоматически, когда Django выполняет файлы .py . Мы не отслеживаем изменения в локальной базе данных, потому что так поступать вообще нежелательно: если на сервере будет использоваться SQLite, вы можете случайно переписать «живую» базу данных локальной тестовой базой данных при отправке проекта на сервер. Звездочка в выражении *.sqlite3 приказывает Git игнорировать любые файлы с расши- рением .sqlite3 ПРИМЕЧАНИЕ Если вы используете macOS, добавьте .DS_Store в файл .gitignore В этом файле хранится информация о настройках папок в macOS, и он не имеет никако- го отношения к этому проекту .
470 Глава 20 • Оформление и развертывание приложения Отображение скрытых файлов Во многих операционных системах файлы и папки, имена которых начинаются с точки (например, .gitignore ), скрываются. Когда вы откроете программу просмотра файлов или попытаетесь открыть файл из такого приложения, как Sublime Text, по умолчанию эти файлы не отображаются. Тем не менее вам как программисту нужно их видеть. Ниже описаны способы отображения скрытых файлов в зависимости от операционной системы: В системе Windows откройте Проводник Windows и папку (например, Рабочий стол ). Щелкните на вкладке Вид и проверьте состояние параметров Показывать скрытые файлы, папки и диски и Скрывать расширения для зарегистрированных типов файлов В macOS нажмите you can press Command Shift . (точка) в любой программе про- смотра файлов, чтобы увидеть скрытые файлы и папки. В системах Linux (таких, как Ubuntu) нажмите Ctrl+H в любой программе про- смотра файлов, чтобы увидеть скрытые файлы и папки. Чтобы этот режим был включен постоянно, откройте программу просмотра файлов (например, Nautilus) и щелкните на вкладке параметров (обозначается тремя линиями). Установите флажок Показывать скрытые файлы Закрепление состояния проекта Чтобы инициализировать репозиторий Git для Learning Log, добавьте все необ- ходимые файлы в репозиторий и закрепите исходное состояние проекта. Вот как это делается: ❶ (ll_env)learning_log$ git init Initialized empty Git repository in /home/ehmatthes/pcc/learning_log/.git/ ❷ (ll_env)learning_log$ git add .❸ (ll_env)learning_log$ git commit -am "Ready for deployment to heroku." [master (root-commit) 79fef72] Ready for deployment to heroku. 45 files changed, 712 insertions(+) create mode 100644 .gitignore create mode 100644 Procfile create mode 100644 users/views.py ❹ (ll_env)learning_log$ git status On branch master nothing to commit, working tree clean (ll_env)learning_log$ В точке вводится команда git init , которая инициализирует пустой репозито- рий в каталоге, содержащем Learning Log. В точке команда git add добавляет все файлы (кроме игнорируемых) в репозиторий (не забудьте точку). В точке вводится команда git commit -am сообщение: флаг -a приказывает Git включить все измененные файлы в закрепленное состояние, а флаг -m приказывает Git сохранить сообщение в журнале. Развертывание Learning Log 471 Вывод команды git status сообщает, что текущей является главная ветвь, а рабо- чий каталог пуст. Этот статус должен выводиться каждый раз, когда вы отправляете свой проект на Heroku. Отправка проекта Наконец-то все готово для отправки проекта на сервер Heroku. В активном терми- нальном сеансе введите следующие команды: ❶ (ll_env)learning_log$ heroku login heroku: Press any key to open up the browser to login or q to exit: Logging in... done Logged in as eric@example.com ❷ (ll_env)learning_log$ heroku create Creating app... done, * secret-lowlands-82594 https://secret-lowlands-82594.herokuapp.com/ | https://git.heroku.com/secret-lowlands-82594.git ❸ (ll_env)learning_log$ git push heroku master remote: -----> Launching... remote: Released v5 ❹ remote: https://secret-lowlands-82594.herokuapp.com/ deployed to Heroku remote: Verifying deploy... done. To https://git.heroku.com/secret-lowlands-82594.git * [new branch] master -> master (ll_env)learning_log$ Сначала войдите на сервер Heroku в терминальном сеансе с именем пользователя и паролем, использованными при создании учетной записи . Затем прикажите Heroku построить пустой проект . Heroku генерирует имя, состоящее из двух слов и числа; позднее вы сможете его изменить. Затем вводится команда git push heroku master , которая приказывает Git отправить главную ветвь проекта в ре- позиторий, только что созданный Heroku. Затем Heroku строит проект на своих серверах с использованием этих файлов. В точке указывается URL, который будет использоваться для обращения к развернутому проекту. После ввода этих команд проект развернут, но еще не настроен полностью. Что- бы проверить, что серверный процесс был запущен правильно, введите команду heroku ps : (ll_env)learning_log$ heroku ps ❶ Free dyno hours quota remaining this month: 450h 44m (81%) Free dyno usage for this app: 0h 0m (0%) For more information on dyno sleeping and how to upgrade, see: https://devcenter.heroku.com/articles/dyno-sleeping ❷ === web (Free): gunicorn learning_log.wsgi --log-file - (1) web.1: up 2019/02/19 23:40:12 -0900 ( 10m ago) (ll_env)learning_log$ В выходных данных указано, сколько еще времени проект может оставаться ак- тивным в следующем месяце . На момент написания книги Heroku позволяет
472 Глава 20 • Оформление и развертывание приложения бесплатно развернутым проектам оставаться активными до 550 часов за месяц. При нарушении этого лимита отображается стандартная серверная страница ошибки; вскоре мы изменим ее. В точке запускается процесс, определенный в Procfile Теперь мы можем открыть приложение в браузере командой heroku open : (ll_env)learning_log$ heroku open (ll_env)learning_log$ Команда избавляет вас от необходимости открывать браузер и вводить URL, который вы получили от Heroku, но при желании сайт можно открыть и так. Вы увидите домашнюю страницу Learning Log с правильным оформлением. Впрочем, с приложением еще работать нельзя, потому что база данных не подготовлена. ПРИМЕЧАНИЕ Процесс развертывания приложений на серверах Heroku время от вре- мени изменяется . Если у вас возникнут неразрешимые проблемы, обращайтесь к доку- ментации Heroku за помощью . Откройте страницу https://devcenter .heroku .com/ и щелкните на ссылке Python, затем найдите ссылку Get Started with Python или Deploying Python and Django Apps on Heroku . Если вы не понимаете то, что там написано, обратитесь к реко- мендациям в приложении В . Подготовка базы данных в Heroku Вы должны выполнить команду migrate , чтобы подготовить базу данных и приме- нить все миграции, сгенерированные в ходе разработки. Для выполнения команд Django и Python в проектах Heroku используется команда heroku run . Пример вы- полнения команды migrate в среде разработки Heroku: ❶ (ll_env)learning_log$ heroku run python manage.py migrate ❷ Running 'python manage.py migrate' on * secret-lowlands-82594... up, run.3060 ❸ Running migrations: Applying learning_logs.0001_initial... OK Applying learning_logs.0002_entry... OK Applying learning_logs.0003_topic_owner... OK Applying sessions.0001_initial... OK (ll_env)learning_log$ Сначала мы вводим команду heroku run python manage.py migrate . Heroku соз- дает терминальный сеанс для выполнения команды migrate . В точке Django применяет миграции по умолчанию, а также миграции, сгенерированные в ходе разработки Learning Log. Теперь при обращении к развернутому приложению вы сможете использовать его так же, как это делалось в локальной системе. Однако при этом вы не увидите никаких данных, введенных при локальном развертывании, потому что мы не скопировали данные на сервер. Это обычная практика: локальные данные почти никогда не копируются на сервер, потому что они чаще всего являются тестовыми.
Развертывание Learning Log 473Если вы перешлете ссылку на Heroku, получатель сможет работать с вашей верси- ей приложения Learning Log. В следующем разделе мы выполним еще несколько операций, чтобы завершить процесс развертывания и подготовиться к дальнейшей разработке Learning Log. Доработка развернутого приложенияВ этом разделе мы доработаем развернутое приложение и создадим суперпользова- теля (так же, как это было сделано в локальной версии). Заодно мы повысим уро- вень защиты проекта, переведя настройку отладочного режима DEBUG в состояние False , чтобы пользователи не получали в сообщениях об ошибке дополнительной информации, которая может использоваться для проведения атак на сервер. Создание суперпользователя в Heroku Вы уже видели, что для выполнения одиночных команд может использоваться команда heroku run . Однако команды также можно выполнять, открыв терми- нальный сеанс Bash при подключении к серверу Heroku командой heroku run bash Bash — язык, который работает во многих терминалах Linux. Мы используем тер- минальный сеанс Bash для создания суперпользователя, чтобы иметь возможность обратиться к административному сайту в развернутом приложении: (ll_env)learning_log$ heroku run bash Running 'bash' on * secret-lowlands-82594... up, run.9858 ❶ $ ls learning_log learning_logs manage.py Procfile requirements.txt runtime.txt staticfiles users ❷ $ python manage.py createsuperuser Username (leave blank to use 'u47318'): ll_admin Email address: Password: Password (again): Superuser created successfully. ❸ $ exit exit (ll_env)learning_log$ В точке команда ls выводит информацию о файлах и каталогах, существующих на сервере; это те же файлы, которые присутствуют в нашей локальной системе. В этой файловой системе можно перемещаться так же, как и в любой другой. ПРИМЕЧАНИЕ Пользователи Windows должны использовать те же команды (напри- мер, ls вместо dir), потому что они работают с терминалом Linux через удаленное подключение . В точке выполняется команда создания суперпользователя. Она выдает тот же вывод, который был получен в локальной системе при создании суперпользовате- ля в главе 18. После того как создание суперпользователя в терминальном сеансе 474 Глава 20 • Оформление и развертывание приложения будет завершено, введите команду exit для возвращения к терминальному сеансу локальной системы . Теперь вы можете добавить /admin/ в конец URL-адреса развернутого приложения, чтобы войти на административный сайт. У меня этот URL-адрес имеет вид https:// secret-lowlands-82594 .herokuapp .com/admin/ Если другие пользователи уже начали работать с вашим проектом, учтите, что вам будут доступны все их данные! Относитесь к конфиденциальности серьезно, и пользователи начнут доверять вам свои данные. Создание удобного URL-адреса на Heroku Вероятно, вы бы предпочли использовать более удобные и запоминающиеся URL- адреса, чем https://secret-lowlands-82594 .herokuapp .com/ . Чтобы переименовать при- ложение, достаточно одной команды: (ll_env)learning_log$ heroku apps:rename learning-log Renaming secret-lowlands-82594 to learning-log-2e... done https://learning-log.herokuapp.com/ | https://git.heroku.com/learning-log.git Git remote heroku updated * Don't forget to update git remotes for all other local checkouts of the app. (ll_env)learning_log$ Имя может содержать буквы, цифры и дефисы и выбирается произвольно (при условии, что никто другой еще не занял это имя). Развернутая версия теперь до- ступна по адресу https://learning-log .herokuapp .com/ . По предыдущему URL-адресу проект теперь недоступен; команда apps:rename полностью перемещает проект на новый URL-адрес. ПРИМЕЧАНИЕ При развертывании проекта на бесплатном сервисе Heroku переводит развернутое приложение в спящий режим, если оно не получало запросов в течение определенного периода времени или было слишком активным для бесплатного уровня . При первом обращении к сайту после перехода в спящий режим загрузка займет больше времени, но последующие запросы будут обрабатываться быстрее . Такой подход позво- ляет Heroku предоставлять бесплатное развертывание . Безопасность проекта В текущем варианте развертывания проекта существует одна очевидная про- блема: настройка DEBUG=True в файле settings .py , включающая вывод отладочных сообщений при возникновении ошибок. Страницы ошибок Django предоставляют критическую отладочную информацию при разработке проекта, но они также дают слишком много информации хакерам, если оставить их включенными на рабочем сервере. Для управления выводом отладочной информации на работающем сайте исполь- зуется переменная среды, то есть значение, связанное с конкретной рабочей средой.
Развертывание Learning Log 475Это один из способов хранения конфиденциальной информации на сервере, при котором она отделяется от остального кода проекта. Изменим файл settings .py , чтобы он проверял переменную среды при запуске про- екта на Heroku: settings.py# Настройки Heroku import django_heroku django_heroku.settings(locals()) if os.environ.get('DEBUG') == 'TRUE': DEBUG = True elif os.environ.get('DEBUG') == 'FALSE': DEBUG = False Метод os.environ.get() читает значение, связанное с заданной переменной среды в любом окружении, в котором выполняется проект. Если запрашиваемая пере- менная задана, метод возвращает ее значение; если она не задана, метод возвращает None . Использование переменной среды для хранения логических значений может привести к путанице. В большинстве случаев переменные среды хранятся в стро- ках, и вы должны действовать внимательно. Рассмотрим следующий фрагмент простого терминального сеанса Python: >>> bool('False')True В логическом контексте строка 'False' интерпретируется как True , потому что лю- бая непустая строка интерпретируется как Tru e. По этой причине мы использовали строки 'TRUE' и 'FALSE' , записанные в верхнем регистре, чтобы четко показать, что мы не сохраняем логические значения True и False языка Python. Когда Django читает переменную среды с ключом 'DEBUG' в Heroku, мы присваиваем DEBUG зна- чение True , если переменная содержит 'TRUE' , или значение False , если переменная содержит 'FALSE' Закрепление и отправка изменений Теперь изменения, внесенные в settings .py , необходимо закрепить в репозитории Git, а затем отправить их на Heroku. Следующий терминальный сеанс показывает, как это делается: ❶ (ll_env)learning_log$ git commit -am "Set DEBUG based on environment variables." [master 3427244] Set DEBUG based on environment variables. 1 file changed, 4 insertions(+) ❷ (ll_env)learning_log$ git status # On branch master nothing to commit, working directory clean (ll_env)learning_log$ 476 Глава 20 • Оформление и развертывание приложения Мы вводим команду git commit с коротким, но содержательным сообщением . Напомню, что флаг -am обеспечивает закрепление всех изменившихся файлов и регистрацию сообщения в журнале. Git видит, что изменился один файл, и за- крепляет изменение в репозитории. В точке из статусной информации видно, что мы работаем с главной ветвью репо- зитория, а новые изменения для закрепления отсутствуют. Очень важно проверять статусную информацию перед отправкой на Heroku. Если вы не видите сообщение, значит, некоторые изменения не были закреплены и они не будут отправлены на сервер. Попробуйте снова ввести команду commit , а если вы не уверены в том, как ре- шить проблему, — прочитайте приложение Г, чтобы лучше понять, как работать с Git. Теперь отправим обновленный репозиторий на Heroku: (ll_env)learning_log$ git push heroku masterremote: Building source: remote: remote: -----> Python app detected remote: -----> Installing requirements with pip remote: -----> Launching... remote: Released v6 remote: https://learning-log.herokuapp.com/ deployed to Heroku remote: remote: Verifying deploy... done. To https://git.heroku.com/learning-log.git 144f020..d5075a1 master -> master (ll_env)learning_log$ Heroku видит, что репозиторий обновился, и заново строит проект, чтобы все из- менения были учтены. База данных при этом не воссоздается, поэтому выполнять migrate для этого обновления не придется. Назначение переменных среды в Heroku Теперь можно задать нужное значение DEBUG в файле settings .py через Heroku. Коман да heroku config:set задает значение переменной за нас: (ll_env)learning_log$ heroku config:set DEBUG='FALSE'Setting DEBUG and restarting * learning-log... done, v7 DEBUG: FALSE (ll_env)learning_log$ Каждый раз, когда вы задаете переменную среды в Heroku, проект автоматически перезапускается, чтобы переменная среды могла начать действовать. Чтобы убедиться в том, что развернутое приложение стало более безопасным, введите URL проекта с путем, который не был определен. Например, попробуйте открыть страницу http://learning-log .herokuapp .com/letmein/ . Должна появиться обоб- щенная страница, которая не сообщает никакой конкретной информации о проекте. Развертывание Learning Log 477Если же вы попробуете применить тот же запрос с локальной версией Learning Log по адресу http://localhost:8000/letmein/ , должна появиться полная страница ошибки Django. Получается именно то, что нужно: вы будете получать содержательные сообщения об ошибках в процессе разработки проекта, но оградите пользователей от критической информации о коде проекта. Если вы только развертываете приложение и проводите диагностику исходного развертывания, выполните команду heroku config:set DEBUG='TRUE' , и вы временно сможете просматривать полный отчет об ошибке для работающего сайта. Только не забудьте вернуть переменной значение 'FALSE' , завершив диагностику. Также постарайтесь не делать этого после того, как пользователи начнут регулярно об- ращаться к вашему сайту. Создание специализированных страниц ошибок В главе 19 мы настроили приложение Learning Log так, чтобы при запросе темы или записи, которая ему не принадлежит, пользователь получал ошибку 404. Вероятно, вы также сталкивались с примерами ошибок 500 (внутренние ошибки). Ошибка 404 обычно означает, что код Django правилен, но запрашиваемый объект не существует; ошибка 500 обычно означает, что в написанном вами коде существует ошибка (на- пример, ошибка в функции из views .py ). В настоящее время Django возвращает одну обобщенную страницу ошибки в обеих ситуациях, но мы можем написать собствен- ные шаблоны страниц ошибок 404 и 500, которые соответствуют общему оформле- нию Learning Log. Эти шаблоны должны находиться в корневом каталоге шаблонов. Создание пользовательских шаблонов В папке learning_log/learning_log создайте новую папку с именем templates . Затем создайте новый файл с именем 404 .html ; полное имя файла имеет вид learning_log/ templates/404 .html . Код файла выглядит так: 404.html{% extends "learning_logs/base.html" %} {% block page_header %} |