More last device connection improvements.
Ylian Saint-Hilaire committed
Jul 31, 2021 at 19:31 UTC
d006dbbff848487ce9954b769f5471409d802d84
4 files changed
+46
-18
meshagent.js
+2
-7
@@ -64,7 +64,7 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
64
// Remove this agent from the webserver list
65
if (parent.wsagents[obj.dbNodeKey] == obj) {
66
delete parent.wsagents[obj.dbNodeKey];
67
- parent.parent.ClearConnectivityState(obj.dbMeshKey, obj.dbNodeKey, 1);
67
+ parent.parent.ClearConnectivityState(obj.dbMeshKey, obj.dbNodeKey, 1, null, { remoteaddrport: obj.remoteaddrport });
68
}
69
70
// Remove this agent from the list of agents with bad web certificates
@@ -95,9 +95,6 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
95
if ((state.connectivity & 1) != 0) { parent.wsagents[obj.dbNodeKey].close(); } // Disconnect mesh agent
96
if ((state.connectivity & 2) != 0) { parent.parent.mpsserver.closeAllForNode(obj.dbNodeKey); } // Disconnect CIRA connection
97
}
98
- } else {
99
- // Update the last connect time
100
- if (obj.authenticated == 2) { db.Set({ _id: 'lc' + obj.dbNodeKey, type: 'lastconnect', domain: domain.id, time: Date.now(), addr: obj.remoteaddrport, cause: 1 }); }
98
}
99
100
// Set this agent as no longer authenticated
@@ -787,7 +784,6 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
784
785
// Mark when this device connected
786
obj.connectTime = Date.now();
790
- db.Set({ _id: 'lc' + obj.dbNodeKey, type: 'lastconnect', domain: domain.id, time: obj.connectTime, addr: obj.remoteaddrport, cause: 1 });
787
788
// Device already exists, look if changes have occured
789
var changes = [], change = 0, log = 0;
@@ -849,7 +845,6 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
845
846
// Mark when this device connected
847
obj.connectTime = Date.now();
852
- db.Set({ _id: 'lc' + obj.dbNodeKey, type: 'lastconnect', domain: domain.id, time: obj.connectTime, addr: obj.remoteaddrport, cause: 1 });
848
849
// This node does not exist, create it.
850
var agentName = obj.agentName ? obj.agentName : obj.agentInfo.computerName;
@@ -893,7 +888,7 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
888
dupAgent.close(3);
889
} else {
890
// Indicate the agent is connected
896
- parent.parent.SetConnectivityState(obj.dbMeshKey, obj.dbNodeKey, obj.connectTime, 1, 1);
891
+ parent.parent.SetConnectivityState(obj.dbMeshKey, obj.dbNodeKey, obj.connectTime, 1, 1, null, { remoteaddrport: obj.remoteaddrport });
892
}
893
894
// We are done, ready to communicate with this agent
meshcentral.js
+38
-7
@@ -2100,7 +2100,7 @@ function CreateMeshCentralServer(config, args) {
2100
// powerState: Value, 0 = Unknown, 1 = S0 power on, 2 = S1 Sleep, 3 = S2 Sleep, 4 = S3 Sleep, 5 = S4 Hibernate, 6 = S5 Soft-Off, 7 = Present
2101
//var connectTypeStrings = ['', 'MeshAgent', 'Intel AMT CIRA', '', 'Intel AMT local', '', '', '', 'Intel AMT Relay', '', '', '', '', '', '', '', 'MQTT'];
2102
//var powerStateStrings = ['Unknown', 'Powered', 'Sleep', 'Sleep', 'Deep Sleep', 'Hibernating', 'Soft-Off', 'Present'];
2103
- obj.SetConnectivityState = function (meshid, nodeid, connectTime, connectType, powerState, serverid) {
2103
+ obj.SetConnectivityState = function (meshid, nodeid, connectTime, connectType, powerState, serverid, extraInfo) {
2104
//console.log('SetConnectivity for ' + nodeid.substring(0, 16) + ', Type: ' + connectTypeStrings[connectType] + ', Power: ' + powerStateStrings[powerState] + (serverid == null ? ('') : (', ServerId: ' + serverid)));
2105
if ((serverid == null) && (obj.multiServer != null)) { obj.multiServer.DispatchMessage({ action: 'SetConnectivityState', meshid: meshid, nodeid: nodeid, connectTime: connectTime, connectType: connectType, powerState: powerState }); }
2106
@@ -2137,6 +2137,11 @@ function CreateMeshCentralServer(config, args) {
2137
// Event the node connection change
2138
if (eventConnectChange == 1) {
2139
obj.DispatchEvent(obj.webserver.CreateNodeDispatchTargets(meshid, nodeid), obj, { action: 'nodeconnect', meshid: meshid, nodeid: nodeid, domain: nodeid.split('/')[1], conn: state.connectivity, pwr: state.powerState, ct: connectTime, nolog: 1, nopeers: 1 });
2140
+
2141
+ // Save indication of node connection change
2142
+ const lc = { _id: 'lc' + nodeid, type: 'lastconnect', domain: nodeid.split('/')[1], time: Date.now(), cause: 1, connectType: connectType, serverid: obj.serverId };
2143
+ if (extraInfo && extraInfo.remoteaddrport) { lc.addr = extraInfo.remoteaddrport; }
2144
+ obj.db.Set(lc);
2145
}
2146
} else {
2147
// Multi server mode
@@ -2144,14 +2149,16 @@ function CreateMeshCentralServer(config, args) {
2149
// Change the node connection state
2150
if (serverid == null) { serverid = obj.serverId; }
2151
if (obj.peerConnectivityByNode[serverid] == null) return; // Guard against unknown serverid's
2152
+ var eventConnectChange = 0;
2153
var state = obj.peerConnectivityByNode[serverid][nodeid];
2154
if (state) {
2155
// Change the connection in the node and mesh state lists
2150
- if ((state.connectivity & connectType) == 0) { state.connectivity |= connectType; }
2156
+ if ((state.connectivity & connectType) == 0) { state.connectivity |= connectType; eventConnectChange = 1; }
2157
state.meshid = meshid;
2158
} else {
2159
// Add the connection to the node and mesh state list
2160
obj.peerConnectivityByNode[serverid][nodeid] = state = { connectivity: connectType, meshid: meshid };
2161
+ eventConnectChange = 1;
2162
}
2163
2164
// Set node power state
@@ -2160,6 +2167,7 @@ function CreateMeshCentralServer(config, args) {
2167
if ((state.connectivity & 1) != 0) { powerState = state.agentPower; } else if ((state.connectivity & 2) != 0) { powerState = state.ciraPower; } else if ((state.connectivity & 4) != 0) { powerState = state.amtPower; }
2168
if ((state.powerState == null) || (state.powerState != powerState)) {
2169
state.powerState = powerState;
2170
+ eventConnectChange = 1;
2171
2172
// Set new power state in database
2173
var record = { time: new Date(connectTime), nodeid: nodeid, power: powerState, server: obj.multiServer.serverid };
@@ -2167,9 +2175,18 @@ function CreateMeshCentralServer(config, args) {
2175
obj.db.storePowerEvent(record, obj.multiServer);
2176
}
2177
2170
- // Update the combined node state
2171
- var x = {}; x[nodeid] = 1;
2172
- obj.UpdateConnectivityState(x);
2178
+ if (eventConnectChange == 1) {
2179
+ // Update the combined node state
2180
+ var x = {}; x[nodeid] = 1;
2181
+ obj.UpdateConnectivityState(x);
2182
+
2183
+ // Save indication of node connection change
2184
+ if (serverid == obj.serverId) {
2185
+ const lc = { _id: 'lc' + nodeid, type: 'lastconnect', domain: nodeid.split('/')[1], time: Date.now(), cause: 1, connectType: connectType, serverid: obj.serverId };
2186
+ if (extraInfo && extraInfo.remoteaddrport) { lc.addr = extraInfo.remoteaddrport; }
2187
+ obj.db.Set(lc);
2188
+ }
2189
+ }
2190
}
2191
};
2192
@@ -2177,7 +2194,7 @@ function CreateMeshCentralServer(config, args) {
2194
// meshId: mesh identifier of format mesh/domain/meshidhex
2195
// nodeId: node identifier of format node/domain/nodeidhex
2196
// connectType: Bitmask, 1 = MeshAgent, 2 = Intel AMT CIRA, 3 = Intel AMT local.
2180
- obj.ClearConnectivityState = function (meshid, nodeid, connectType, serverid) {
2197
+ obj.ClearConnectivityState = function (meshid, nodeid, connectType, serverid, extraInfo) {
2198
//console.log('ClearConnectivity for ' + nodeid.substring(0, 16) + ', Type: ' + connectTypeStrings[connectType] + (serverid == null?(''):(', ServerId: ' + serverid)));
2199
if ((serverid == null) && (obj.multiServer != null)) { obj.multiServer.DispatchMessage({ action: 'ClearConnectivityState', meshid: meshid, nodeid: nodeid, connectType: connectType }); }
2200
@@ -2192,6 +2209,11 @@ function CreateMeshCentralServer(config, args) {
2209
if ((state.connectivity & connectType) != 0) {
2210
state.connectivity -= connectType;
2211
2212
+ // Save indication of node connection change
2213
+ const lc = { _id: 'lc' + nodeid, type: 'lastconnect', domain: nodeid.split('/')[1], time: Date.now(), cause: 0, connectType: connectType, serverid: obj.serverId };
2214
+ if (extraInfo && extraInfo.remoteaddrport) { lc.addr = extraInfo.remoteaddrport; }
2215
+ obj.db.Set(lc);
2216
+
2217
// If the node is completely disconnected, clean it up completely
2218
if (state.connectivity == 0) { delete obj.connectivityByNode[nodeid]; }
2219
eventConnectChange = 1;
@@ -2210,7 +2232,9 @@ function CreateMeshCentralServer(config, args) {
2232
}
2233
2234
// Event the node connection change
2213
- if (eventConnectChange == 1) { obj.DispatchEvent(obj.webserver.CreateNodeDispatchTargets(meshid, nodeid), obj, { action: 'nodeconnect', meshid: meshid, nodeid: nodeid, domain: nodeid.split('/')[1], conn: state.connectivity, pwr: state.powerState, nolog: 1, nopeers: 1 }); }
2235
+ if (eventConnectChange == 1) {
2236
+ obj.DispatchEvent(obj.webserver.CreateNodeDispatchTargets(meshid, nodeid), obj, { action: 'nodeconnect', meshid: meshid, nodeid: nodeid, domain: nodeid.split('/')[1], conn: state.connectivity, pwr: state.powerState, nolog: 1, nopeers: 1 });
2237
+ }
2238
} else {
2239
// Multi server mode
2240
@@ -2224,6 +2248,13 @@ function CreateMeshCentralServer(config, args) {
2248
if ((state.connectivity & connectType) != 0) {
2249
state.connectivity -= connectType; // Remove one connectivity mode
2250
2251
+ // Save indication of node connection change
2252
+ if (serverid == obj.serverId) {
2253
+ const lc = { _id: 'lc' + nodeid, type: 'lastconnect', domain: nodeid.split('/')[1], time: Date.now(), cause: 0, connectType: connectType, serverid: obj.serverId };
2254
+ if (extraInfo && extraInfo.remoteaddrport) { lc.addr = extraInfo.remoteaddrport; }
2255
+ obj.db.Set(lc);
2256
+ }
2257
+
2258
// If the node is completely disconnected, clean it up completely
2259
if (state.connectivity == 0) { delete obj.peerConnectivityByNode[serverid][nodeid]; state.powerState = 0; }
2260
}
meshuser.js
+2
-1
@@ -2568,6 +2568,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
2568
if ((common.validateString(command.desc, 0, 1024) == true) && (command.desc != mesh.desc)) { if (change != '') change += ' and description changed'; else change += 'Group "' + mesh.name + '" description changed'; mesh.desc = command.desc; }
2569
if ((common.validateInt(command.flags) == true) && (command.flags != mesh.flags)) { if (change != '') change += ' and flags changed'; else change += 'Group "' + mesh.name + '" flags changed'; mesh.flags = command.flags; }
2570
if ((common.validateInt(command.consent) == true) && (command.consent != mesh.consent)) { if (change != '') change += ' and consent changed'; else change += 'Group "' + mesh.name + '" consent changed'; mesh.consent = command.consent; }
2571
+ if ((common.validateInt(command.expireDevs, 0, 2000) == true) && (command.expireDevs != mesh.expireDevs)) { if (change != '') change += ' and auto-remove changed'; else change += 'Group "' + mesh.name + '" auto-remove changed'; if (command.expireDevs == 0) { delete mesh.expireDevs; } else { mesh.expireDevs = command.expireDevs; } }
2572
2573
// See if we need to change device group invitation codes
2574
if (mesh.mtype == 2) {
@@ -2598,7 +2599,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
2599
2600
if (change != '') {
2601
db.Set(mesh);
2601
- var event = { etype: 'mesh', userid: user._id, username: user.name, meshid: mesh._id, name: mesh.name, mtype: mesh.mtype, desc: mesh.desc, flags: mesh.flags, consent: mesh.consent, action: 'meshchange', links: mesh.links, msg: change, domain: domain.id, invite: mesh.invite };
2602
+ var event = { etype: 'mesh', userid: user._id, username: user.name, meshid: mesh._id, name: mesh.name, mtype: mesh.mtype, desc: mesh.desc, flags: mesh.flags, consent: mesh.consent, action: 'meshchange', links: mesh.links, msg: change, domain: domain.id, invite: mesh.invite, expireDevs: mesh.expireDevs };
2603
if (db.changeStream) { event.noact = 1; } // If DB change stream is active, don't use this event to change the mesh. Another event will come.
2604
parent.parent.DispatchEvent(parent.CreateMeshDispatchTargets(mesh, [user._id]), obj, event);
2605
}
views/default.handlebars
+4
-3
@@ -2912,6 +2912,7 @@
2912
if (message.event.links) { meshes[message.event.meshid].links = message.event.links; }
2913
if (message.event.amt) { meshes[message.event.meshid].amt = message.event.amt; }
2914
if (message.event.invite != null) { meshes[message.event.meshid].invite = message.event.invite; } else { delete meshes[message.event.meshid].invite; }
2915
+ if (message.event.expireDevs != null) { meshes[message.event.meshid].expireDevs = message.event.expireDevs; } else { delete meshes[message.event.meshid].expireDevs; }
2916
2917
// Check if we lost rights to this mesh in this change.
2918
if (IsMeshViewable(message.event.meshid) == false) {
@@ -4269,7 +4270,7 @@
4270
if (deviceViewSettings.devsCols.indexOf('user') >= 0) { r += '<td style=text-align:center>' + getUserShortStr(node); } // User
4271
if (deviceViewSettings.devsCols.indexOf('ip') >= 0) { r += '<td style=text-align:center>' + (node.ip != null ? node.ip : ''); } // IP address
4272
if (deviceViewSettings.devsCols.indexOf('conn') >= 0) { r += '<td style=text-align:center>' + states.join(' + '); } // Connectivity
4272
- if (deviceViewSettings.devsCols.indexOf('lastseen') >= 0) { r += '<td style=text-align:center;font-size:x-small>'; if (node.conn & 1) { r += "Connected"; } else if (node.lastconnect != null) { r += printDateTime(new Date(node.lastconnect)); } }
4273
+ if (deviceViewSettings.devsCols.indexOf('lastseen') >= 0) { r += '<td style=text-align:center;font-size:x-small>'; if (node.conn > 0) { r += "Connected"; } else if (node.lastconnect != null) { r += printDateTime(new Date(node.lastconnect)); } }
4274
4275
div.innerHTML = r;
4276
} else if ((view == 3) || (view == 5)) {
@@ -5300,7 +5301,7 @@
5301
function powerSort(a, b) { var ap = a.pwr?a.pwr:0; var bp = b.pwr?b.pwr:0; if (ap > bp) return -1; if (ap < bp) return 1; if (ap == bp) { if (showRealNames == true) { if (a.rnamel > b.rnamel) return 1; if (a.rnamel < b.rnamel) return -1; return 0; } else { if (a.namel > b.namel) return 1; if (a.namel < b.namel) return -1; return 0; } } return 0; }
5302
function deviceSort(a, b) { if (a.namel > b.namel) return 1; if (a.namel < b.namel) return -1; return 0; }
5303
function deviceHostSort(a, b) { if (a.rnamel > b.rnamel) return 1; if (a.rnamel < b.rnamel) return -1; return 0; }
5303
- function lastConnectSort(a, b) { var aa = a.lastconnect, bb = b.lastconnect; if (aa == null) { aa = 99999999999999; } if (bb == null) { bb = 99999999999999; } if (a.conn & 1) { aa = 99999999999998; } if (b.conn & 1) { bb = 99999999999998; } if (aa == bb) { return nameSort(a, b); } return (aa - bb); }
5304
+ function lastConnectSort(a, b) { var aa = a.lastconnect, bb = b.lastconnect; if (aa == null) { aa = 99999999999999; } if (bb == null) { bb = 99999999999999; } if (a.conn > 0) { aa = 99999999999998; } if (b.conn > 0) { bb = 99999999999998; } if (aa == bb) { return nameSort(a, b); } return (aa - bb); }
5305
function onSearchFocus(x) { searchFocus = x; }
5306
function clearDeviceSearch() { Q('KvmSearchInput').value = Q('SearchInput').value = ''; Q('DevFilterSelect').value = 0; onOnlineCheckBox(); mainUpdate(1); }
5307
function onMapSearchFocus(x) { mapSearchFocus = x; }
@@ -11489,7 +11490,7 @@
11490
if (Q('d20flag2').checked) { flags += 2; }
11491
}
11492
if (serverinfo.devGroupSessionRecording == 1) { if (Q('d20flag4').checked) { flags += 4; } }
11492
- cmd.expireDevs = 0;
11493
+ var expireDevs = 0;
11494
if (((flags & 1) == 0) && Q('d20expireDevice').checked) { expireDevs = parseInt(Q('d20expireDeviceDays').value); }
11495
meshserver.send({ action: 'editmesh', meshid: currentMesh._id, flags: flags, expireDevs: expireDevs });
11496
}