Перейти к содержимому
PD
Supabase

Edge-функции Supabase: логика без своего сервера

Когда нужны серверные функции, какие у них ограничения, как работать с секретами и как устроены деплой, логи и отладка.

Все статьи гида Supabase · 7

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

Когда нужны

Признаки задачи, требующей функции:

Секреты внешних сервисов. Ключ от платёжной системы, от сервиса рассылки, от модели. В клиентском коде их держать нельзя, а больше в проекте на Supabase им жить негде.

Вебхуки. Внешний сервис присылает уведомление о платеже или событии. Принимать его должен серверный код, который может проверить подпись.

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

Обращение к внешним API с последующей записью результата.

Тяжёлые операции, которые не стоит делать в браузере.

Когда не нужны: если задача решается запросом к базе с корректными политиками. Оборачивать в функцию обычную выборку - лишний слой, который надо поддерживать и который замедляет ответ. Про политики - авторизация и RLS.

Ограничения

Важные до того, как строить на них архитектуру:

Время выполнения ограничено. Долгие операции не подходят: их надо разбивать или выносить в отдельный сервис.

Холодный старт. Функция, которую давно не вызывали, отвечает медленнее первый раз. Для интерактивного действия это заметно.

Ограничения среды. Не всё, что работает на обычном сервере, работает здесь: часть библиотек и системных возможностей недоступна.

Нет постоянного состояния. Между вызовами ничего не сохраняется. Состояние - в базе.

Ограничения по сети. Исходящие вызовы возможны, но со своими правилами и таймаутами.

Практический вывод: функции хороши для коротких действий и плохи для фоновой обработки. Если нужен долгий процесс, ему нужен отдельный сервис или очередь - см. связку с n8n.

Секреты

Единственно правильная схема:

  • Секреты в переменных окружения проекта, а не в коде функции.
  • Функция читает их при выполнении. В клиент они не попадают никогда.
  • Разные значения для разных сред. Тестовый ключ платёжной системы и боевой не должны совпадать.
  • Служебный ключ базы - только здесь. Если функции нужен доступ в обход политик, это допустимо. В клиентском коде такой ключ недопустим никогда.

Отдельно: функция с доступом в обход политик должна сама проверять права. Обход правил снимает защиту, и если функция вызывается пользователем, проверка ложится на неё.

Деплой, логи и отладка

Локальная разработка. Функции запускаются локально, и это правильный способ отлаживать логику: цикл правки быстрее, чем через публикацию.

Публикация отдельной командой. Здесь всплывает самая частая проблема: переменные окружения задаются отдельно для облака. Локально они берутся из вашего файла настроек, и функция, работавшая локально, падает после публикации именно поэтому.

Логи доступны в интерфейсе проекта. Логировать стоит вход, результат и ошибки - без этого разбор проблемы сводится к угадыванию.

Ошибки возвращайте осмысленно. Функция, отдающая пустой ответ при сбое, выглядит так же, как функция, отработавшая успешно.

Порядок отладки при проблеме после публикации:

  1. Проверить переменные окружения в проекте.
  2. Посмотреть логи функции.
  3. Проверить, проходит ли внешний вызов из среды выполнения.
  4. Проверить права: возможно, функция упирается в политику, а не в свою логику.

Общая картина - гид по Supabase.

Вопросы и ответы

Когда нужны edge-функции в Supabase?

Когда логику нельзя отдавать клиенту: работа с секретами внешних сервисов, обработка платёжных вебхуков, действия, которые пользователь не должен уметь вызвать напрямую. Всё, что можно сделать запросом к базе с корректными политиками, функции не требует.

Можно ли хранить ключи от внешних API в функции?

Не в коде, а в переменных окружения проекта. Функция читает их при выполнении, и в клиент они не попадают. Это единственное место в проекте на Supabase, где секреты внешних сервисов вообще могут находиться безопасно.

Почему функция работает локально и падает после публикации?

Чаще всего не заданы переменные окружения в проекте: локально они берутся из вашего файла настроек, а в облаке их нужно задать отдельно. Вторая причина - сетевые ограничения среды выполнения, из-за которых внешний вызов не проходит.

Ещё по теме