feat: admin-роль (isAdmin, requireAdmin), getCompanyById, getAllCompanies, setLimit, getAudit с JOIN
This commit is contained in:
+28
-1
@@ -4,6 +4,10 @@ const crypto = require('crypto');
|
||||
const ISSUER = process.env.JWT_ISSUER || 'mock-auth-api';
|
||||
const JWKS_URL = process.env.JWKS_URL || '';
|
||||
|
||||
// clientId платформы, которому выдаётся роль администратора.
|
||||
// Задаётся через .env, по умолчанию WZ01112 (Nubes) согласно ТЗ.
|
||||
const ADMIN_CLIENT_ID = process.env.ADMIN_CLIENT_ID || 'WZ01112';
|
||||
|
||||
let keyPair = null;
|
||||
let jwks = null;
|
||||
|
||||
@@ -36,16 +40,22 @@ function initAuth() {
|
||||
|
||||
function createMiddleware() {
|
||||
return function authMiddleware(req, res, next) {
|
||||
// DEV_MODE: обход авторизации для локальной разработки.
|
||||
// Активен только если NODE_ENV != 'production' — в prod всегда требует токен.
|
||||
// DEV_ADMIN=true позволяет тестировать admin-функционал в dev-режиме.
|
||||
if (process.env.DEV_MODE === 'true' && process.env.NODE_ENV !== 'production') {
|
||||
req.user = {
|
||||
email: 'dev@test.local',
|
||||
clientId: 'WZ01325',
|
||||
companyId: '00000000-0000-0000-0000-000000000000',
|
||||
companyName: 'DEV',
|
||||
// DEV_ADMIN=true → имитировать admin-права в dev-окружении
|
||||
isAdmin: process.env.DEV_ADMIN === 'true',
|
||||
};
|
||||
return next();
|
||||
}
|
||||
|
||||
// Токен извлекаем из httpOnly-cookie (браузер) или Authorization header (API)
|
||||
var token = (req.cookies && req.cookies.jwt) ||
|
||||
(req.headers.authorization || '').replace('Bearer ', '');
|
||||
|
||||
@@ -63,6 +73,9 @@ function createMiddleware() {
|
||||
clientId: payload.ClientID,
|
||||
companyId: payload.company_id,
|
||||
companyName: payload.company_name || payload.ClientID,
|
||||
// Роль admin определяется по clientId платформы согласно ТЗ.
|
||||
// В проде: можно расширить проверкой отдельного claim из Keycloak.
|
||||
isAdmin: payload.ClientID === ADMIN_CLIENT_ID,
|
||||
};
|
||||
next();
|
||||
} catch (e) {
|
||||
@@ -75,8 +88,22 @@ function createMiddleware() {
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Middleware-защита для admin-only маршрутов.
|
||||
* Использовать после app.use(auth.middleware):
|
||||
* app.get('/admin', requireAdmin, handler)
|
||||
*/
|
||||
function requireAdmin(req, res, next) {
|
||||
if (!req.user || !req.user.isAdmin) {
|
||||
return res.status(403).send('403 Forbidden: требуется роль администратора');
|
||||
}
|
||||
next();
|
||||
}
|
||||
|
||||
function verifyJWT(token) {
|
||||
if (JWKS_URL) {
|
||||
// TODO: реализовать верификацию через внешний JWKS-endpoint.
|
||||
// Нужен URL от команды Keycloak: JWKS_URL=https://auth-api.../jwks
|
||||
throw new Error('JWKS_URL verification not implemented yet');
|
||||
}
|
||||
return jwt.verify(token, keyPair.publicKey, {
|
||||
@@ -106,4 +133,4 @@ function issueJWT(claims) {
|
||||
);
|
||||
}
|
||||
|
||||
module.exports = { initAuth };
|
||||
module.exports = { initAuth, requireAdmin };
|
||||
|
||||
Reference in New Issue
Block a user