Розробка API на Python із Serverless

У попередній статті я показавши, як можна взаємодіяти з безсерверною платформою AWS Lambda лише засобами, наданими Amazon. Це був корисний експеримент — раджу так робити з будь-якою новою технологією чі системою, яку бажаєте вивчити. Починайте з найпростішого і спробуйте збудувати проект, не застосовуючи надто багато додаткових інструментів чи абстракцій, — так ви ліпше зрозумієте як працює базова система і з якими неприємностями, труднощами чи випадками, що вимагатимуть шаблонного коду, ви стикнетеся. Щойно побачите, як все працює, ви значно глибше зрозумієте абстракції, які лежати на поверхні, оскільки матимете уявлення про ті, як вони влаштовані, які проблеми розв'язків язують і яких складнощів дозволяють уникнути.

AWS має потужні служби, які, втім, потрібно відповідним чином поєднувати, щоб досягти потрібного результату. По суті, вони є модулями, які мають певну функціональність, але мають бути якось об єднані в єдине ціле, щоб ними було дійсно зручно користуватися. На щастя, платформа підтримує скрипти, і вже з'єднання являється додатковий софт і шарі абстракцій, що спрощують для програмістів самостійне керування налаштуваннями, не вдаючись до посередництва додаткових апаратних засобів чи людей. CloudFormation (CF) дає змогу описувати інфраструктуру за допомогою JSON або YAML.

Завдяки шаблонам CF на зразок serverless і трансформаціям CodeStar, вам знадобиться значно менше коду, щоб описати безсерверну конфігурацію у CloudFormation. А такі інструменти як Serverless додають іще один рівень автоматизації, полегшуючи роботу розробникам. Amazon тут не пасе задніх, пропонуючи інструментарій навіть вищого рівня, який має назву Amplify (про нього розповім у наступних дописах) і дає змогу іще більше автоматизувати роботу із залученням апаратних та програмних засобів.

Інструментарій Serverless

Погравшись трохи з AWS SAM і трансформацією serverless для CF, я швидко відчув певні недоліки відмови від складнішої системи для автоматизації:

  1. Перегляд логів. Переглядати логи CloudWatch в консолі AWS — не найліпший спосіб стежити в реальному часі (та й узагалі) за тім, що ваш додаток видає на виході.
  2. Було незрозуміло, як зберегти деякі складники архітектури безсерверного додатку для повторного використання в інших проектах. Я поцікавився у розсилці Flask і на його IRC-каналі, як реалізувати цє в розширенні — і жодної путньої відповіді не отримав.
  3. Визначення промов на зразок шлюзів API, сховищ S3 для кодом і доменів засобами CF — марудна праця. Її можна автоматизувати більшою мірою.
  4. Було б чудово отримувати одразу якусь інформацію щодо розгорнутого додатку, як-від його URL-адресою.
  5. Розгортання, включно з розгортаннями до різних стадій.
  6. Сповіщення про закінчення розгортання, особливо в разі використання CodeStar.
  7. Виклик функцій для тестування і засобами автоматизації.
  8. Керування залежностями.

І деякі інші аспекти, наприклад відстежування коректності профілю налаштування AWS й регіону.

Як часто трапляється у сфері інформаційних технологій, я не перший, хто стикнувся з цими проблемами, і дехто вже потурбувався про їх розв'язків язання.

Є такий інструментарій Serverless — не сказати, що назва додає ясності в обговорення недавньої тенденції використовувати безсерверні архітектури додатків, де вже маємо, наприклад, прикметник serverless, безсерверну модель додатку (Serverless Application Model (SAM)) і CF-трансформацією serverless для AWS.

Serverless допоможе впоратися з усіма переліченими вище проблемами. З огляду на мій недавній досвід, гадаю, продовжувати розробка безсерверних додатків без нього було б марною тратою часу й зусиль. Звісно, якщо ви не початківець і не маєте на меті опанувати основи.

Не буду описувати тут як починати роботу з Serverless , про це можна почитати його сайті. Тут нічого складного немає, особливо якщо у вас вже налаштовані реквізити AWS. Роздивімося краще переваги, які він надає:

Логування

Тут усе просто. Продивитися всі чи кілька останніх записів у файлах логів можна так:

sls logs -f myfunction -t

Повторне використання коду

# Створити Flask-додаток на основі шаблону
sls install --url https://github.com/revmischa/serverless-flask --name myapp

Дехто ще пішов шляхом Create-React-App і створив шаблони Serverless-проектів, до яких можна отримати доступ за допомогою команди «sls install». З одного боці, це значно спрощує створення й розповсюдження готових рішень і залишає можливість для розгалуження упродовж розвитку шаблонів. Альо з іншого — додавати нові поліпшення до проектів на основі старих шаблонів стає значно складніше. Оскільки йдеться про Flask і Python, навряд самих лише шаблонів вистачить, щоб розв'язків зв'язати цю проблему. Потрібен іще якийсь модуль для Python, який буде розвиватися паралельно. Було б чудово, якщо б це було щось аналогічне до пакету react-scripts, який співіснує з Create-React-App.

Налаштування і CloudFormation

Тепер оголошувати ресурси й функції можна у файлі налаштувань serverless.yml . Туди ж можна додати ще купу корисного .

Майже весь шаблонний код, який потрібен CF для налаштування всіх аспектів безсерверного додатку (сховища S3 для кодом, IAM-дозволів для виклику і CloudWatch, API Gateway тощо) від вас схований — ним більше не треба перейматися. Від вас потрібні лише мінімальна конфігурація та CF, щоб описати те, що потрібно саме для вашого випадку. За шкалою зручності від sendmail.conf до .emacs, serverless.yml є доволі близьким до останнього.

Інформація

Тут усе просто. Де я там запаркував свій домен?

 $ sls info
Service Information
service: myapp
stage: dev
region: eu-central-1
stack: myapp-dev
api keys:
None
endpoints:
 ANY - https://di1baaanvc.execute-api.eu-central-1.amazonaws.com/dev
 ANY - https://di1baaanvc.execute-api.eu-central-1.amazonaws.com/dev/{proxy+}
 GET - https://di1baaanvc.execute-api.eu-central-1.amazonaws.com/dev/openapi
functions:
 app: myapp-dev-app
 openapi: myapp-dev-openapi
Serverless Domain Manager Summary
Domain Name
myappmyapp.net
Distribution Domain Name
dcwyw3gslhqw1.cloudfront.net

Розгортання

Тут теж все просто, навіть занадто просто!

$ sls deploy
$ sls deploy -s prod # specify stage

Ця команда збирає залежності, створює пакет служби, завантажує його у сховище S3 і запускає оновлення стеку CloudFormation.

Бачите розділ «Serverless Domain Manager Summary» (Короткі відомості для диспетчера доменів для безсерверних додатків)? Це налаштування плагіну serverless-domain-manager. Якщо вам потрібно розгорнути кінцеві точки під доменним ім'я ям у зоні Route53 (сподіваюся, ви вже маєте ACM-сертифікат для регіону us-west-1), Serverless може автоматично прикріпити домен або піддомен, створити дистрибутив CloudFront і виконати зіставлення домену з API Gateway.

Плагін обирає ACM-certificate для вашого домену випадково з переліку збігів серед доменних імен, і це призвело до однієї проблеми: він обирав сертифікат з вичерпаним терміном дії. Тому довелося дещо виправити, щоб відфільтрувати проблемні сертифікати. І мій запит на внесення виправлень до коду плагіну одразу задовольнили . Приємно, коли так трапляється.

Очікування/Сповіщення

Після виконання згаданої вище команди розгортання ви отримаєте сповіщення. Потім одразу можна переходіті до тестування. Щоб прискорити процес, можна розгорнути лише певну функцію, або скористатися опцією пришвидшення передачі даних (Transfer Acceleration) сховища S3, щоб пришвидшити завантаження ваших кунштиків. І ніякого марнування часу, розгортаючи непотрібні вам речі або роздивляючись веб-інтерфейс CodeStar.

Виклик функцій

Як і в AWS SAM, у Serverless немає нічого складного. Якщо ви пишете веб-додаток з використанням плагіну serverless-wsgi, його можна також обслуговувати локально.
Керування залежностями

(Ця частина стосується Python)

Як керувати залежностями вашої «лямбда» з кодом на Python? Просто записати їх у файл requirements.txt. Очевидно, її ж? У всякому разі, із Serverless це більш-менш так. Також не забувайте, що всі залежності мають міститися у zip-файлі вашої «лямбда». Треба скомпілювати залежності в бінарники, а поряд немає 64-бітної linux-машини? Просто додайте рядок «dockerizePip: "true»до налаштувань плагіну serverless-python-requirements у файлі serverless.yml.

Зверніть увагу: якщо вам треба викликати функцію локально або запустити WSGI-сервер, доведеться створити локальні віртуальне оточення. Якось мені трапився дивний шаблон — він не мав стосунку до Serverless, — в якому керування локальними залежностями й залежностями «лямбда» було реалізовано за допомогою pipenv. Не найкращий варіант, не раджу так робити.

Розширення функціональності Serverless

Я користуюся AWS Lambda здебільшого коли пишу невеличкі Web API-служби на Python з використанням мікрофреймворка Flask. Serverless надає мені потрібні інструменти, але хочу мати вже готові підвалини для свого додатку, щоб додатково спростити створення нових проектів.

Отже, я зробив форк шаблоном serverless-flask і дещо його переробив . Зробив так, щоб він більше не питав, чи у вас Python 2 або 3 (чому б краще не питати хочу я UTF-8 або EBCDIC?) і усталено вимкнув докерування pip.

Створюючи API-сервер на основі Flask, можна полегшити собі життя, додавши marshmallow для виконання серіалізації та десеріалізації запитів, flask-apispec для інтеграції marshmallow з OpenAPI (Swagger) і Flask, а також CORS . У моїй версії шаблону це все потрібно, щоб спростити наскільки можливо створення документованого REST API засобами Python і Serverless найменшими зусиллями та з мінімумом написання коду. У якості бонусу він генерує клієнтські бібліотеки для вашого API на основі визначення OpenAPI будь-якою зручною для вас мовою програмування.

Інструкції з використання шаблону й швидкого початку роботи з ним шукайте тут .

Serverless? Чому б і ні

Цей допис — друга віха в нашій подорожі. Поліпшення процесу написання додатків та служб — це тривалий процес. Минулого разу ми розглядали служби AWS окремо, а в цьому дописі зосередитися на допоміжному інструментарії. Логічним наступним кроком могли б стати AWS Amplify та GraphQL. А може й ні. Стежте за оновленнями.

Читати першу частину статті

Опубліковано: 23/08/19 @ 10:00
Розділ Різне

Рекомендуємо:

Як Live Animations створили AR-контент для книги Alif and Sofia, яка вчить мусульманських дітей молитися
Країна сієсти: подружжя українських програмістів про переїзд на Мальту й причини повернення додому
ML для мобільного розробника: Google Cloud для тренування ML-моделі
QA дайджест #38: техніки тестування, генерація реалістичних тестових даних, мобільне тестування
Безсерверні веб-застосунки на Python з використанням Lambda і Flask