Files
radixOS/utils.js
2026-04-28 09:34:12 +02:00

294 lines
9.0 KiB
JavaScript

const { exec } = require('child_process');
const path = require('path');
const { permission } = require('process');
const { dirname } = require('path');
const { File: HotReload } = require(`@services/hotReload.js`);
const { service } = require(`@root/server.js`);
const { json } = require('body-parser');
// let integratedStartmenuItems = require('@models/integratedStartmenuItems');
global.path = {
root: dirname(require.main.filename),
source:`${dirname(require.main.filename)}/src`,
public: `${dirname(require.main.filename)}/public`,
plugins: `${dirname(require.main.filename)}/plugins`
};
global.json = {
releaseNotes: new HotReload(path.join(global.path.source, 'models', 'releasenotes.json')),
configuration: new HotReload(path.join(global.path.source, 'models', 'configuration.json')),
stylesheet: new HotReload(path.join(global.path.source, 'models', 'stylesheet.json')),
indexRoutes: new HotReload(path.join(global.path.source, 'routes', 'indexRoutes.js'), { historyLimit: 50, fileType: 'js' }),
startMenuItems: new HotReload(path.join(global.path.source, 'models', 'integratedStartMenuItems.json'))
}
module.exports = startMenuItems = async function (app, objectGuid) {
const debug = global.json.configuration.live.debug.startMenuItems;
let logContent = [];
function safeClone(obj) {
return JSON.parse(JSON.stringify(obj));
}
const log = (...args) => {
if (debug) logContent.push(...args);
};
// =========================
// Load menu sources
// =========================
const integratedStartmenuItems =
service.get('fileSystemManager')
.loadJSON(global.json.startMenuItems.filePath) || [];
const plugins = service
.get('pluginManager')
.getStatus()
.map(({ config, ...plugin }) => ({
...safeClone(plugin),
section: 'Plugin'
}));
let allPlugins = [...plugins, ...integratedStartmenuItems];
// =========================
// Load user permissions
// =========================
const rbacManager = service.get('rbacManager');
const userPermissions = objectGuid === undefined ? [] : (await rbacManager.resolvePermissions(objectGuid))?.permissions;
const normalizedPermissions = userPermissions.map(p => ({
scope: p.scope,
action: p.action,
resource: p.resource || null
}));
// =========================
// SUPER ADMIN CHECK
// =========================
const isSuperAdmin = normalizedPermissions.some(p =>
p.scope === 'SYSTEM' &&
p.resource === 'ALL' &&
p.action === 'ALL'
);
log(`PERMISSIONS: ${JSON.stringify(normalizedPermissions)} - IS SUPER ADMIN: ${isSuperAdmin}`);
// =========================
// BUILD MENU
// =========================
for (const plugin of allPlugins) {
plugin.menu.items = (plugin.menu.items || []).map(item => {
const resource = item.label;
const requiredPermissions = item.permissions || [];
const debugTrace = [];
const authorized = isSuperAdmin
? (debugTrace.push('SUPERADMIN OVERRIDE'), true)
: normalizedPermissions.some(userPerm => {
return requiredPermissions.some(required => {
const scopeMatch =
userPerm.scope === required.scope;
const actionMatch =
userPerm.action === 'ALL' ||
userPerm.action === required.action ||
required.action === 'ALL';
const resourceMatch =
!userPerm.resource ||
userPerm.resource === 'ALL' ||
userPerm.resource === resource;
const result = scopeMatch && actionMatch && resourceMatch;
if (debug) {
debugTrace.push({
userPerm,
required,
scopeMatch,
actionMatch,
resourceMatch,
result
});
}
return result;
});
});
if (debug) {
log(`\nMENU ITEM: ${item.label} - AUTHORIZED:', ${authorized} - TRACE:', ${debugTrace}`);
}
return {
...safeClone(item),
authorized
};
});
plugin.onlyAdministration =
plugin.menu.items.every(i => !i.authorized);
if (debug) {
log(`PLUGIN: ${plugin.name} - VISIBLE:', ${!plugin.onlyAdministration}`);
}
}
// =========================
// FILTER FINAL MENU
// =========================
allPlugins = allPlugins
.filter(p => !p.onlyAdministration)
.filter(p => p.active);
app.locals.startMenuItems = allPlugins;
if(debug) {
service.get('eventManager').writeLog(objectGuid, 0, 'StartMenuItems', logContent);
}
return allPlugins;
};
// module.exports = startMenuItems = async function (app, sAMAccountName) {
// function safeClone(obj) {
// return JSON.parse(JSON.stringify(obj));
// }
// const integratedStartmenuItems = safeClone(service.get('fileSystemManager').loadJSON(global.json.startMenuItems.filePath));
// const plugins = service
// .get('pluginManager')
// .getStatus()
// .map(({ config, ...plugin }) => ({
// ...safeClone(plugin),
// section: 'Plugin'
// }));
// let getAllPlugins = [...plugins, ...integratedStartmenuItems];
// for (const plugin of getAllPlugins) {
// plugin.menu.items = await Promise.all(
// (plugin.menu.items || []).map(async item => {
// const authorized =
// item.label === 'hr' ||
// item.permissions.includes('Administration')
// ? global.json.configuration.live.administration.some(
// name => name.toLowerCase() === sAMAccountName.toLowerCase()
// )
// : item.permissions.includes('*') ||
// (
// await Promise.all(
// item.permissions.map(async permission =>
// (await service.get('activeDirectoryManager').getGroup(permission)) &&
// (await service.get('activeDirectoryManager').isUserMemberOfRecursive(
// sAMAccountName,
// permission
// ))
// )
// )
// ).some(Boolean);
// return {
// ...safeClone(item),
// authorized
// };
// })
// );
// plugin.onlyAdministration =
// plugin.menu.items.every(item => !item.authorized) &&
// !global.json.configuration.live.administration.includes(sAMAccountName);
// }
// getAllPlugins = getAllPlugins
// .filter(plugin => !plugin.onlyAdministration)
// .filter(plugin => plugin.active);
// app.locals.startMenuItems = getAllPlugins;
// return [...getAllPlugins];
// };
/**
* Convert date into custom dateformat
* @param {any} date - Valid date as datetype or string
* @param {string} [format] - (optional) date characters are lowercase, time characters are uppercase; If is null, format will be "dd.mm.yyyy HH:MM:SS"
*/
module.exports = dateFormat = function(date, format = null) {
format = (format == null ? "dd.mm.yyyy HH:MM:SS" : format);
const finish_date = new Date(date);
return format
.replace('yyyy', finish_date.getFullYear())
.replace('yy', finish_date.getFullYear().toString().slice(-2))
.replace('mm', ("0" + (finish_date.getMonth() + 1)).slice(-2))
.replace('dd', ("0" + finish_date.getDate()).slice(-2))
.replace('HH', ("0" + finish_date.getHours()).slice(-2))
.replace('MM', ("0" + finish_date.getMinutes()).slice(-2))
.replace('SS', ("0" + finish_date.getSeconds()).slice(-2));
}
/**
* Limits the number of functions that can be executed in parallel.
*/
// module.exports = createLimiter = function(max) {
// let active = 0;
// const queue = [];
// const runNext = () => {
// if (active >= max || queue.length === 0) return;
// active++;
// const { fn, resolve, reject } = queue.shift();
// fn()
// .then(resolve)
// .catch(reject)
// .finally(() => {
// active--;
// runNext();
// });
// };
// return fn =>
// new Promise((resolve, reject) => {
// queue.push({ fn, resolve, reject });
// runNext();
// });
// }
/**
* try to call an existing host by name or ip adress
* @param {string} hostname - Valid hostname or ip adress
* @param {string} [format] - (optional) date characters are lowercase, time characters are uppercase; If is null, format will be "dd.mm.yyyy HH:MM:SS"
*/
module.exports = ping = function(hostname, cbErr, cb, ttl = 1) {
exec(`ping ${hostname} -c 1 -W ${ttl}`, function (err, stdout, stderr) {
if(err) {
cbErr(err);
} else {
cb(stdout);
}
});
}
module.exports = isObject = function(param) {
return param !== null && typeof param === 'object' && !Array.isArray(param);
}