I need to hash the password before insert in the DB I have the function of bcrypt but I don't know how to get it into a const and use it for make the insert into mysql.
I'm using bcrypt for it, so what's the method I should follow to get the password hashed?
async postCompletedetails(req, res) {
const company = req.params.company;
const name = req.params.name;
const password = req.params.password;
bcrypt.hash(password, saltRounds, (err, hash) => {
});
if (
company !== undefined &&
name !== undefined &&
password !== undefined
) {
const { token } = req.headers;
const decoded = jwt.verify(token, process.env.JWT_ACCOUNT_ACTIVATION);
const id = decoded.id;
const update = await pool.query(
`UPDATE user SET Name_user= '${name}', password= '${password}' WHERE ID_user = ${id}`
);
const incompany = await pool.query(
`INSERT INTO company (Name_company) VALUES ('${company}') `
);
const inrelcompany = await pool.query(
`INSERT INTO rel_company_user (ID_company, ID_user) VALUES (LAST_INSERT_ID(), ${id})`
);
return res.json({
code: 200,
message: "todo bien... todo correcto y yo que me alegro",
password,
});
} else {
return res.json({
code: 400,
message: "Bro hiciste algo mal",
});
}
}
async postCompletedetails(req, res) {
const company = req.params.company;
const name = req.params.name;
const password = req.params.password;
const saltRounds = 10;
if (
company !== undefined &&
name !== undefined &&
password !== undefined
) {
const hashPass = bcrypt.hash(password, saltRounds, (err, hash) => {
if (err)
{
return err;
}
return hash;
});
hashPass // this will be what you insert into the database.
}
Ok, I have it but the problem is that I can't get the hashed password, hassPass have de value undefined, what I should change?
const hashPass = await bcrypt.genSalt(saltRounds, function (err, salt) {
if (err) {
throw err
} else {
bcrypt.hash(password, salt, function(err, hash) {
if (err) {
throw err
} else {
console.log(hash)
}
})
}
})
The password is being hashed, I now it for the console.log
Related
I created a user update controller in my application, but the problem is that when testing this in postman, I can't just send information that I want to edit without having to pass the password along, which is being rendered asynchronously with the bcryptjs
error:
Error: Illegal arguments: undefined, string
at Object.bcrypt.hashSync (/home/pc/api_foodelivery/node_modules/bcryptjs/dist/bcrypt.js:189:19)
at exports.update (/home/pc/api_foodelivery/src/controllers/UserController/UpdateUser.js:16:37)
at processTicksAndRejections (node:internal/process/task_queues:96:5)
const db = require('../../models/index');
const bcrypt = require('bcryptjs');
exports.update = async (req, res) => {
const { id } = req.params;
const { firstName, lastName, email, password, phoneNumber } = req.body;
try {
const user = await db.User.findOne({ where: { id } });
if (!user) {
return res.status(401).json('User does not exist');
}
const hashPassword = bcrypt.hashSync(password, 8);
await user.update({
firstName,
lastName,
email,
password: hashPassword,
phoneNumber,
});
return res.status(200).json('User updated!');
} catch (err) {
return console.log(err);
}
}
From what I understand, this error occurs because I am not passing anything to my hashPassword, but how can I make this not mandatory when updating my database user?
const db = require('../../models/index');
const bcrypt = require('bcryptjs');
exports.update = async (req, res) => {
const { id } = req.params;
const { firstName, lastName, email, password, phoneNumber } = req.body;
try {
const user = await db.User.findOne({ where: { id } });
if (!user) {
return res.status(401).json('User does not exist');
}
// You need to check here if user wants to update password or not
const updatedUser = {
firstName,
lastName,
email,
phoneNumber
} // You may further check for every filed if not undefined here
if(password && password !== "") {
const hashPassword = bcrypt.hashSync(password, 8);
updatedUser.password = hashPassword
}
await user.update(updatedUser);
return res.status(200).json('User updated!');
} catch (err) {
return console.log(err);
}
}
I'm trying to let the user sign in using either email or username, I'm trying this code in Postman and each time I try it gives me this error:
"success":false,"status":500,"message":"data and hash arguments
required","stack":"Error: data and hash arguments required\n at
Object.compare
Auth.js Configurations:
const emailRegex = "/^\w+([\.-]?\w+)*#\w+([\.-]?\w+)*(\.\w{2,3})+$/";
router.post("/login", async (req, res, next) => {
const isEmail = String(req.body.emailOrUsername).match(emailRegex);
try {
if (!req.body.password) {
return next(createError(400, "Invalid password"));
}
let user;
if (isEmail) {
user = await User.findOne({ where: { email: req.body.emailOrUsername } });
} else {
user = await User.findOne({ where: { username: req.body.emailOrUsername } });
};
if (!user) return next(createError(404, "User not found!"));
const isPasswordCorrect = await bcrypt.compare(
req.body.password,
user.password
);
if (!isPasswordCorrect) return next(createError(400, "Wrong password!"));
const { password, ...others } = user._doc;
res.status(200).json(others);
} catch (err) {
next(err);
}
});
I'm not sure what I'm missing here!
I'm having issues converting this setup: https://github.com/WebDevSimplified/Nodejs-Passport-Login
to push and pull user data from a mysql database. I've got the registration to work just fine, but I appear to be having difficulty with the login portion. I converted this portion from lines 14-18 of server.js
initializePassport(
passport,
email => users.find(user => user.email === email),
id => users.find(user => user.id === id)
)
to look like this
initializePassport(
passport,
email => db.getConnection( async (err, connection) => {
if (err) throw (err)
const sqlSearch = "SELECT * FROM users WHERE email = ?"
const searchQuery = mysql.format(sqlSearch, [email])
await connection.query(searchQuery, async (err, result) => {
connection.release()
if (err) throw (err)
console.log(result[0].email)
return result[0].email
})
}),
id => db.getConnection( async (err, connection) => {
if (err) throw (err)
const sqlSearch = "SELECT * FROM users WHERE id = ?"
const searchQuery = mysql.format(sqlSearch, [id])
await connection.query(searchQuery, async (err, result) => {
connection.release()
if (err) throw (err)
console.log(result[0].id)
return result[0].id
})
})
)
Basically, the initial setup found the relevant data from an array called "users", so I figured I could do the same with the mysql database. I have not changed the passport-config.js file, as I figured it didn't need it, but now I'm not so sure.
During login, the terminal logs the correct input email on login as per my modifications, but it never gets to the id portion of this. Also, it throws the programmed message "No user with that email" as found in line 8 of passport-config.js.
The rest of the code I have in my file is basically the same except for the database connection which looks like this (all the stuff references a .env file that has all the correct params):
const DB_HOST = process.env.DB_HOST
const DB_USER = process.env.DB_USER
const DB_PASSWORD = process.env.DB_PASSWORD
const DB_DATABASE = process.env.DB_DATABASE
const DB_PORT = process.env.DB_PORT
const mysql = require("mysql")
const db = mysql.createPool({
connectionLimit: 100,
host: DB_HOST,
user: DB_USER,
password: DB_PASSWORD,
database: DB_DATABASE,
port: DB_PORT
})
and the registration post method which looks like this:
app.post('/register', checkNotAuthenticated, async (req, res) => {
try {
const id = Date.now().toString()
const fName = req.body.firstName
const lName = req.body.lastName
const email = req.body.email
const password = await bcrypt.hash(req.body.password, 10)
db.getConnection( async (err, connection) => {
if (err) throw (err)
const sqlSearch = "SELECT * FROM users WHERE fName = ?"
const searchQuery = mysql.format(sqlSearch, [fName])
const sqlInsert = "INSERT INTO users VALUES (?,?,?,?,?)"
const insertQuery = mysql.format(sqlInsert,[id, fName, lName, email, password])
await connection.query (searchQuery, async (err, result) => {
if (err) throw (err)
console.log("------> Search Results")
console.log(result.length)
if (result.length != 0) {
connection.release()
console.log("------> User already exists")
}
else {
await connection.query (insertQuery, (err, result)=> {
connection.release()
if (err) throw (err)
console.log ("--------> Created new User")
console.log(result.insertId)
})
}
}) //end of connection.query()
}) //end of db.getConnection()
res.redirect('/login')
} catch {
res.redirect('/register')
}
})
As I said, I have no issues with the registration. The connection is successful, and subsequent inspection of the users table in the mysql terminal (I'm using Mac), the data is being stored correctly. How do I proceed here?
Looks like an issue with the return in initializePassport function.
When you return result[0].email or return result[0].id it returns out of the inner callback function of connection.query() not the outer function.
This may fix it:
initializePassport(
passport,
(email) =>
db.getConnection(async (err, connection) => {
if (err) throw err;
const sqlSearch = "SELECT * FROM users WHERE email = ?";
const searchQuery = mysql.format(sqlSearch, [email]);
// return out of db.getConnection()
return connection.query(searchQuery, async (err, result) => {
connection.release();
if (err) throw err;
console.log(result[0].email);
// return out of connection.query()
return result[0].email;
});
}),
(id) =>
db.getConnection(async (err, connection) => {
if (err) throw err;
const sqlSearch = "SELECT * FROM users WHERE id = ?";
const searchQuery = mysql.format(sqlSearch, [id]);
// return out of db.getConnection()
return connection.query(searchQuery, async (err, result) => {
connection.release();
if (err) throw err;
console.log(result[0].id);
// return out of connection.query()
return result[0].id;
});
})
);
Can anyone explain to me why I'm getting this error? Here's my code where I'm getting this error. I assume it's becuase of the imports/exports in my code?
emailController
const User = require("../models/User")
const jwt = require("jsonwebtoken")
const { transporter, getResetPasswordURL, resetPasswordTemplate } = require("../utils/mailer")
module.exports = {
createOneTimeTokenAndSendMail: async (req, res) => {
const email = req.params.email
try {
const user = await User.findOne({ email })
if (!user) {
return res.status(404).json({ error: "No user with that email "})
}
const hashedPassword = user.password
const createdAt = user.createdAt
const userId = user._id
const secret = hashedPassword + "-" + createdAt
const token = jwt.sign({ userId }, secret, {
expiresIn: 3600
})
const url = getResetPasswordURL(user, token)
const emailTemplate = resetPasswordTemplate(user, url)
const sendEmail = () => {
transporter.sendMail(emailTemplate, (err, info) => {
if (err) {
res.status(500).json("Error sending email")
}
console.log("email sent", info.response)
})
}
sendEmail()
} catch (error) {
res.status(500).json({ error })
}
}
}
mailer
const User = require("../models/User")
const jwt = require("jsonwebtoken")
const {
transporter,
getResetPasswordURL,
resetPasswordTemplate
} = require("../utils/mailer")
module.exports = {
createOneTimeTokenAndSendMail: async (req, res) => {
const email = req.params.email
try {
const user = await User.findOne({ email })
if (!user) {
return res.status(404).json({ error: "No user with that email " })
}
const hashedPassword = user.getPassword
const createdAt = user.createdAt
const userId = user._id
const secret = hashedPassword + "-" + createdAt
const token = jwt.sign({ userId }, secret, {
expiresIn: 3600
})
const url = getResetPasswordURL(user, token)
const emailTemplate = resetPasswordTemplate(user, url)
const sendEmail = () => {
transporter.sendMail(emailTemplate, (err, info) => {
if (err) {
res.status(500).json("Error sending email")
}
console.log("email sent", info.response)
})
}
sendEmail()
} catch (error) {
res.status(500).json({ error })
}
}
}
This is the route which is throwing the above error:
router.post("/reset-password/:email", emailController.createOneTimeTokenAndSendMail)
I have been dealing with errors like these constantly, so I'd like to clear my doubts once and for all.
I have an error while trying to post for login in postman.. but an error shown cannot read property username,this is my code
This is the Controllers
var connection = require('../../config/db');
function Todo() {
this.create = function (req, res, next) {
var username = req.body.username;
var password = req.body.password;
connection.acquire(function (err, con) {
con.query('SELECT s.id, s.username, s.sls_nama, s.password, g.id as id_group, g.title FROM salesmen s, groups g WHERE g.id = s.group_id AND username = ?', [username], function (error, results, fields) {
if (error) throw error;
if (results.length == 0) {
// connected!;
if (password == results[0].password) {
results[0]['status'] = "Success"
res.json(results[0]);
res.status(200).send();
} else {
results[0]['status'] = "Wrong Password"
res.json(results[0]);
res.status(200).send();
}
} else {
res.status(401).json({
message: "Wrong password or username"
});
}
});
});
}
}
module.exports = new Todo();
This is the Routers
var login = require('../controllers/login');
module.exports = {
configure: function(app) {
app.route('/login').post(login.create);
}
};
this is the error shown in postman
In your where clause, since you have added alias for your table you must have s.username = ? instead of username = ?.
SELECT s.id, s.username, s.sls_nama, s.password, g.id as id_group, g.title FROM salesmen s, groups g WHERE g.id = s.group_id AND s.username = ?