v0.5.2: multi-company, isAdmin fix, appVersion, docs

This commit is contained in:
2026-06-02 10:52:12 +03:00
parent 07528b0de3
commit a083f65323
13 changed files with 616 additions and 61 deletions
+11 -6
View File
@@ -50,13 +50,18 @@ function createUiRouter({ auth, MOCK_USERS, authLimiter }) {
try {
const payload = jwt.decode(api.token(req));
if (!payload) throw new Error('empty payload');
const clientId = payload.ClientID || payload.clientId || payload.sub || '';
const rawClientId = payload.ClientID || payload.clientId || payload.sub || '';
const allClientIds = rawClientId.split(',').map(s => s.trim()).filter(Boolean);
const activeClientId = allClientIds[0] || rawClientId;
req.user = {
clientId,
companyId: payload.company_id || payload.companyId || null,
companyName: payload.company_name || payload.companyName || clientId,
email: payload.email || clientId + '@unknown',
isAdmin: clientId === ADMIN_CLIENT_ID,
clientId: rawClientId,
allClientIds,
activeClientId,
companyId: payload.company_id || payload.companyId || null,
companyName: payload.company_name || payload.companyName || activeClientId,
email: payload.email || activeClientId + '@unknown',
isAdmin: activeClientId === ADMIN_CLIENT_ID,
};
} catch (e) {
req.session.destroy(() =>
+12 -5
View File
@@ -28,6 +28,7 @@ function createRouter({ auth, MOCK_USERS, authLimiter }) {
MOCK_USERS: devMode() ? MOCK_USERS : [],
error: req.query.error || null,
returnTo: req.query.returnTo || '/',
appVersion: require('../../package.json').version,
});
});
@@ -39,6 +40,10 @@ function createRouter({ auth, MOCK_USERS, authLimiter }) {
const user = MOCK_USERS.find(u => u.clientId === clientId);
if (!user) return res.redirect('/login?error=Пользователь+не+найден');
// Разбор clientId с запятой (мульти-компания)
const allClientIds = user.clientId.split(',').map(s => s.trim()).filter(Boolean);
const activeClientId = allClientIds[0] || user.clientId;
const token = auth.issueMockToken({
clientId: user.clientId,
companyId: user.companyId || '00000000-0000-0000-0000-000000000001',
@@ -48,11 +53,13 @@ function createRouter({ auth, MOCK_USERS, authLimiter }) {
req.session.token = token;
req.session.user = {
clientId: user.clientId,
email: user.email || user.clientId + '@mock.local',
companyId: user.companyId || '00000000-0000-0000-0000-000000000001',
companyName: user.companyName || user.clientId,
isAdmin: user.role === 'admin',
clientId: user.clientId,
allClientIds,
activeClientId,
email: user.email || user.clientId + '@mock.local',
companyId: user.companyId || '00000000-0000-0000-0000-000000000001',
companyName: user.companyName || user.clientId,
isAdmin: user.isAdmin || user.role === 'admin',
};
res.redirect(returnTo || '/');
});
+23 -10
View File
@@ -33,6 +33,14 @@ function createRouter() {
// GET / — список записей
router.get('/', async (req, res) => {
const token = api.token(req);
// ── Переключатель компании для мульти-компании ──────────────────────
const switchTo = (req.query.switchTo || '').trim();
if (!req.user.isAdmin && switchTo && req.user.allClientIds && req.user.allClientIds.includes(switchTo)) {
req.session.user.activeClientId = switchTo;
if (req.session.user.clientId) req.session.user.clientId = switchTo;
}
try {
let entries = [], limit = 15, selectedCompany = null, companies = [];
@@ -43,10 +51,8 @@ function createRouter() {
const companyId = req.query.company ? parseInt(req.query.company, 10) : null;
if (!companyId) {
// Найти свою компанию admin по clientId
let ownCo = companies.find(c => c.client_id === req.user.clientId) || null;
if (!ownCo) {
// Компании нет — создаём через первый GET /entries (getOrCreateCompany внутри)
await api.get('/api/v1/entries', token);
const cr2 = await api.get('/api/v1/companies', token);
ownCo = (cr2.data.companies || []).find(c => c.client_id === req.user.clientId) || null;
@@ -61,30 +67,37 @@ function createRouter() {
limit = er.data.limit || 15;
}
} else {
// Обычный пользователь: запрашиваем записи для активной компании
const activeClientId = req.user.activeClientId || req.user.clientId;
const er = await api.get('/api/v1/entries', token);
entries = er.data.entries || [];
limit = er.data.limit || 15;
}
const hasMultiple = !req.user.isAdmin && req.user.allClientIds && req.user.allClientIds.length > 1;
res.render('index', {
entries,
limit,
used: entries.length,
user: req.user,
isAdmin: req.user.isAdmin,
used: entries.length,
user: req.user,
isAdmin: req.user.isAdmin,
companies,
selectedCompany,
error: req.query.error || null,
success: req.query.success || null,
lastValue: req.query.lastValue || '',
lastComment: req.query.lastComment || '',
csrfToken: '',
allClientIds: hasMultiple ? req.user.allClientIds : null,
activeClientId: req.user.activeClientId || req.user.clientId,
error: req.query.error || null,
success: req.query.success || null,
lastValue: req.query.lastValue || '',
lastComment: req.query.lastComment || '',
csrfToken: '',
});
} catch (e) {
res.render('index', {
entries: [], limit: 15, used: 0,
user: req.user, isAdmin: req.user.isAdmin,
companies: [], selectedCompany: null,
allClientIds: null, activeClientId: null,
error: 'Ошибка загрузки: ' + e.message,
success: null, lastValue: '', lastComment: '', csrfToken: '',
});