Account emails are not always lowercase.

Ylian Saint-Hilaire committed Jul 15, 2019 at 10:24 UTC 64f26135e1b39a336ac0c04a2bf9c64beb2dc07b
4 files changed +31 -10
db.js
+7
@@ -96,6 +96,11 @@ module.exports.CreateDB = function (parent, func) {
96 for (var i in docs) {
97 var fixed = false;
98
99 + // Fix email address capitalization
100 + if (docs[i].email && (docs[i].email != docs[i].email.toLowerCase())) {
101 + docs[i].email = docs[i].email.toLowerCase(); fixed = true;
102 + }
103 +
104 // Fix account creation
105 if (docs[i].creation) {
106 if (docs[i].creation > 1300000000000) { docs[i].creation = Math.floor(docs[i].creation / 1000); fixed = true; }
@@ -852,6 +857,7 @@ module.exports.CreateDB = function (parent, func) {
857
858 // Called when a device group has changed
859 function dbMeshChange(meshChange, added) {
860 + if (parent.webserver == null) return;
861 common.unEscapeLinksFieldName(meshChange.fullDocument);
862 const mesh = meshChange.fullDocument;
863
@@ -872,6 +878,7 @@ module.exports.CreateDB = function (parent, func) {
878
879 // Called when a user account has changed
880 function dbUserChange(userChange, added) {
881 + if (parent.webserver == null) return;
882 const user = userChange.fullDocument;
883
884 // Update the user object in memory
meshuser.js
+17 -9
@@ -862,7 +862,11 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
862
863 // Change our own email address
864 if ((domain.auth == 'sspi') || (domain.auth == 'ldap')) return;
865 - if (common.validateEmail(command.email, 1, 256) == false) return;
865 + if (common.validateEmail(command.email, 1, 1024) == false) return;
866 +
867 + // Always lowercase the email address
868 + command.email = command.email.toLowerCase();
869 +
870 if (parent.users[req.session.userid].email != command.email) {
871 // Check if this email is already validated on a different account
872 db.GetUserWithVerifiedEmail(domain.id, command.email, function (err, docs) {
@@ -901,7 +905,11 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
905 // Send a account email verification email
906 if ((domain.auth == 'sspi') || (domain.auth == 'ldap')) return;
907 if (common.validateString(command.email, 3, 1024) == false) return;
904 - if ((parent.parent.mailserver != null) && (parent.users[req.session.userid].email == command.email)) {
908 +
909 + // Always lowercase the email address
910 + command.email = command.email.toLowerCase();
911 +
912 + if ((parent.parent.mailserver != null) && (parent.users[req.session.userid].email.toLowerCase() == command.email)) {
913 // Send the verification email
914 parent.parent.mailserver.sendAccountCheckMail(domain, user.name, user.email);
915 }
@@ -1064,7 +1072,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
1072 if ((command.users[i].user == '~') || (command.users[i].user.indexOf('/') >= 0)) break; // This is a reserved user name
1073 if (common.validateString(command.users[i].pass, 1, 256) == false) break; // Password is between 1 and 256 characters
1074 if (common.checkPasswordRequirements(command.users[i].pass, domain.passwordrequirements) == false) break; // Password does not meet requirements
1067 - if ((command.email != null) && (common.validateEmail(command.users[i].email, 1, 256) == false)) break; // Check if this is a valid email address
1075 + if ((command.users[i].email != null) && (common.validateEmail(command.users[i].email, 1, 1024) == false)) break; // Check if this is a valid email address
1076 userCount++;
1077 }
1078
@@ -1086,7 +1094,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
1094 var newuserid = 'user/' + domain.id + '/' + command.users[i].user.toLowerCase();
1095 var newuser = { type: 'user', _id: newuserid, name: command.users[i].user, creation: Math.floor(Date.now() / 1000), domain: domain.id };
1096 if (domain.newaccountsrights) { newuser.siteadmin = domain.newaccountsrights; }
1089 - if (command.users[i].email != null) { newuser.email = command.users[i].email; if (command.users[i].emailVerified === true) { newuser.emailVerified = true; } } // Email
1097 + if (command.users[i].email != null) { newuser.email = command.users[i].email.toLowerCase(); if (command.users[i].emailVerified === true) { newuser.emailVerified = true; } } // Email, always lowercase
1098 if (command.users[i].resetNextLogin === true) { newuser.passchange = -1; } else { newuser.passchange = Math.floor(Date.now() / 1000); }
1099 if ((command.users[i].groups != null) && (common.validateStrArray(command.users[i].groups, 1, 32))) { newuser.groups = command.users[i].groups; } // New account are automatically part of our groups.
1100
@@ -1131,7 +1139,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
1139 else if (common.validateString(command.pass, 1, 256) == false) { err = 'Invalid password'; } // Password is between 1 and 256 characters
1140 else if (command.username.indexOf('/') >= 0) { err = 'Invalid username'; } // Usernames can't have '/'
1141 else if (common.checkPasswordRequirements(command.pass, domain.passwordrequirements) == false) { err = 'Invalid password'; } // Password does not meet requirements
1134 - else if ((command.email != null) && (common.validateEmail(command.email, 1, 256) == false)) { err = 'Invalid email'; } // Check if this is a valid email address
1142 + else if ((command.email != null) && (common.validateEmail(command.email, 1, 1024) == false)) { err = 'Invalid email'; } // Check if this is a valid email address
1143 else {
1144 newusername = command.username;
1145 newuserid = 'user/' + domain.id + '/' + command.username.toLowerCase();
@@ -1171,7 +1179,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
1179 var newuser = { type: 'user', _id: newuserid, name: newusername, creation: Math.floor(Date.now() / 1000), domain: domain.id };
1180 if (command.siteadmin != null) { newuser.siteadmin = command.siteadmin; }
1181 else if (domain.newaccountsrights) { newuser.siteadmin = domain.newaccountsrights; }
1174 - if (command.email != null) { newuser.email = command.email; if (command.emailVerified === true) { newuser.emailVerified = true; } } // Email
1182 + if (command.email != null) { newuser.email = command.email.toLowerCase(); if (command.emailVerified === true) { newuser.emailVerified = true; } } // Email
1183 if (command.resetNextLogin === true) { newuser.passchange = -1; } else { newuser.passchange = Math.floor(Date.now() / 1000); }
1184
1185 parent.users[newuserid] = newuser;
@@ -1188,7 +1196,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
1196 if (command.email == null) {
1197 event = { etype: 'user', username: newusername, account: parent.CloneSafeUser(newuser), action: 'accountcreate', msg: 'Account created, username is ' + command.username, domain: domain.id };
1198 } else {
1191 - event = { etype: 'user', username: newusername, account: parent.CloneSafeUser(newuser), action: 'accountcreate', msg: 'Account created, email is ' + command.email, domain: domain.id };
1199 + event = { etype: 'user', username: newusername, account: parent.CloneSafeUser(newuser), action: 'accountcreate', msg: 'Account created, email is ' + command.email.toLowerCase(), domain: domain.id };
1200 }
1201 if (parent.db.changeStream) { event.noact = 1; } // If DB change stream is active, don't use this event to create the user. Another event will come.
1202 parent.parent.DispatchEvent(targets, obj, event);
@@ -1220,7 +1228,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
1228
1229 // Validate and change email
1230 if (domain.usernameisemail !== true) {
1223 - if (common.validateString(command.email, 1, 256) && (chguser.email != command.email)) { chguser.email = command.email; change = 1; }
1231 + if (common.validateString(command.email, 1, 1024) && (chguser.email != command.email)) { chguser.email = command.email.toLowerCase(); change = 1; }
1232 }
1233
1234 // Make changes
@@ -2259,7 +2267,7 @@ module.exports.CreateMeshUser = function (parent, db, ws, req, args, domain, use
2267 }
2268
2269 // Perform email invitation
2262 - parent.parent.mailserver.sendAgentInviteMail(domain, user.name, command.email, command.meshid, command.name, command.os, command.msg, command.flags, command.expire);
2270 + parent.parent.mailserver.sendAgentInviteMail(domain, user.name, command.email.toLowerCase(), command.meshid, command.name, command.os, command.msg, command.flags, command.expire);
2271
2272 // Send a response if needed
2273 if (command.responseid != null) { try { ws.send(JSON.stringify({ action: 'inviteAgent', responseid: command.responseid, result: 'ok' })); } catch (ex) { } }
package.json
+1 -1
@@ -1,6 +1,6 @@
1 {
2 "name": "meshcentral",
3 - "version": "0.3.7-q",
3 + "version": "0.3.7-r",
4 "keywords": [
5 "Remote Management",
6 "Intel AMT",
webserver.js
+6
@@ -740,6 +740,9 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) {
740 const domain = checkUserIpAddress(req, res);
741 if ((domain == null) || (domain.auth == 'sspi') || (domain.auth == 'ldap')) { res.sendStatus(404); return; }
742
743 + // Always lowercase the email address
744 + if (req.body.email) { req.body.email = req.body.email.toLowerCase(); }
745 +
746 // If the email is the username, set this here.
747 if (domain.usernameisemail) { req.body.username = req.body.email; }
748
@@ -916,6 +919,9 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) {
919 const domain = checkUserIpAddress(req, res);
920 if ((domain == null) || (domain.auth == 'sspi') || (domain.auth == 'ldap') || (obj.args.lanonly == true) || (obj.parent.certificates.CommonName == null) || (obj.parent.certificates.CommonName.indexOf('.') == -1)) { res.sendStatus(404); return; }
921
922 + // Always lowercase the email address
923 + if (req.body.email) { req.body.email = req.body.email.toLowerCase(); }
924 +
925 // Get the email from the body or session.
926 var email = req.body.email;
927 if ((email == null) || (email == '')) { email = req.session.tokenemail; }