13.2 Аутентификация
enum Principal {
User(id: UserId, roles: Set<AppRole>, claims: Map<str, str>, mfa: bool, tenant: str?)
Service(name: str, role: str)
Node(id: NodeId)
Anonymous
}- Провайдеры задаются в
cluster { auth { … } }:jwt(issuer, audience?, jwks?),oidc(issuer, clientId),apikey,session(cookie: name). Роли пользователя:roles from claim("roles") as AppRole.
Определяется реализацией. OIDC (D-8055; DIV-025; D-4739). Необязательная возможность: провайдер
oidc(issuer, clientId). Эта реализация его не содержит; проверка JWT поjwksили заданному ключу (jwt(…)) поддерживается.
apikey— ключ в заголовке (apikey(header: h), по умолчаниюx-api-key) или вAuthorization: ApiKey …; сервер хранит только хеш ключа, ключ даётPrincipal.User.session(cookie: name)— серверная сессия:createSession(user, roles, ttl) -> str | SessionError(std.rpc) создаёт сессию и возвращает идентификатор, который клиент несёт в cookiename;endSession(id)её завершает; установкаSet-Cookie— дело приложения. Порядок: Bearer (jwt) → ключ → cookie сессии; первый предъявленный решает; предъявленный неверный документ —UNAUTHENTICATED, отсутствие всех —Anonymous. Заголовки учётных данных не попадают вctx.metaи не передаются дальше (D-8065; D-8200..D-8202, D-8208).
Определяется реализацией. Хранилище ключей и сессий (D-8065; DIV-025; D-8200, D-8201). Эта реализация: ключи — JSON-файл с SHA-256 (
OXL_AUTH_APIKEYS/--auth-apikeys; поляid,sha256,sub,roles,tenant,mfa,claims,expires), сравнение за постоянное время, перечитывается при изменении; нет файла — все ключи отвергаются; сессия — запись{exp, principal}под хешем идентификатора в реплицируемом хранилище, срок 1 мс..30 суток.
- Проверка выполняется до входа в обработчик. Неудача —
AccessDenied(UNAUTHENTICATED). - Сервисы и узлы опознаются по mTLS-сертификату.
- Делегирование: исходящие вызовы из обработчика несут исходного пользователя (
ctx.caller) и вызывающий сервис (ctx.via). Сузить права:asScoped(caller.scoped([…])) { … }; вызвать от имени своего сервиса:asService { … }. Вызовы внешних сервисов (S.connect(addr)) идентичность пользователя и сервиса НЕ несут: заголовкиx-oxl-principalиx-oxl-userтуда не передаются, аauthorizationвходящего вызова не пересылается (приложение при необходимости кладёт собственный документ вctx.meta) (D-8066; D-8300).
Определяется реализацией. Тип идентификатора пользователя (D-8056; DIV-049; D-2905).
UserIdвPrincipal.Userи вuserId()— тип приложения (например,distinct u64), а стандартная библиотека не знает его. Эта реализация хранит идентификатор вPrincipal.Userкакstr(значение claimsubJWT);Ctx.userId()иisUserпринимают и возвращаютstr; приложение разбирает его в свойUserId(в V.5 — функциейcallerId(ctx)).
Методы Principal: isUser(id: UserId?) -> bool (ложь при none и не-пользователе), has(role: AppRole) -> bool, service(name: str) -> bool, userId() -> UserId | AccessDenied. В обработчиках ctx.userId() — сокращение для ctx.caller.userId(); в политиках принципал доступен как caller.
Связанные диагностики
См. также
Исходник: docs/spec/oxl-standard.md