Введение: почему Serverless и PHP?
Долгое время считалось, что PHP и бессерверные вычисления несовместимы. Однако с появлением пользовательских рантаймов AWS Lambda и развитием инструментов вроде Bref ситуация кардинально изменилась. Сегодня вы можете запускать PHP-приложения в полностью управляемой инфраструктуре AWS Lambda, платя только за реальное время выполнения кода.
В этой статье мы разберем, как создать, настроить и развернуть Serverless-функцию на PHP с использованием AWS Lambda. Вы узнаете о ключевых концепциях, типичных проблемах и лучших практиках. Материал рассчитан на PHP-разработчиков, знакомых с основами AWS, но мы постараемся объяснить все максимально подробно.
К концу руководства вы сможете запустить свой первый PHP-эндпоинт в облаке без единого выделенного сервера.
1. Архитектура Serverless PHP на AWS Lambda
1.1. Как AWS Lambda выполняет PHP?
Нативная среда Lambda не поддерживает PHP напрямую. Для запуска PHP-кода используется специальная прослойка — Custom Runtime. Она представляет собой исполняемый файл (обычно на Python или Bash), который запускает PHP-интерпретатор, передает ему событие (event) и возвращает результат.
Самый популярный инструмент для этого — Bref (Bare-metal PHP for AWS Lambda). Он предоставляет готовый образ PHP с оптимизированными настройками для бессерверной среды.
Базовый процесс выглядит так:
- Клиент отправляет HTTP-запрос к API Gateway.
- API Gateway преобразует запрос в JSON-событие и передает его Lambda.
- Lambda запускает Custom Runtime, который инициализирует PHP-FPM.
- PHP-скрипт обрабатывает событие и возвращает ответ.
1.2. Ключевые компоненты стека
- AWS Lambda — вычислительная единица.
- API Gateway — HTTP-интерфейс для вызова функции.
- Bref — PHP runtime для Lambda.
- Serverless Framework (опционально) — инструмент для деплоя.
- Amazon S3 / DynamoDB — хранение данных (если нужно).
2. Пошаговая настройка: от проекта до деплоя
2.1. Установка инструментов
Для работы вам потребуется:
- PHP 8.1+ с расширениями
mbstring,curl,json. - Composer — менеджер зависимостей.
- Node.js и npm (для Serverless Framework).
- Учетная запись AWS с настроенным IAM-пользователем.
Установите глобально Serverless Framework:
npm install -g serverless
2.2. Создание проекта с Bref
Создайте директорию проекта и инициализируйте его:
mkdir php-lambda-demo
cd php-lambda-demo
composer require bref/bref
Создайте файл index.php — это будет наша функция:
<?php
require __DIR__ . '/vendor/autoload.php';
return function ($event) {
$name = $event['queryStringParameters']['name'] ?? 'World';
return [
'statusCode' => 200,
'headers' => ['Content-Type' => 'text/plain'],
'body' => "Hello, {$name}! This is Serverless PHP on AWS Lambda."
];
};
Обратите внимание: функция должна возвращать массив с ключами statusCode, headers и body. Это стандартный формат ответа для интеграции с API Gateway.
2.3. Конфигурация serverless.yml
Создайте файл serverless.yml в корне проекта:
service: php-lambda-demo
provider:
name: aws
region: eu-central-1
runtime: provided.al2
plugins:
- ./vendor/bref/bref
functions:
hello:
handler: index.php
description: 'Простая PHP функция, возвращающая приветствие'
events:
- httpApi: 'GET /hello'
Ключевые моменты:
runtime: provided.al2— указывает, что мы используем Custom Runtime на базе Amazon Linux 2.handler: index.php— путь к файлу с функцией.events: httpApi— автоматически создает API Gateway HTTP API.
2.4. Деплой и тестирование
Выполните команду в терминале:
serverless deploy
Процесс займет 1-2 минуты. После завершения вы увидите URL вашей функции. Откройте его в браузере:
https://xxxxxxxxx.execute-api.eu-central-1.amazonaws.com/hello?name=PHP
Вы должны получить ответ: Hello, PHP! This is Serverless PHP on AWS Lambda.
3. Продвинутые техники и оптимизация
3.1. Работа с базой данных
Для подключения к MySQL или PostgreSQL используйте расширения PDO. Однако помните: Lambda не поддерживает постоянные соединения. Каждый холодный старт создает новое подключение.
Рекомендуется использовать сервисы AWS:
- Aurora Serverless — масштабируемая БД, идеально подходящая для Serverless.
- DynamoDB — NoSQL база данных, отлично интегрируется с Lambda.
Пример работы с DynamoDB:
<?php
require __DIR__ . '/vendor/autoload.php';
use Aws\DynamoDb\DynamoDbClient;
return function ($event) {
$client = new DynamoDbClient([
'region' => 'eu-central-1',
'version' => 'latest'
]);
$result = $client->getItem([
'TableName' => 'Visitors',
'Key' => ['id' => ['S' => '1']]
]);
return [
'statusCode' => 200,