Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Zappa, Chalice и друзья: запускаем код без серверов с помощью AWS Lambda

Zappa, Chalice и друзья: запускаем код без серверов с помощью AWS Lambda

Михаил Новиков (fstrk.io) @ MoscowPython Meetup 69

"Технологии Serverless несколько лет, и с каждым годом её популярность растет. Для высоконагруженных систем это простой способ бесконечного масштабирования, а для простых сайд-проектов - это отличная возможность бесплатного хостинга. Принцип в том, что вы деплоите не вебсервер, а функции, и платите только за время выполнения этих функций (обычно это миллисекунды).
В докладе мы рассмотрим, как устроены эти функции, какие есть инструменты для их создания - и зачем это обычному питонисту. Также мы увидим, как деплоить уже готовые приложения на Django и Flask в serverless-режиме."

Видео: http://www.moscowpython.ru/meetup/69/zappa-chalice-and-friends/

Moscow Python Meetup
PRO

October 30, 2019
Tweet

More Decks by Moscow Python Meetup

Other Decks in Programming

Transcript

  1. Zappa, Chalice и
    друзья
    Запускаем код без
    серверов с помощью AWS
    Lambda
    Михаил Новиков
    Founder & Dev Lead, fstrk.io
    "Пишу чатботов на джанго" (c)
    @nooovikov 1

    View Slide

  2. План
    @nooovikov 2

    View Slide

  3. План
    1. Что такое Serverless / FaaS ?
    @nooovikov 2

    View Slide

  4. План
    1. Что такое Serverless / FaaS ?
    2. Где это может пригодиться?
    @nooovikov 2

    View Slide

  5. План
    1. Что такое Serverless / FaaS ?
    2. Где это может пригодиться?
    3. Как деплоить Serverless
    @nooovikov 2

    View Slide

  6. План
    1. Что такое Serverless / FaaS ?
    2. Где это может пригодиться?
    3. Как деплоить Serverless
    4. Ограничения и хаки
    @nooovikov 2

    View Slide

  7. План
    1. Что такое Serverless / FaaS ?
    2. Где это может пригодиться?
    3. Как деплоить Serverless
    4. Ограничения и хаки
    5. Цены
    @nooovikov 2

    View Slide

  8. План
    1. Что такое Serverless / FaaS ?
    2. Где это может пригодиться?
    3. Как деплоить Serverless
    4. Ограничения и хаки
    5. Цены
    6. Отечественный Serverless
    @nooovikov 2

    View Slide

  9. 1. Что такое Serverless / FaaS ?
    @nooovikov 3

    View Slide

  10. 1. Что такое Serverless / FaaS ?
    • Деплоим код, не разворачивая сервера
    @nooovikov 3

    View Slide

  11. 1. Что такое Serverless / FaaS ?
    • Деплоим код, не разворачивая сервера
    • Платим только за время обработки запросов
    @nooovikov 3

    View Slide

  12. 1. Что такое Serverless / FaaS ?
    • Деплоим код, не разворачивая сервера
    • Платим только за время обработки запросов
    • Не храним стейт в функции (внешняя БД, внешний кэш,
    авторизация и пр.)
    @nooovikov 3

    View Slide

  13. 1. Что такое Serverless / FaaS ?
    • Деплоим код, не разворачивая сервера
    • Платим только за время обработки запросов
    • Не храним стейт в функции (внешняя БД, внешний кэш,
    авторизация и пр.)
    • Не занимаемся (кое-чем) с инфраструктурой
    @nooovikov 3

    View Slide

  14. @nooovikov 4

    View Slide

  15. Простое объяснение
    @nooovikov 5

    View Slide

  16. Философское объяснение
    Код - "клей" для инфраструктуры
    @nooovikov 6

    View Slide

  17. 2. Где это может пригодится?
    @nooovikov 7

    View Slide

  18. 2. Где это может пригодится?
    • ⚡ Вебхуки, интеграции
    @nooovikov 7

    View Slide

  19. 2. Где это может пригодится?
    • ⚡ Вебхуки, интеграции
    • " API & микросервисы
    @nooovikov 7

    View Slide

  20. 2. Где это может пригодится?
    • ⚡ Вебхуки, интеграции
    • " API & микросервисы
    • # ETL-пайплайны
    @nooovikov 7

    View Slide

  21. 2. Где это может пригодится?
    • ⚡ Вебхуки, интеграции
    • " API & микросервисы
    • # ETL-пайплайны
    • $ Бэкенды для ботов, SPA
    @nooovikov 7

    View Slide

  22. 2. Где это может пригодится?
    • ⚡ Вебхуки, интеграции
    • " API & микросервисы
    • # ETL-пайплайны
    • $ Бэкенды для ботов, SPA
    • % IoT
    @nooovikov 7

    View Slide

  23. Где это нельзя использовать
    @nooovikov 8

    View Slide

  24. Где это нельзя использовать
    • ⏳ Длинные задачи (напр. получасовой парсинг сайта)
    @nooovikov 8

    View Slide

  25. Где это нельзя использовать
    • ⏳ Длинные задачи (напр. получасовой парсинг сайта)
    • " Приложения с большим кол-вом зависимостей
    @nooovikov 8

    View Slide

  26. Где это нельзя использовать
    • ⏳ Длинные задачи (напр. получасовой парсинг сайта)
    • " Приложения с большим кол-вом зависимостей
    • # Приложения, хранящие в себе стейт
    @nooovikov 8

    View Slide

  27. 3. Как деплоить
    @nooovikov 9

    View Slide

  28. 3.1. Деплой в интерфейсе AWS
    @nooovikov 10

    View Slide

  29. Шаг 1. Пишем функцию
    @nooovikov 11

    View Slide

  30. Шаг 2. Добавляем API к функции
    @nooovikov 12

    View Slide

  31. Это удобно?
    @nooovikov 13

    View Slide

  32. Это удобно?
    • Нет!
    @nooovikov 13

    View Slide

  33. Это удобно?
    • Нет!
    • Нет контроля версий
    @nooovikov 13

    View Slide

  34. Это удобно?
    • Нет!
    • Нет контроля версий
    • Сложности с зависимостями (в
    Lambda нельзя сделать pip
    install)
    @nooovikov 13

    View Slide

  35. Это удобно?
    • Нет!
    • Нет контроля версий
    • Сложности с зависимостями (в
    Lambda нельзя сделать pip
    install)
    • Код либо пишешь в редакторе,
    либо загружаешь в ZIP-архиве
    @nooovikov 14

    View Slide

  36. Нам нужен фреймворк:
    @nooovikov 15

    View Slide

  37. Нам нужен фреймворк:
    • Чтобы работать в своем уютном IDE
    @nooovikov 15

    View Slide

  38. Нам нужен фреймворк:
    • Чтобы работать в своем уютном IDE
    • Чтобы zip-архивы сами загружались в облако
    @nooovikov 15

    View Slide

  39. Нам нужен фреймворк:
    • Чтобы работать в своем уютном IDE
    • Чтобы zip-архивы сами загружались в облако
    • Чтобы решались проблемы с зависимостями
    @nooovikov 15

    View Slide

  40. 3.2. Деплой с Serverless Framework
    https://serverless.com/
    @nooovikov 16

    View Slide

  41. Serverless
    Framework
    • YML конфиг позволяет не
    касаться админки AWS
    • Деплой одной командой
    • Можно настроить ВСЁ
    • Много доков и примеров
    • Есть энтерпрайз версия! !
    @nooovikov 17

    View Slide

  42. Но...
    Он написан на Node.js. !
    npm install serverless
    npm install serverless-python-requirements
    @nooovikov 18

    View Slide

  43. 3.3. Деплой с Chalice
    • Написан на питоне
    • Поддерживается амазоном:
    https://github.com/aws/chalice
    • Еще проще деплоить
    • Очень амбициозное название
    @nooovikov 19

    View Slide

  44. @nooovikov 20

    View Slide

  45. Странности Chalice
    API похож на Flask, но не совсем:
    @app.route('/')
    def view():
    # request нужно доставать из аппы
    request = app.current_request
    # получение JSON-пейлоада
    body = request.json_body
    # получение GET-параметров
    params = requst.query_params
    @nooovikov 21

    View Slide

  46. Странности Chalice
    Заявляет, что поддерживает вебсокеты, но это не заводится:
    app = Chalice(app_name="echo-server")
    app.websocket_api.session = Session()
    app.experimental_feature_flags.update(['WEBSOCKETS'])
    @app.on_ws_message()
    def message(event):
    app.websocket_api.send(
    connection_id=event.connection_id,
    message=event.body
    )
    @nooovikov 22

    View Slide

  47. Странности Chalice
    • Требует все файлы класть в папку chalicelib
    • Некоторые зависимости пакует автоматически, а
    некоторые - нет
    • chalice logs выдает ВСЕ логи за всю историю
    проекта (осторожно)
    @nooovikov 23

    View Slide

  48. 3.4. Деплой с Zappa
    github.com/Miserlou/Zappa
    @nooovikov 24

    View Slide

  49. Zappa
    • Пишем просто Flask-приложение
    • Все настройки в
    zappa_settings.json
    • Можно мигрировать текущие
    проекты без доработок (ну почти)
    @nooovikov 25

    View Slide

  50. @nooovikov 26

    View Slide

  51. Сравнение фреймворков
    • SLS Framework:
    • Меньше всего магии, больше всего гибкости
    • Сложно для начинающих
    • Chalice:
    • Питоничные обертки над амазоновскими командами. АПИ со странностями
    • Подходит для простых проектов
    • Zappa:
    • Максимум магии, но проще всего использовать
    • Просто Flask
    @nooovikov 27

    View Slide

  52. 4. Ограничения и
    хаки
    @nooovikov 28

    View Slide

  53. 4.1. Время
    выполнения
    • Синхронные функции: до 30 сек
    • Асинхронные функции: до 15 мин
    Как быть?
    @nooovikov 29

    View Slide

  54. 4.1. Время
    выполнения
    • Синхронные функции: до 30 сек
    • Асинхронные функции: до 15 мин
    Как быть?
    Amazon SQS + 2 функции
    @nooovikov 30

    View Slide

  55. @nooovikov 31

    View Slide

  56. 4.2. Регулярный
    запуск тасков
    • Невозможно запустить Celery
    • Нет cron
    Как быть?
    @nooovikov 32

    View Slide

  57. 4.2. Регулярный
    запуск тасков
    • Невозможно запустить Celery
    • Нет cron
    Как быть?
    Cloudwatch Events!
    @nooovikov 33

    View Slide

  58. @nooovikov 34

    View Slide

  59. 4.3. Зависимости
    • На AWS Lambda нельзя сделать pip install
    • Все засимости пакуем в zip и загружаем вместе с приложением
    • Поэтому на Lambda сложно запускать проекты с тяжелыми зависимостями
    ./requests 376K
    ./psycopg2 564K
    ./PIL 11M
    ./numpy 23M
    ./pandas 65M
    Как быть?
    @nooovikov 35

    View Slide

  60. Lambda Layers
    @nooovikov 36

    View Slide

  61. 4.4. Хранение стейта
    @nooovikov 37

    View Slide

  62. 4.4. Хранение стейта
    • Можем запустить на Амазоне инстанс Postgres.
    @nooovikov 37

    View Slide

  63. 4.4. Хранение стейта
    • Можем запустить на Амазоне инстанс Postgres.
    • Но это покупка сервера (от $15/мес)
    @nooovikov 37

    View Slide

  64. 4.4. Хранение стейта
    • Можем запустить на Амазоне инстанс Postgres.
    • Но это покупка сервера (от $15/мес)
    • Можем подключиться к AWS DynamoDB (от $0/мес)
    @nooovikov 37

    View Slide

  65. 4.4. Хранение стейта
    • Можем запустить на Амазоне инстанс Postgres.
    • Но это покупка сервера (от $15/мес)
    • Можем подключиться к AWS DynamoDB (от $0/мес)
    • Но это проприетарная NoSQL база со своими
    особенностями
    @nooovikov 37

    View Slide

  66. 4.4. Хранение стейта
    • Можем запустить на Амазоне инстанс Postgres.
    • Но это покупка сервера (от $15/мес)
    • Можем подключиться к AWS DynamoDB (от $0/мес)
    • Но это проприетарная NoSQL база со своими
    особенностями
    • [хак] Можем хранить SQLite базу на S3
    @nooovikov 37

    View Slide

  67. 4.4. Хранение стейта
    • Можем запустить на Амазоне инстанс Postgres.
    • Но это покупка сервера (от $15/мес)
    • Можем подключиться к AWS DynamoDB (от $0/мес)
    • Но это проприетарная NoSQL база со своими
    особенностями
    • [хак] Можем хранить SQLite базу на S3
    • Это Serverless SQL!
    @nooovikov 37

    View Slide

  68. Serverless SQLite
    @nooovikov 38

    View Slide

  69. Serverless SQLite
    @nooovikov 39

    View Slide

  70. Serverless SQLite
    @nooovikov 40

    View Slide

  71. Serverless SQLite
    @nooovikov 41

    View Slide

  72. Serverless SQLite
    @nooovikov 42

    View Slide

  73. Serverless SQLite
    Ограничения
    @nooovikov 43

    View Slide

  74. Serverless SQLite
    Ограничения
    • Несколько параллельных SELECT - ок
    @nooovikov 43

    View Slide

  75. Serverless SQLite
    Ограничения
    • Несколько параллельных SELECT - ок
    • Несколько параллельных UDPATE/DELETE - не ок.
    Закоммитится только последний.
    @nooovikov 43

    View Slide

  76. Serverless SQLite
    Ограничения
    • Несколько параллельных SELECT - ок
    • Несколько параллельных UDPATE/DELETE - не ок.
    Закоммитится только последний.
    • Подходит для сервисов с редкой записью, частым
    чтением
    @nooovikov 43

    View Slide

  77. Пример Serverless
    SQL
    https://clc.to/board
    Serverless мессаджборд
    Zappa + Flask + S3sqlite
    registry.register("s3sqlite", "dialect", "S3SQLiteDialect")
    engine = create_engine('s3sqlite:///messageboard.sqlite')
    class Board(Base):
    id = Column(Integer, primary_key=True)
    name = Column(String)
    class Post(Base):
    id = Column(Integer, primary_key=True)
    content = Column(String)
    created_at = Column(DateTime)
    board = relationship("Board",
    back_populates="posts")
    @nooovikov 44

    View Slide

  78. 5. Цены
    @nooovikov 45

    View Slide

  79. 5. Цены
    Service Units Price per unit Free quota
    Lambda GB-second $0.00001667 ✅
    1 million requests $0.2 ✅
    GB of data out $0.09 ✅
    RDS Postgres Instance hour $0.021(μ)/$0.164(L) ✅ (1y)
    GB-month of storage $0.133 ✅
    DynamoDB 1 million PUT $1.25
    1 million GET $0.25
    GB-month of storage $0.25 ✅
    @nooovikov 46

    View Slide

  80. 6. Отечественный Серверлесс
    Mom, can we have serverless?
    No, we have serverless at home.
    Serverless at home: Yandex Cloud Functions
    @nooovikov 47

    View Slide

  81. Yandex Cloud
    Functions
    • Синтаксис идентичен AWS
    Lambda (ну почти)
    @nooovikov 48

    View Slide

  82. Yandex Cloud
    Functions
    • Синтаксис идентичен AWS
    Lambda (ну почти)
    • Можно работать как в
    интерфейсе, так и в консоли
    (установить Yandex CLI)
    @nooovikov 49

    View Slide

  83. Yandex Cloud
    Functions
    • Синтаксис идентичен AWS
    Lambda (ну почти)
    • Можно работать как в
    интерфейсе, так и в консоли
    (установить Yandex CLI)
    • Не нужно создавать HTTP-ручку -
    она подключается сама
    @nooovikov 50

    View Slide

  84. Yandex Cloud
    Functions
    • Синтаксис идентичен AWS Lambda (ну
    почти)
    • Можно работать как в интерфейсе, так
    и в консоли (установить Yandex CLI)
    • Не нужно создавать HTTP-ручку - она
    подключается сама
    • Workflow идентичен: пишем код,
    пакуем зависимости, загружаем zip-
    архив
    @nooovikov 51

    View Slide

  85. А фреймворки?
    @nooovikov 52

    View Slide

  86. ./deploy.sh
    mkdir ./package && cp * ./package
    pip install -r requirements.txt -t ./package
    zip ./package.zip ./package/*
    yc serverless function version create \
    --function-name=hello \
    --runtime python37 \
    --entrypoint handler.handler \
    --memory 128m \
    --execution-timeout 5s \
    --source-path ./package.zip
    rm ./package.zip && rm -rf ./package
    @nooovikov 53

    View Slide

  87. ./deploy.sh
    mkdir ./package && cp * ./package
    pip install -r requirements.txt -t ./package
    zip ./package.zip ./package/*
    yc serverless function version create \
    --function-name=hello \
    --runtime python37 \
    --entrypoint handler.handler \
    --memory 128m \
    --execution-timeout 5s \
    --source-path ./package.zip
    rm ./package.zip && rm -rf ./package
    @nooovikov 54

    View Slide

  88. ./deploy.sh
    mkdir ./package && cp * ./package
    pip install -r requirements.txt -t ./package
    zip ./package.zip ./package/*
    yc serverless function version create \
    --function-name=hello \
    --runtime python37 \
    --entrypoint handler.handler \
    --memory 128m \
    --execution-timeout 5s \
    --source-path ./package.zip
    rm ./package.zip && rm -rf ./package
    @nooovikov 55

    View Slide

  89. ./deploy.sh
    mkdir ./package && cp * ./package
    pip install -r requirements.txt -t ./package
    zip ./package.zip ./package/*
    yc serverless function version create \
    --function-name=hello \
    --runtime python37 \
    --entrypoint handler.handler \
    --memory 128m \
    --execution-timeout 5s \
    --source-path ./package.zip
    rm ./package.zip && rm -rf ./package
    @nooovikov 56

    View Slide

  90. ./deploy.sh
    mkdir ./package && cp * ./package
    pip install -r requirements.txt -t ./package
    zip ./package.zip ./package/*
    yc serverless function version create \
    --function-name=hello \
    --runtime python37 \
    --entrypoint handler.handler \
    --memory 128m \
    --execution-timeout 5s \
    --source-path ./package.zip
    rm ./package.zip && rm -rf ./package
    @nooovikov 57

    View Slide

  91. ./deploy.sh
    mkdir ./package && cp * ./package
    pip install -r requirements.txt -t ./package
    zip ./package.zip ./package/*
    yc serverless function version create \
    --function-name=hello \
    --runtime python37 \
    --entrypoint handler.handler \
    --memory 128m \
    --execution-timeout 5s \
    --source-path ./package.zip
    rm ./package.zip && rm -rf ./package
    @nooovikov 58

    View Slide

  92. Как сделать проще?
    @nooovikov 59

    View Slide

  93. Yandex + Zappa = ...
    @nooovikov 60

    View Slide

  94. Yandex + Zappa = Yappa
    @nooovikov 61

    View Slide

  95. Yappa
    pip install yappa
    @nooovikov 62

    View Slide

  96. Yappa
    github.com/kurtgn/yappa
    @nooovikov 63

    View Slide

  97. Yappa
    github.com/kurtgn/yappa
    • Выполняет под капотом упаковку и деплой
    @nooovikov 63

    View Slide

  98. Yappa
    github.com/kurtgn/yappa
    • Выполняет под капотом упаковку и деплой
    • Упрощает типовые задачи (yappa logs, yappa
    status, ...)
    @nooovikov 63

    View Slide

  99. Yappa
    github.com/kurtgn/yappa
    • Выполняет под капотом упаковку и деплой
    • Упрощает типовые задачи (yappa logs, yappa
    status, ...)
    • Можно писать навыки для Алисы
    @nooovikov 63

    View Slide

  100. YCF vs. AWS Lambda
    @nooovikov 64

    View Slide

  101. YCF vs. AWS Lambda
    • Сделаем функцию, которая
    считает тяжелый цикл
    @nooovikov 64

    View Slide

  102. YCF vs. AWS Lambda
    • Сделаем функцию, которая
    считает тяжелый цикл
    • Задеплоим на 512MB AWS
    Lambda
    @nooovikov 64

    View Slide

  103. YCF vs. AWS Lambda
    • Сделаем функцию, которая
    считает тяжелый цикл
    • Задеплоим на 512MB AWS
    Lambda
    • Задеплоим на 512MB Yandex
    Cloud Functions
    @nooovikov 64

    View Slide

  104. YCF vs. AWS Lambda
    • Сделаем функцию, которая
    считает тяжелый цикл
    • Задеплоим на 512MB AWS
    Lambda
    • Задеплоим на 512MB Yandex
    Cloud Functions
    • Купим сервера в двух ДЦ, дадим
    нагрузку
    @nooovikov 64

    View Slide

  105. YCF vs. AWS Lambda
    • Сделаем функцию, которая
    считает тяжелый цикл
    • Задеплоим на 512MB AWS
    Lambda
    • Задеплоим на 512MB Yandex
    Cloud Functions
    • Купим сервера в двух ДЦ, дадим
    нагрузку
    • Пусть победит сильнейший!
    @nooovikov 64

    View Slide

  106. @nooovikov 65

    View Slide

  107. @nooovikov 66

    View Slide

  108. YCF vs. AWS Lambda
    Результаты
    • Amazon - тяжелый и прожорливый (но 250 RPS)
    • Yandex - легкий и экономный (но 20 RPS)
    @nooovikov 67

    View Slide

  109. 8. Итог
    Особенности Serverless
    @nooovikov 68

    View Slide

  110. 8. Итог
    Особенности Serverless
    • ! Код - это "клей", а не основа
    @nooovikov 68

    View Slide

  111. 8. Итог
    Особенности Serverless
    • ! Код - это "клей", а не основа
    • " Процессы эфемерны, в них нельзя хранить стейт
    @nooovikov 68

    View Slide

  112. 8. Итог
    Особенности Serverless
    • ! Код - это "клей", а не основа
    • " Процессы эфемерны, в них нельзя хранить стейт
    • # Платим только за время выполнения
    @nooovikov 68

    View Slide

  113. 8. Итог
    Особенности Serverless
    • ! Код - это "клей", а не основа
    • " Процессы эфемерны, в них нельзя хранить стейт
    • # Платим только за время выполнения
    • $ Автоматическое горизонтальное масштабирование
    @nooovikov 68

    View Slide

  114. 8. Итог
    Особенности Serverless
    • ! Код - это "клей", а не основа
    • " Процессы эфемерны, в них нельзя хранить стейт
    • # Платим только за время выполнения
    • $ Автоматическое горизонтальное масштабирование
    • % Странный workflow, но фреймворки упрощают жизнь
    @nooovikov 68

    View Slide

  115. 8. Итог
    Применение Serverless
    @nooovikov 69

    View Slide

  116. 8. Итог
    Применение Serverless
    • ✅ REST API бэкенды, боты
    @nooovikov 69

    View Slide

  117. 8. Итог
    Применение Serverless
    • ✅ REST API бэкенды, боты
    • ✅ ETL пайплайны
    @nooovikov 69

    View Slide

  118. 8. Итог
    Применение Serverless
    • ✅ REST API бэкенды, боты
    • ✅ ETL пайплайны
    • ✅ Бесплатный хостинг для пет проджектов
    @nooovikov 69

    View Slide

  119. 8. Итог
    Применение Serverless
    • ✅ REST API бэкенды, боты
    • ✅ ETL пайплайны
    • ✅ Бесплатный хостинг для пет проджектов
    • ❌ Не подходит для долгих тасков
    @nooovikov 69

    View Slide

  120. 8. Итог
    Применение Serverless
    • ✅ REST API бэкенды, боты
    • ✅ ETL пайплайны
    • ✅ Бесплатный хостинг для пет проджектов
    • ❌ Не подходит для долгих тасков
    • ❌ Не подходит для энтерпрайза
    @nooovikov 69

    View Slide

  121. 8. Итог
    Применение Serverless
    • ✅ REST API бэкенды, боты
    • ✅ ETL пайплайны
    • ✅ Бесплатный хостинг для пет проджектов
    • ❌ Не подходит для долгих тасков
    • ❌ Не подходит для энтерпрайза
    • ❌ Не подходит для постоянного хайлоада
    @nooovikov 69

    View Slide

  122. Спасибо!
    Mikhail Novikov
    Founder & Dev Lead, Fasttrack
    • github.com/kurtgn/yappa
    • clc.to/board
    • t.me/pyshorts
    @nooovikov 70

    View Slide