Вы когда-нибудь забывали о дне рождения друга? Это случается с каждым. После того как я устал ежедневно проверять Facebook на предмет дней рождения, мне захотелось создать более удобную систему push-уведомлений с улучшенными фильтрами.
Я написал статью «Создание простого приложения для дней рождения с Flask-SQLAlchemy», в которой показал, как экспортировать календарь дней рождений из Facebook в файл .ics и импортировать его в базу данных с помощью Flask и Flask-SQLAlchemy.
После общения с Twilio на PyCon мы подумали, что было бы здорово расширить это приложение, добавив SMS-уведомления и возможность отправлять поздравительные сообщения через SMS. Поэтому я зарегистрировался в Twilio и начал кодить.
В этой статье мы создадим простое приложение для дней рождений с использованием Python, Flask и API программируемых SMS-сообщений Twilio, чтобы вы больше никогда не пропустили день рождения:
Далее создайте виртуальное окружение и установите зависимости:
Обновите файл переменных окружения `env.conf` с корректными настройками:
— flask – secret = установите сложную для угадывания строку (документация Flask)
— twilio_api – sid token = получен на шаге 3
— phones – twilio = получен на шаге 3
— phones – admin = ваш (верифицированный) номер мобильного телефона, на который вы хотите получать уведомления
— login – user password = ваши учетные данные для входа в приложение Flask
— server – url = оставьте без изменений, если запускаете локально, или обновите базовый URL при развертывании на сервере
ПРИМЕЧАНИЕ: убедитесь, что вы используете формат номеров E.164 для телефонов (например, +34666555444, +442071838750). См. статью поддержки Twilio: Форматирование международных номеров телефонов.
Приложение использует configparser для загрузки этих настроек.
Импортируйте календарь дней рождений из Facebook в локальную базу данных SQLite:
— Экспортируйте календарь дней рождений из Facebook и сохраните его как `cal.ics` в корневой директории приложения.
— Запустите model.py, чтобы импортировать дни рождения в базу данных. Здесь я использую опцию -t для замены настоящих имен на вымышленные с помощью Faker. Для реального использования опустите -t:
Убедитесь, что ваше виртуальное окружение активировано. Это приложение состоит из двух частей: фронтенд на Flask и ежедневный cron-скрипт на бэкенде.
Фронтенд — это приложение Flask, которое можно запустить командой: `python app.py`.
На этом этапе перейдите по адресу 127.0.0.1:5000, и вы увидите дни рождения своих друзей. Как мы увидим чуть позже, вам нужно добавить номер телефона для каждого друга, о дне рождения которого вы хотите получать уведомления.
Уведомление — это ежедневный cron-скрипт, который проверяет дни рождения с установленным номером телефона. Он отправляет SMS-уведомления на административный телефон, указанный в настройках. Этот скрипт должен работать в фоновом режиме, поэтому используйте инструмент вроде nohup:
Весь код приложения Flask находится в `app.py`. Поскольку вы, вероятно, захотите разместить его в облаке, аутентификация предусмотрена с самого начала.
Это реализовано с помощью декоратора login_required для всех приватных маршрутов. При входе в приложение сначала необходимо авторизоваться. Здесь я использую ngrok для тестирования локального приложения:
После входа вы увидите список импортированных друзей и их дни рождения. Простой CSS выделяет сегодняшние дни рождения:
Вы можете перемещаться по друзьям с помощью вкладок и через поисковую строку:
Приложение использует Flask-SQLAlchemy для взаимодействия с базой данных, с одной таблицей для хранения дней рождений. Модель определена в model.py, который мы использовали ранее для загрузки данных. Вот часть, определяющая структуру таблицы:
ПРИМЕЧАНИЕ: чтобы отправлять сообщения друзьям с помощью бесплатной версии Twilio, сначала необходимо верифицировать их номера телефонов. Это ограничение можно снять, обновив аккаунт. Подробнее об этом здесь.
Различные правила валидации установлены в соответствующем маршруте `/friends/`. Например, нельзя использовать один и тот же номер телефона дважды.
После добавления номера телефона вы будете получать SMS-уведомление в день рождения друга.
Cron-задание запрограммировано в `notify.py` с использованием пакета schedule для уведомлений о днях рождения, приходящихся на текущий день.
Оно запрашивает базу данных с помощью Flask-SQLAlchemy, получая дни рождения на текущий день:
Запуск cron-задания вручную:
Поскольку это задание будет выполняться на удаленном сервере, текущая версия приложения использует логирование вместо вывода в stdout. Как уже упоминалось, используйте nohup для запуска в фоновом режиме. Модуль schedule сделает все остальное:
А вот и SMS-уведомление о сегодняшнем дне рождении:
Ссылка ведет на точку входа в приложение Flask для отправки поздравительного сообщения или SMS-открытки, о чем мы поговорим в следующем разделе.
###
Отправка поздравительных сообщений и открыток
Это вторая часть приложения. Есть два способа попасть в раздел *отправки сообщения*: перейти по ссылке в SMS или нажать на значок телефона слева от имени друга на главной странице.
Перед вами появится следующая форма:
Действует валидация, позволяющая отправлять сообщения только тому человеку, у которого сегодня день рождения:
Теперь вы можете отправить текстовое сообщение и включить ссылку на изображение:
Если вы добавите ссылку на изображение, библиотека Pillow будет использована для наложения текста на изображение, создавая простую поздравительную открытку. Код для этого находится в модуле text_on_image.py.
Когда вы нажмете *проверить*, вы сможете убедиться, что результат вас устраивает:
Гэри получит SMS следующего содержания:
Это на iPhone. На Android изображение не отображается встроенно. По этой причине текст отправляется вместе с изображением.
Управление приложением для дней рождений через SMS — это круто. API Twilio делает это очень простым. Интеграция изображений с помощью Pillow была самой сложной частью создания этого приложения.
Разделение кода на различные модули помогло и будет помогать управлять сложностью. В будущем было бы хорошо добавить набор регрессионных тестов и, возможно, автоматизировать сквозное тестирование с помощью инструмента вроде Selenium.
И наконец, ничто не сравнится с созданием практических приложений, когда речь идет о совершенствовании навыков программирования. Помимо API Twilio, работая над этим приложением, я узнал больше о Flask и интеграции различных интересных модулей.
Присоединяйтесь к нашему Twilio PyBites код-челленджу, чтобы создать собственное приложение для автоматической отправки сообщений и другие классные приложения каждую неделю.
Если у вас есть вопросы или комментарии, не стесняйтесь обращаться:
Я Боб Белдербос из PyBites, вы можете связаться со мной по:
— Email: pybitesblog@gmail.com
— Twitter: https://twitter.com/pybites
— GitHub: https://github.com/pybites