const UserError = require('vn-loopback/util/user-error'); module.exports = Self => { require('../methods/notification/getList')(Self); Self.observe('before save', async function(ctx) { await checkModifyPermission(ctx); }); Self.observe('before delete', async function(ctx) { await checkModifyPermission(ctx); }); async function checkModifyPermission(ctx) { const models = Self.app.models; const instance = ctx.instance; const userId = ctx.options.accessToken.userId; let notificationFk; let workerId; if (instance) { notificationFk = instance.notificationFk; workerId = instance.userFk; } else { const notificationSubscription = await models.NotificationSubscription.findById(ctx.where.id); notificationFk = notificationSubscription.notificationFk; workerId = notificationSubscription.userFk; } const worker = await models.Worker.findById(workerId, {fields: ['id', 'bossFk']}); const available = await Self.getAvailable(workerId); const hasAcl = available.has(notificationFk); if (!hasAcl || (userId != worker.id && userId != worker.bossFk)) throw new UserError('The notification subscription of this worker cant be modified'); } Self.getAvailable = async function(userId, options) { const availableNotificationsMap = new Map(); const models = Self.app.models; const myOptions = {}; if (typeof options == 'object') Object.assign(myOptions, options); const roles = await models.RoleMapping.find({ fields: ['roleId'], where: {principalId: userId} }, myOptions); const availableNotifications = await models.NotificationAcl.find({ fields: ['notificationFk', 'roleFk'], include: {relation: 'notification'}, where: { roleFk: { inq: roles.map(role => role.roleId), }, } }, myOptions); for (available of availableNotifications) { availableNotificationsMap.set(available.notificationFk, { id: null, notificationFk: available.notificationFk, name: available.notification().name, description: available.notification().description, active: false }); } return availableNotificationsMap; }; };