Working on password recovery
This commit is contained in:
@@ -0,0 +1,106 @@
|
||||
//libraries
|
||||
const nodemailer = require('nodemailer');
|
||||
|
||||
const { accounts, recovery } = require('../database/models');
|
||||
|
||||
//utilities
|
||||
const uuid = require('../utilities/uuid');
|
||||
const validateEmail = require('../utilities/validate-email');
|
||||
|
||||
//auth/recover
|
||||
const route = async (req, res) => {
|
||||
//validate details
|
||||
const validateErr = await validateDetails(req.body);
|
||||
if (validateErr) {
|
||||
return res.status(401).end(validateErr);
|
||||
}
|
||||
|
||||
//recovery token
|
||||
const token = uuid(32);
|
||||
|
||||
//send the recovery email
|
||||
const emailErr = await sendRecoveryEmail(req.body.email, token);
|
||||
if (emailErr) {
|
||||
return res.status(500).send(emailErr);
|
||||
}
|
||||
|
||||
//save the token
|
||||
recovery.upsert({
|
||||
email: req.body.email,
|
||||
token: token
|
||||
});
|
||||
|
||||
//finally
|
||||
res.status(200).send("Validation email sent!");
|
||||
return null;
|
||||
};
|
||||
|
||||
const validateDetails = async (body) => {
|
||||
//basic formatting
|
||||
if (!validateEmail(body.email)) {
|
||||
return 'Invalid email';
|
||||
}
|
||||
|
||||
//check for existing email
|
||||
const emailRecord = await accounts.findOne({
|
||||
where: {
|
||||
email: body.email
|
||||
}
|
||||
});
|
||||
|
||||
if (!emailRecord) {
|
||||
return 'Invalid email';
|
||||
}
|
||||
|
||||
//OK
|
||||
return null;
|
||||
};
|
||||
|
||||
const sendRecoveryEmail = async (email, token) => {
|
||||
const addr = `${process.env.WEB_PROTOCOL}://${process.env.WEB_ADDRESS}/auth/validation?token=${token}`;
|
||||
const msg = `Hello,
|
||||
|
||||
Please visit the following link to reset your password: ${addr}
|
||||
|
||||
If you did not request a password reset, you can safely ignore this message.
|
||||
`;
|
||||
|
||||
let transporter, info;
|
||||
|
||||
//what exactly is a transport?
|
||||
try {
|
||||
transporter = nodemailer.createTransport({
|
||||
host: process.env.MAIL_SMTP,
|
||||
port: 465,
|
||||
secure: true,
|
||||
auth: {
|
||||
user: process.env.MAIL_USERNAME,
|
||||
pass: process.env.MAIL_PASSWORD
|
||||
},
|
||||
});
|
||||
}
|
||||
catch(e) {
|
||||
return `failed to create a mail transport: ${e}`;
|
||||
}
|
||||
|
||||
// send mail with defined transport object
|
||||
try {
|
||||
info = await transporter.sendMail({
|
||||
from: `recovery@${process.env.WEB_ADDRESS}`, //WARNING: google overwrites this
|
||||
to: email,
|
||||
subject: 'Password Recovery',
|
||||
text: msg
|
||||
});
|
||||
}
|
||||
catch(e) {
|
||||
return `failed to send validation mail: ${e}`;
|
||||
}
|
||||
|
||||
if (info.accepted[0] != email) {
|
||||
return 'recovery email failed to send';
|
||||
}
|
||||
|
||||
return null;
|
||||
};
|
||||
|
||||
module.exports = route;
|
||||
Reference in New Issue
Block a user