edge — плоскость трафика Versola: обратный прокси, который выполняет вход пользователей, хранит их сессии, проверяет каждый запрос к вашему API по разрешениям и правилам из central и только потом пересылает его дальше. Еще он дает нативным мобильным приложениям отдельный канал к auth. Начните с этой страницы, если хотите поставить Versola перед API. Нужна работающая установка хотя бы с одним тенантом (Запуск Versola локально).
Когда нужен edge
edge нужен, когда решение о доступе должно приниматься один раз перед API, а не повторяться в каждом сервисе:
- Браузерное приложение без токенов в JavaScript.
edgeработает как OAuth-клиент. Браузер получает только cookieEDGE_SESSION(HttpOnly,Secure,SameSite=Strict). - Политики вне кода. Разрешения, CEL-правила по эндпоинтам, step-up-аутентификация и подстановка идентичности настраиваются в консоли администратора, а не пишутся в сервисе.
- Нативное приложение в профиле безопасности
fapi2. У приложения нет учетных данных клиента. См. Нативные приложения. - Вызовы между сервисами. Токен
client_credentialsпроверяется по разрешениям клиента тем же конвейером.
edge не нужен, если ваши сервисы уже сами проверяют токены auth и шлюз вам не требуется. auth работает и без него.
Три способа аутентифицировать вызов
edge ищет учетные данные в таком порядке и берет первые найденные:
| Порядок | Учетные данные | Типичный вызывающий |
|---|---|---|
| 1 | Authorization: Bearer <access token> | Сервис или скрипт с непривязанным токеном |
| 2 | Authorization: DPoP <access token> и заголовок DPoP с proof | Нативное приложение или любой клиент с токеном, привязанным к ключу |
| 3 | Cookie EDGE_SESSION, которую /complete выставляет после входа в браузере | Браузерное приложение |
Токен, привязанный к сертификату, от API-клиента вроде банка приходит как Authorization: Bearer на mutual-TLS порт, а не на обычный. См. Вызов API с токеном, привязанным к сертификату.
Что нужно доказать, определяет claim cnf токена, а не схема, которую выбрал вызывающий. Правила описаны в разделе Токены с привязкой к отправителю:
- Токен, привязанный к ключу (
cnf.jkt), черезBearerотклоняется, независимо от того, есть ли в конфигурации блокdpop. - Токен, привязанный к сертификату (
cnf.x5t#S256), принимается из cookie, где сертификат принадлежит самомуedge, и на mutual-TLS listener, если вызывающий предъявил ровно тот сертификат, который назван в токене. ПоBearerна обычном порту он отклоняется: сертификат вызывающегоedgeтам не видит. - Токен, привязанный и к ключу, и к сертификату, отклоняется при любом способе предъявления, включая cookie.
- Заголовок
DPoPс токеном, у которого нет привязки к ключу, отклоняется.
Если в cookie лежит просроченный access token, edge обновляет его по сохраненному refresh token и отправляет новую cookie. Токен из заголовка никогда не обновляется.
Жизненный цикл запроса
Вход в браузере через пресет
Пресет авторизации — именованный шаблон входа в клиенте: redirect URI, URI после входа и после выхода, scope, тип ответа, домен и путь cookie. Пресеты создаются в консоли, в карточке клиента.
- Ваше приложение переводит браузер на
GET /login/{presetId}.edgeсохраняет PKCE-верификатор иstateэтого входа (живут 10 минут) и отвечает303на/authorizeвauth. Параметрыacr_values,max_age,prompt,login_hintиui_localesпередаются дальше.return_to— путь на origin пресета, например/resources/auth/settings, —edgeзапоминает и дальше не передает: именно туда ведет шаг 3 вместо URI после входа. Все, что не такой путь (другой хост,//host, обратный слэш, фрагмент), игнорируется, как и остальные параметры. - Пользователь входит в
auth, и тот перенаправляет его наGET /completeвedgeсcodeиstate. edgeобменивает код, сохраняет зашифрованный refresh token в своей схеме, выставляетEDGE_SESSIONи отвечает303на URI после входа из пресета или на путьreturn_toна origin этого URI. Еслиauthвернул ошибку,edgeперенаправляет туда же, добавивerror,error_descriptionиerror_uri.GET /logout/{presetId}отправляет браузер на/logoutвauth. Затемauthвызывает/logout/frontchannelи/logout/backchannel, иedgeсбрасывает сессию.
Значение cookie — <presetId>:<accessToken>. Срок ее жизни равен сроку refresh token, а если refresh token не выдавался, сроку access token.
Вызов API
Приложение вызывает /resources/{resourceId}/{path} методами GET, POST, PUT, PATCH или DELETE. Остальные методы не маршрутизируются. Дальше edge выполняет фиксированный конвейер: токен, отзыв, привязка, поиск ресурса и эндпоинта, разрешение, audience, необязательный userinfo, правило allow, step-up, подстановка, пересылка. Любой шаг может завершить запрос. Шаги, контекст CEL и коды ошибок описаны на странице Политики эндпоинтов.
Правила пересылки:
| Часть запроса | Что получает ресурс |
|---|---|
Authorization | Внутренний ресурс: Basic, где имя пользователя — ID ресурса, а пароль — секрет ресурса в base64url. Токен вызывающего не пересылается. Публичный ресурс: токен вызывающего как Bearer |
Cookie | Все cookie, кроме EDGE_SESSION |
Host, DPoP, Content-Length | Удаляются |
| Правила inject | Значения заголовков, query и полей JSON-тела верхнего уровня, вычисленные в CEL. Они заменяют то, что прислал клиент |
| Ответ | Статус и тело как у ресурса, без Set-Cookie. edge читает ответ целиком, прежде чем отдать его |
Чтобы скрыть элементы интерфейса, можно запросить GET /permissions/me?resource=<id> (параметр можно повторять для нескольких ресурсов). Ответ — ID эндпоинтов, которые разрешены ролям вызывающего. Прокси применяет те же правила независимо.
Чего edge не делает
- Не терминирует TLS на
PORT. Там он отдает обычный HTTP, поставьте перед ним прокси с TLS. Для cookie с флагомSecureнужен HTTPS. Единственный TLS-listener, которыйedgeзапускает сам, — необязательный mutual-TLS порт для/resources. - Не ограничивает частоту запросов, не кэширует, не переписывает пути и не фильтрует содержимое.
- Не стримит ответы. Большой ответ ресурса сначала целиком буферизуется в памяти.
- CEL-правила видят токен, claims из
userinfo, параметры пути, query, заголовки и JSON-тело. Обратиться из правила к другому сервису нельзя. - Подстановка в тело работает только для JSON-объекта верхнего уровня, а все подставляемые значения — строки.
- Не выдает токены и не хранит данные пользователей. Это делает
auth.
Порты и служебные эндпоинты
| Порт | Переменная | По умолчанию | Что отдает |
|---|---|---|---|
| Приложение | PORT | 8080 | Все, что описано на этой странице |
| Диагностика | DPORT | 8081 | GET /liveness, GET /readiness, GET /metrics |
| Mutual TLS | MPORT | 8083 | Только /resources/{resourceId}/{path} и только если есть блок mutual-tls. Адрес привязки: MBIND_HOST |
edge не использует APORT. Без блока mutual-tls второй порт приложения не открывается. В развертывании vps, созданном через CLI, edge слушает 8095 и 8096. POST /service/configuration/sync заставляет edge сразу перечитать конфигурацию из central. Он нужен для тестов, требует Basic-учетные данные на основе security.internal-secret и отвечает 404, когда env равен prod. См. Конфигурация edge и Наблюдаемость.
Ограничения
- Один Postgres для всех реплик. Все реплики
edgeиспользуют один Postgres: собственную базуedgeили схемуedgeв общей базе в простейшей конфигурации (цели CLIlocalиvps). В нем лежат сессии, незавершенные входы, отзывы и записи для защиты DPoP от повторов, и через него реплики согласуют работу. - Отзыв распространяется через Postgres
LISTEN/NOTIFY. Отозванный токен отклоняется по списку в памяти, который каждая реплика поддерживает актуальным.LISTENне работает через пулер в transaction-режиме: задайтеpostgres.notifications-urlс прямым URL (за пулером соединений). Сверка раз вrevocation.reload-interval(по умолчанию600 s) страхует от пропущенного уведомления. Реплика, которая не смогла загрузить список при старте, не запускается. - Конфигурация отстает. Ресурсы, эндпоинты, разрешения, клиенты и пресеты кэшируются и перечитываются каждые
configuration-cache-refresh-interval. Удаленное разрешение доходит до каждой реплики не позднее чем через один интервал. Отзыв токена этого интервала не ждет. - Для нативных приложений нужен блок
native, а ему нуженdpop. Без них любой вызов/native/*отвечает404. - Для токенов, привязанных к сертификату, нужен блок
mutual-tls, а дляfetchUserInfoеще и блокnative. Эндпоинт с включеннымfetchUserInfoдля такого токена обращается кauthсобственным сертификатомedge, а он есть только приnative. См. Вызов API с токеном, привязанным к сертификату.
Что дальше
- Политики эндпоинтов: CEL-правила, step-up и подстановка по эндпоинтам.
- Вызов API с токеном, привязанным к сертификату: mutual-TLS порт для
/resources. - Конфигурация edge: все ключи и секреты.
- Как защитить API с помощью edge: рабочая настройка от начала до конца.
- Спецификации OpenAPI:
edge.yamlс описанием маршрутов.