Added support for accounts that manage all device group

Ylian Saint-Hilaire committed Feb 17, 2020 at 13:01 UTC 916e20fa9f9b896ecb4302efa98c78e731275a50
8 files changed +45 -7
meshagent.js
+1 -1
@@ -214,7 +214,7 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
214 obj.sendBinary(common.ShortToStr(10) + common.ShortToStr(0)); // Command 10, ask mesh agent to clear the core
215 } else {
216 // Update new core
217 - if (parent.parent.meshAgentsArchitectureNumbers[obj.agentInfo.agentId].amt == true) {
217 + if ((parent.parent.meshAgentsArchitectureNumbers[obj.agentInfo.agentId] != null) && (parent.parent.meshAgentsArchitectureNumbers[obj.agentInfo.agentId].amt == true)) {
218 obj.sendBinary(common.ShortToStr(10) + common.ShortToStr(0) + parent.parent.defaultMeshCoreHash + parent.parent.defaultMeshCore); // Command 10, ask mesh agent to set the core (with MEI support)
219 } else {
220 obj.sendBinary(common.ShortToStr(10) + common.ShortToStr(0) + parent.parent.defaultMeshCoreNoMeiHash + parent.parent.defaultMeshCoreNoMei); // Command 10, ask mesh agent to set the core (No MEI)
meshcentral.js
+4
@@ -1280,6 +1280,10 @@ function CreateMeshCentralServer(config, args) {
1280 if (obj.config.settings.autobackup && (typeof obj.config.settings.autobackup.backupintervalhours == 'number')) {
1281 setInterval(obj.db.performBackup, obj.config.settings.autobackup.backupintervalhours * 60 * 60 * 1000);
1282 }
1283 +
1284 + // Setup users that can see all device groups
1285 + obj.config.settings.managealldevicegroups = [];
1286 + for (i in obj.config.domains) { if (Array.isArray(obj.config.domains[i].managealldevicegroups)) { for (var j in obj.config.domains[i].managealldevicegroups) { if (typeof obj.config.domains[i].managealldevicegroups[j] == 'string') { obj.config.settings.managealldevicegroups.push('user/' + i + '/' + obj.config.domains[i].managealldevicegroups[j]); } } } }
1287 });
1288 });
1289 };
meshuser.js
+5 -1
@@ -370,7 +370,11 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
370 try { ws.send(JSON.stringify({ action: 'serverinfo', serverinfo: serverinfo })); } catch (ex) { }
371
372 // Send user information to web socket, this is the first thing we send
373 - try { ws.send(JSON.stringify({ action: 'userinfo', userinfo: parent.CloneSafeUser(parent.users[user._id]) })); } catch (ex) { }
373 + try {
374 + var xuserinfo = parent.CloneSafeUser(parent.users[user._id]);
375 + if ((user.siteadmin == 0xFFFFFFFF) && (parent.parent.config.settings.managealldevicegroups.indexOf(user._id) >= 0)) { xuserinfo.manageAllDeviceGroups = true; }
376 + ws.send(JSON.stringify({ action: 'userinfo', userinfo: xuserinfo }));
377 + } catch (ex) { }
378
379 if (user.siteadmin == 0xFFFFFFFF) {
380 // Send server tracing information
package.json
+1 -1
@@ -1,6 +1,6 @@
1 {
2 "name": "meshcentral",
3 - "version": "0.4.9-f",
3 + "version": "0.4.9-h",
4 "keywords": [
5 "Remote Management",
6 "Intel AMT",
sample-config.json
+1
@@ -81,6 +81,7 @@
81 "_UserNameIsEmail": true,
82 "_NewAccountEmailDomains": [ "sample.com" ],
83 "_NewAccountsRights": [ "nonewgroups", "notools" ],
84 + "_ManageAllDeviceGroups": [ "admin" ],
85 "Footer": "<a href='https://twitter.com/mytwitter'>Twitter</a>",
86 "_CertUrl": "https://192.168.2.106:443/",
87 "_PasswordRequirements": { "min": 8, "max": 128, "upper": 1, "lower": 1, "numeric": 1, "nonalpha": 1, "reset": 90, "force2factor": true, "skip2factor": "127.0.0.1,192.168.2.0/24" },
views/default-mobile.handlebars
+7 -1
@@ -936,7 +936,7 @@
936 }
937 case 'createmesh': {
938 // A new mesh was created
939 - if (message.event.links[userinfo._id] != null) { // Check if this is a mesh create for a mesh we own. If site administrator, we get all messages so need to ignore some.
939 + if ((meshes[message.event.meshid] == null) && ((userinfo.manageAllDeviceGroups) || (message.event.links[userinfo._id] != null))) { // Check if this is a mesh create for a mesh we own. If site administrator, we get all messages so need to ignore some.
940 meshes[message.event.meshid] = { _id: message.event.meshid, name: message.event.name, mtype: message.event.mtype, desc: message.event.desc, links: message.event.links };
941 updateMeshes();
942 updateDevices();
@@ -3445,6 +3445,9 @@
3445 if (typeof mesh == 'string') { mesh = meshes[mesh] }
3446 if ((mesh == null) || (mesh.links == null)) { return 0; }
3447
3448 + // Check if user user
3449 + if (userinfo.manageAllDeviceGroups) return 0xFFFFFFFF;
3450 +
3451 // Check direct link permission
3452 var rights = 0, r = mesh.links[userid];
3453 if (r != null) {
@@ -3478,6 +3481,9 @@
3481 if ((mesh == null) || (mesh.links == null)) { return false; }
3482 if (mesh.links[userid] != null) { return true; } // User has visilibity thru a direct link
3483
3484 + // Check if user user
3485 + if (userinfo.manageAllDeviceGroups) return true;
3486 +
3487 // Check permissions thru user groups
3488 var user = null;
3489 if (userid == userinfo._id) { user = userinfo; } else { if (users != null) { user = users[userid]; } }
views/default.handlebars
+7 -3
@@ -2326,7 +2326,7 @@
2326 }
2327 case 'createmesh': {
2328 // A new mesh was created
2329 - if ((meshes[message.event.meshid] == null) && (message.event.links[userinfo._id] != null)) { // Check if this is a mesh create for a mesh we own. If site administrator, we get all messages so need to ignore some.
2329 + if ((meshes[message.event.meshid] == null) && ((userinfo.manageAllDeviceGroups) || (message.event.links[userinfo._id] != null))) { // Check if this is a mesh create for a mesh we own. If site administrator, we get all messages so need to ignore some.
2330 meshes[message.event.meshid] = { _id: message.event.meshid, name: message.event.name, mtype: message.event.mtype, desc: message.event.desc, links: message.event.links };
2331 masterUpdate(4 + 128 + 8192 + 16384);
2332 meshserver.send({ action: 'files' });
@@ -2399,8 +2399,6 @@
2399 if (xxcurrentView >= 20 && xxcurrentView < 30 && currentMesh._id == message.event.meshid) { setDialogMode(0); go(2); }
2400 // If we are looking at a node in the deleted mesh, move back to "My Devices"
2401 if (xxcurrentView >= 10 && xxcurrentView < 20 && currentNode && currentNode.meshid == message.event.meshid) { setDialogMode(0); go(1); }
2402 -
2403 - console.log('deletemesh', meshes);
2402 break;
2403 }
2404 case 'addnode': {
@@ -10958,6 +10956,9 @@
10956 if (typeof mesh == 'string') { mesh = meshes[mesh] }
10957 if ((mesh == null) || (mesh.links == null)) { return 0; }
10958
10959 + // Check if user user
10960 + if (userinfo.manageAllDeviceGroups) return 0xFFFFFFFF;
10961 +
10962 // Check direct link permission
10963 var rights = 0, r = mesh.links[userid];
10964 if (r != null) {
@@ -10991,6 +10992,9 @@
10992 if ((mesh == null) || (mesh.links == null)) { return false; }
10993 if (mesh.links[userid] != null) { return true; } // User has visilibity thru a direct link
10994
10995 + // Check if user user
10996 + if (userinfo.manageAllDeviceGroups) return true;
10997 +
10998 // Check permissions thru user groups
10999 var user = null;
11000 if (userid == userinfo._id) { user = userinfo; } else { if (users != null) { user = users[userid]; } }
webserver.js
+19
@@ -4031,7 +4031,14 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) {
4031 obj.GetAllMeshWithRights = function (user, rights) {
4032 if (typeof user == 'string') { user = obj.users[user]; }
4033 if ((user == null) || (user.links == null)) { return []; }
4034 +
4035 var r = [];
4036 + if ((user.siteadmin == 0xFFFFFFFF) && (parent.config.settings.managealldevicegroups.indexOf(user._id) >= 0)) {
4037 + // This is a super user that can see all device groups for a given domain
4038 + var meshStartStr = 'mesh/' + user.domain + '/';
4039 + for (var i in obj.meshes) { if ((obj.meshes[i]._id.startsWith(meshStartStr)) && (obj.meshes[i].deleted == null)) { r.push(obj.meshes[i]); } }
4040 + return r;
4041 + }
4042 for (var i in user.links) {
4043 if (i.startsWith('mesh/')) {
4044 // Grant access to a device group thru a direct link
@@ -4062,6 +4069,12 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) {
4069 if (typeof user == 'string') { user = obj.users[user]; }
4070 if ((user == null) || (user.links == null)) { return []; }
4071 var r = [];
4072 + if ((user.siteadmin == 0xFFFFFFFF) && (parent.config.settings.managealldevicegroups.indexOf(user._id) >= 0)) {
4073 + // This is a super user that can see all device groups for a given domain
4074 + var meshStartStr = 'mesh/' + user.domain + '/';
4075 + for (var i in obj.meshes) { if ((obj.meshes[i]._id.startsWith(meshStartStr)) && (obj.meshes[i].deleted == null)) { r.push(obj.meshes[i]._id); } }
4076 + return r;
4077 + }
4078 for (var i in user.links) {
4079 if (i.startsWith('mesh/')) {
4080 // Grant access to a device group thru a direct link
@@ -4099,6 +4112,9 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) {
4112 meshid = mesh._id;
4113 } else return 0;
4114
4115 + // Check if this is a super user that can see all device groups for a given domain
4116 + if ((user.siteadmin == 0xFFFFFFFF) && (parent.config.settings.managealldevicegroups.indexOf(user._id) >= 0) && (meshid.startsWith('mesh/' + user.domain + '/'))) { return 0xFFFFFFFF; }
4117 +
4118 // Check direct user to device group permissions
4119 var rights = 0;
4120 r = user.links[meshid];
@@ -4140,6 +4156,9 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) {
4156 meshid = mesh._id;
4157 } else return false;
4158
4159 + // Check if this is a super user that can see all device groups for a given domain
4160 + if ((user.siteadmin == 0xFFFFFFFF) && (parent.config.settings.managealldevicegroups.indexOf(user._id) >= 0) && (meshid.startsWith('mesh/' + user.domain + '/'))) { return true; }
4161 +
4162 // Check direct user to device group permissions
4163 if (user.links[meshid] != null) { return true; } // If the user has a direct link, stop here.
4164