From 6719e9faf75c6e9e55e21ef8d2a3ef1a98d970a8 Mon Sep 17 00:00:00 2001 From: Ruslan Bakiev Date: Sun, 31 May 2026 22:01:00 +0500 Subject: [PATCH] Authorize manager orders by app JWT scope --- src/auth.ts | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/src/auth.ts b/src/auth.ts index 79e5c70..c6030d6 100644 --- a/src/auth.ts +++ b/src/auth.ts @@ -5,7 +5,7 @@ import type { Request } from 'express' const LOGTO_JWKS_URL = process.env.LOGTO_JWKS_URL || 'https://auth.optovia.ru/oidc/jwks' const LOGTO_ISSUER = process.env.LOGTO_ISSUER || 'https://auth.optovia.ru/oidc' const LOGTO_ORDERS_AUDIENCE = process.env.LOGTO_ORDERS_AUDIENCE || 'https://orders.optovia.ru' -const MANAGER_JWT_ISSUER = 'optovia:teams' +const APP_JWT_ISSUER = 'optovia:teams' const jwks = createRemoteJWKSet(new URL(LOGTO_JWKS_URL)) @@ -69,22 +69,21 @@ export async function teamContext(req: Request): Promise { } } -function managerJwtSecret(): Uint8Array { - const secret = process.env.MANAGER_JWT_SECRET - if (!secret) throw new GraphQLError('MANAGER_JWT_SECRET is required', { extensions: { code: 'INTERNAL_SERVER_ERROR' } }) +function appJwtSecret(): Uint8Array { + const secret = process.env.APP_JWT_SECRET + if (!secret) throw new GraphQLError('APP_JWT_SECRET is required', { extensions: { code: 'INTERNAL_SERVER_ERROR' } }) return new TextEncoder().encode(secret) } export async function managerContext(req: Request): Promise { const token = getBearerToken(req) - const { payload } = await jwtVerify(token, managerJwtSecret(), { - issuer: MANAGER_JWT_ISSUER, + const { payload } = await jwtVerify(token, appJwtSecret(), { + issuer: APP_JWT_ISSUER, audience: LOGTO_ORDERS_AUDIENCE, }) const scopes = scopesFromPayload(payload) - const role = (payload as Record).role const teamUuid = (payload as Record).team_uuid as string | undefined - if (!payload.sub || role !== 'manager' || !scopes.includes('manager') || !teamUuid) { + if (!payload.sub || !scopes.includes('manager') || !teamUuid) { throw new GraphQLError('Unauthorized', { extensions: { code: 'UNAUTHENTICATED' } }) } return { userId: payload.sub, teamUuid, scopes: ['teams:member', 'manager'] }