Запуск консольного приложения PHP в качестве микросервиса

В предыдущей статье я создал простое консольное приложение Hello World, используя Консольный компонент Symfony. Прочтите его, если вы не знаете, как создать консольное приложение Symfony.

В этой статье я попытаюсь развернуть свое консольное приложение в AWS Lambda для запуска в качестве задания Cron с Amazon EvenBridge.

Давайте попробуем разобраться в AWS Lambda и посмотрим, как мы можем развернуть в ней PHP-приложения.

АВС Лямбда

Эта статья не об AWS Lambda. Если вы не знаете, что такое AWS Lambda, перейдите в официальную документацию AWS Lambda и прочтите ее.

Для развертывания приложения в AWS Lambda вам потребуется учетная запись AWS. Пожалуйста, зарегистрируйте https://aws.amazon.com/».

Теперь я могу предположить, что у вас есть учетная запись AWS и доступ к лямбда-сервису AWS.

Давайте откроем консоль AWS, перейдем к сервису AWS Lambda и нажмем кнопку «Создать функцию».

Если мы посмотрим на консоль AWS, там будут показаны среды выполнения для многих разных языков, но PHP в списке нет.

PHP — не единственный отсутствующий язык в списке, потому что отсутствуют многие другие языки, такие как Rust, Erlang и другие. В августе 2020 года AWS представила настраиваемую среду выполнения для поддержки любого языка, который пользователь хочет развернуть и запустить в AWS Lambda.

Если вы не знаете, что такое среда выполнения, прочтите официальную документацию, чтобы понять.

Среды выполнения Lambda
Пользовательские среды выполнения AWS Lambda

Amazon предоставляет среду выполнения по умолчанию для определенных языков, а для всех остальных требуется пользовательская среда выполнения.

Бреф-плагин

Сообщество PHP представило плагин Bref для Serverless Framework, который предоставляет пользовательские среды выполнения PHP для AWS Lambda для различных типов приложений.

Мы собираемся развернуть консольное приложение, и у Bref есть для него специальная среда выполнения. Вы можете найти все пользовательские среды выполнения PHP здесь: https://runtimes.bref.sh/

Как установить Bref и использовать его в проекте

Вам необходимо установить Bref и настроить учетную запись AWS, чтобы следовать инструкциям из официальной документации Bref. https://bref.sh/docs/installation.html

Теперь вы можете перейти в свое консольное приложение или загрузить мое приложение «Hello World» с Github, чтобы продолжить эту статью.

Консольное приложение PHP: Репозиторий Github

Как только вы окажетесь в корневом каталоге проекта, установите пакет Bref.

composer require bref/bref

Теперь пакет Bref установлен и готов начать инициализацию бессерверного проекта.

Пришло время создать бессерверную структуру проекта для развертывания приложения в AWS Lambda.

vendor/bin/bref init

Команда инициализации Bref попросит вас создать тип лямбда-функции, которую будет использовать ваше приложение.

В нашем случае мы собираемся создать «управляемую событиями функцию», потому что она будет вызываться событием EventBridge. Выберите второй вариант, набрав 1 в консоли.

Он добавит два новых файла в корневой каталог проекта.

index.php
serverless.yml

Index.php является обработчиком AWS Lambda по умолчанию и работает так же, как index.php работает для apache в общедоступном каталоге веб-приложения Symfony.

serverless.yml — это файл безсерверного фреймворка, в котором мы укажем AWS, где и как развернуть наше приложение в облаке.

Давайте рассмотрим подробно и попробуем создать нашу инфраструктуру в виде кода в файле serverless.yml.

По умолчанию Bref создаст следующую структуру. Это хорошее начало, но этого недостаточно, чтобы отправить консольное приложение в Lambda.

service: app

provider:
    name: aws
    region: us-east-1
    runtime: provided.al2

plugins:
    - ./vendor/bref/bref

functions:
    hello:
        handler: index.php
        description: ''
        layers:
            - ${bref:layer.php-81}

# Exclude files from deployment
package:
    patterns:
        - '!tests/**'

Нам нужно понять каждый блок кода и изменить его в соответствии с нашими потребностями.

Дайте имя приложению.

service: php-console-app

Мы будем использовать того же провайдера, но изменим регион с «us-east-1» на «eu-west-1», потому что мы собираемся разместить наше приложение в регионе «Ирландия».

provider:
    name: aws
    region: eu-west-1
    runtime: provided.al2

Плагин будет тот же, поэтому ничего менять не нужно.

plugins:
    - ./vendor/bref/bref

Далее самая важная часть, где мы настроим нашу функцию Lambda и развернем приложение.

Измените функциональный блок в соответствии со следующими инструкциями.

functions:
    cron:
        handler: bin/console
        description: 'Hello world console command'
        layers:
            - ${bref:layer.php-81}
            - ${bref:layer.console}

Как видите, мы изменили метод вызова с «hello» на «cron» и заменили обработчик index.php на bin/console. Причина в том, что когда EventBridge вызовет нашу команду, точка входа нашего приложения будет bin/console, а не index.php.

Нам не нужен index.php в приложении, поэтому удалите его, выполнив следующую команду:

rm index.php

Затем мы добавили две разные среды выполнения в качестве слоев для запуска нашего приложения:

functions:
    cron:
        layers:
            - ${bref:layer.php-81}
            - ${bref:layer.console}

После добавления слоев функция AWS Lambda готова к работе:

#serverless.yml
service: php-console-app

provider:
    name: aws
    region: eu-west-1
    runtime: provided.al2

plugins:
    - ./vendor/bref/bref

functions:
    cron:
        handler: bin/console
        description: 'Hello world console command'
        layers:
            - ${bref:layer.php-81}
            - ${bref:layer.console}

# Exclude files from deployment
package:
    patterns:
        - '!tests/**'

Попробуем развернуть и посмотреть, как это выглядит:

serverless deploy

Как видите, приложение успешно развернуто. Перейдите в свою консоль Lambda и найдите функцию php-console-app.

Вы можете видеть, что Lambda добавила dev и cron в конце имени функции. Он добавляет среду (по умолчанию dev) и вызывает имя метода к имени функции.

Нажмите на название функции и откройте ее:

Вы можете видеть, что лямбда-функция создана и имеет два слоя, как определено в файле serverless.yml.

Если вы прокрутите вниз, вы также сможете увидеть код своего приложения.

Если вы видите обзор Lambda, в нем отсутствует триггер для вызова этой функции.

Есть несколько способов вызвать функцию Lambda, но в нашем случае мы будем вызывать ее каждую минуту, как задание cron в Linux.

Amazon EventBridge или официально известный как Amazon CloudWatch Events

В Amazone EventBridge есть два разных правила для вызова функции Lambda.

  1. Создание правил Amazon EventBridge, реагирующих на события
  2. Создание правила Amazon EventBridge, работающего по расписанию

Мы будем использовать второе правило для планирования нашей работы cron. У него есть два способа запланировать событие, выражение скорости или выражение cron.

Давайте настроим выражение cron в нашем файле serverless.yml следующим образом, чтобы наша команда запускалась каждую минуту:

functions:
        {.....} 
        events:
            - schedule:
                  rate: cron(* * * * ? *)
                  input: '"app:hello-world --verbose"'

Вы можете найти все правила cron на официальной странице документации EventBridge.

Окончательная версия нашего serverless.yml:

#serverless.yml
service: php-console-app

provider:
    name: aws
    region: eu-west-1
    runtime: provided.al2

plugins:
    - ./vendor/bref/bref

functions:
    cron:
        handler: bin/console
        description: 'Hello world console command'
        layers:
            - ${bref:layer.php-81}
            - ${bref:layer.console}
        events:
            - schedule:
                  rate: cron(* * * * ? *)
                  input: '"app:hello-world --verbose"'

# Exclude files from deployment
package:
    patterns:
        - '!tests/**'

Теперь снова разверните и посмотрите, работает ли это:

serverless deploy

Чтобы проверить нашу конфигурацию EventBridge, откройте свою функцию Lambda в консоли AWS и посмотрите, добавлен ли EventBridge в качестве триггера или нет.

Для меня это выглядит как добавлено:

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

Есть несколько способов просмотреть журналы из консоли AWS. Вы можете просматривать журналы в настольном приложении Bref или непосредственно на вкладке «Монитор функции Lambda».

Журналы из консоли AWS:

Если вы щелкните один из этих журналов, вы сможете увидеть вывод команды приложения.

Или вы можете просмотреть те же журналы из приложения Bref. Откройте настольное приложение Bref, выберите регион eu-west-1 и функцию php-console-app-dev.

Теперь консольное приложение PHP запускается каждую минуту для выполнения своей задачи.

Я надеюсь, что вы узнали что-то из поста. Если у вас есть вопросы, пожалуйста, не стесняйтесь спрашивать.

Вы можете скачать исходный код из репозитория GitHub.