1
0
mirror of https://github.com/Foltik/Shimapan synced 2024-11-27 21:19:09 -05:00

Extend body verifier to sanitize, regex trim, and length check

This commit is contained in:
Jack Foltz 2018-08-01 12:34:15 -04:00
parent c23c9b345e
commit 21fe0de46d
Signed by: foltik
GPG Key ID: 303F88F996E95541
3 changed files with 19 additions and 11 deletions

View File

@ -50,13 +50,6 @@ const validateInvite = wrap(async (req, res, next) => {
const validateUsername = wrap(async (req, res, next) => { const validateUsername = wrap(async (req, res, next) => {
const username = req.body.username; const username = req.body.username;
if (username.length > config.get('User.Username.maxLength'))
return res.status(422).json({message: 'Username too long.'});
const restrictedRegex = new RegExp(config.get('User.Username.restrictedChars'), 'g');
if (username !== req.sanitize(username).replace(restrictedRegex, ''))
return res.status(422).json({message: 'Username contains invalid characters.'});
const count = await User.countDocuments({username: username}).catch(next); const count = await User.countDocuments({username: username}).catch(next);
if (count !== 0) if (count !== 0)
return res.status(422).json({message: 'Username in use.'}); return res.status(422).json({message: 'Username in use.'});
@ -65,7 +58,13 @@ const validateUsername = wrap(async (req, res, next) => {
}); });
const registerProps = [ const registerProps = [
{name: 'displayname', type: 'string'}, {
name: 'displayname',
type: 'string',
maxLength: config.get('User.Username.maxLength'),
sanitize: true,
restrict: new RegExp(config.get('User.Username.restrictedChars')),
},
{name: 'password', type: 'string'}, {name: 'password', type: 'string'},
{name: 'invite', type: 'string'}]; {name: 'invite', type: 'string'}];
router.post('/register', router.post('/register',

View File

@ -16,6 +16,15 @@ const verifyBody = expectedProps =>
if (prop && expected.instance && !(prop instanceof expected.instance)) if (prop && expected.instance && !(prop instanceof expected.instance))
return res.status(400).json({message: expected.name + ' malformed.'}); return res.status(400).json({message: expected.name + ' malformed.'});
if (prop && expected.maxLength && prop.length > expected.maxLength)
return res.status(422).json({message: expected.name + ' too long.'});
if (prop && expected.sanitize && req.sanitize(prop) !== prop)
return res.status(422).json({message: expected.name + ' contains invalid characters.'});
if (prop && expected.restrict && prop.replace(expected.restrict, '') !== prop)
return res.status(422).json({message: expected.name + ' contains invalid characters.'});
} }
next(); next();
}; };

View File

@ -121,20 +121,20 @@ describe('Authentication', function() {
{displayname: 'user name', password: 'pass', invite: 'code2'} {displayname: 'user name', password: 'pass', invite: 'code2'}
]; ];
const failMsg = 'Username contains invalid characters.'; const failMsg = 'displayname contains invalid characters.';
return Promise.all(users.map(user => verifyRejectedUsername(user, failMsg))); return Promise.all(users.map(user => verifyRejectedUsername(user, failMsg)));
}); });
it('MUST NOT register a username containing HTML', async () => { it('MUST NOT register a username containing HTML', async () => {
await util.createTestInvite(); await util.createTestInvite();
const user = {displayname: 'user<svg/onload=alert("XSS")>', password: 'pass', invite: 'code'}; const user = {displayname: 'user<svg/onload=alert("XSS")>', password: 'pass', invite: 'code'};
return verifyRejectedUsername(user, 'Username contains invalid characters.'); return verifyRejectedUsername(user, 'displayname contains invalid characters.');
}); });
it('MUST NOT register a username with too many characters', async () => { it('MUST NOT register a username with too many characters', async () => {
await util.createTestInvite(); await util.createTestInvite();
const user = {displayname: '123456789_123456789_123456789_1234567', password: 'pass', invite: 'code'}; const user = {displayname: '123456789_123456789_123456789_1234567', password: 'pass', invite: 'code'};
return verifyRejectedUsername(user, 'Username too long.'); return verifyRejectedUsername(user, 'displayname too long.');
}) })
}); });