How can i used db.findAndUpdate table user and change my balance from previous amount to newer?
i have try to get balance and the result it show nothing, now i'm confuse to write in findAndUpdate. here's my code:
api:
app.post('/api/account/transfer', (req, res, next) => {
const { body } = req;
const {
sender,
receiver,
amount,
user,
balance,
} = body;
if (!sender) {
return res.send({
success: false,
message: 'Error: Sender cannot be blank!'
});
}
if (!receiver) {
return res.send({
success: false,
message: 'Error: Receiver cannot be blank!'
});
}
if (!amount) {
return res.send({
success: false,
message: 'Error: Fill Amount!'
});
} else if(balance < amount || balance == 0) {
return res.send({
success: false,
message: 'Insufficient funds!'
});
}
//save the new transaction
const newTransaction = new Transaction();
newTransaction.sender = sender;
newTransaction.receiver = receiver;
newTransaction.amount = amount;
newTransaction.save( (err, transaction) => {
if(err) {
return res.send({
success: false,
message: 'Error: Server error.'
});
}else{
return res.send({
success: true,
message: 'Transfer Success!'
});
}
});
//update user balance
User.findOneAndUpdate({
});
and here's the screenshoot:
so what i want is, if i'm as a receiver my balance will be increase.
Try this, the findOneAndUpdate operation does not wait for save operation to complete.
app.post('/api/account/transfer', (req, res, next) => {
const {
body
} = req;
const fields = ['sender', 'receiver', 'amount', 'balance'];
fields.forEach((field) => {
if (!body[field]) {
return res.send({
success: false,
message: 'Error: ' + field + ' cannot be blank!'
});
}
})
if (body.balance < body.amount || body.balance == 0) {
return res.send({
success: false,
message: 'Insufficient funds!'
});
}
//save the new transaction
let newTransaction = new Transaction();
// newTransaction = Object.assign(newTransaction, body); // If you want to copy all params from body to newTransaction
newTransaction.sender = body.sender;
newTransaction.receiver = body.receiver;
newTransaction.amount = body.amount;
newTransaction.save((err, transaction) => {
if (err) {
return res.send({
success: false,
message: 'Error: Server error.'
});
} else {
//update user balance
User.findOneAndUpdate({
/*query*/
}, {
/*body*/
}, (err, data) => {
if (err)
return res.send({
success: false,
message: 'Error: Server error.'
});
return res.send({
success: true,
message: 'Transfer Success!'
});
});
}
});
});
Related
I am trying to implement 2fa using the otplib package and it's working fine on the local machine but not on the live server.
Can somebody help me?
on live, I am getting an invalid 2FA.
Here is the code:
exports.enableTwoFactorAuthentication = async (req, res) => {
try {
let data = req.body;
console.log("data: ", data)
const { userId, one_time_password } = data;
const user = await CRMUser.findById(userId);
const { tfa_auth_secret_key } = user;
console.log('user', tfa_auth_secret_key, user)
console.log("authenticator.check(one_time_password, tfa_auth_secret_key): ",authenticator.check(one_time_password, tfa_auth_secret_key))
if (!one_time_password || !authenticator.check(one_time_password, tfa_auth_secret_key)) {
return res.status(200).send({ success: false, message: 'Invalid 2FA Code.'});
}
else {
user.tfa_auth_status = true;
await user.save();
return res.status(200).json({ success: true, message: '2FA enabled successfully.', tfa_auth_status: true, secretKey: user.tfa_auth_secret_key, qrImage: user.tfa_auth_qr_image });
}
} catch (error) {
return res.status(500).json({ success: false, message: error.message })
}
};
While calling the service layer from the controller, the response is not waiting for the result in the controller.
So, I am not getting correct response (return value) from the service layer.
controller =>
const { serviceCreateData } = require("../services/data.servises");
module.exports.createData = async (req, res) => {
try {
const result = await serviceCreateData(req.body);
if (result) {
res.status(result.status).json({ message: result.msg });
}
} catch (error) {
res.status(500).json({ message: "Server is not responding!!" });
}
};
Service layer
/** #format */
const dataModel = require("../models/data.model");
module.exports.serviceCreateData = async (insertedData) => {
const { name, email, username, phone, address } = insertedData;
try {
dataModel.findOne({ email }).exec(async (error, user) => {
if (user) {
return { success: false, status: 400, msg: "Data already exist!!" };
} else {
const _data = new dataModel({
name,
email,
username,
phone,
address,
});
await _data.save((error, data) => {
if (error) {
return {
success: false,
status: 400,
msg: "Something went wrong!!",
};
}
if (data) {
return {
success: true,
status: 201,
body: "Data inserted successfully!!",
};
}
});
}
});
} catch (error) {
return { success: false, status: 400, msg: "Something went wrong!!" };
}
};
I need to return the value from the services layer to controller, so that I can send it to the client.
Right now I am getting error responses from the controller only.
All the help is appreciated.
I am writing an Express endpoint in Typescript to update a user's password in the database, but having some trouble with multiple queries/synchronous code.
My problem is right now I am trying to await the return of a function but it doesn't seem to be awaiting.
My route looks like this:
router.put("/:userId", validateUser, async (req: any, res: Response) => {
const result: any = await updatePassword(req.body.password, req.body.confirmPassword, req.params.userId);
console.log(result) //LOGS UNDEFINED????
if (result.status !== 200) res.status(result.status).send({ message: result.message, code: result.code });
res.send("Success!");
});
and that updatePassword function looks like this:
const updatePassword = async (password: string, confirmPassword: string, userId: string) => {
if (password !== confirmPassword) {
return { status: 409, message: Errors.mismatchingPasswordMessage, code: Errors.mismatchingPasswordCode };
}
const hashedPassword = bcrypt.hashSync(password, 10);
//update the password in the DB
pool.query("UPDATE users SET password = ? WHERE userId = ?", [hashedPassword, userId], (err: MysqlError, result: any) => {
if (err) {
console.log(err);
return { status: 500, message: err.message, code: err.code };
}
if (result.changedRows !== 1) {
return { status: 500, message: "Password could not be updated!" };
}
return { status: 200 };
});
}
Why is this the route not correctly awaiting the result of updatePassword??
Thanks in advance for any help.
The problem is, you're mixing async/await and callback style in this part
pool.query("UPDATE users SET password = ? WHERE userId = ?", [hashedPassword, userId], (err: MysqlError, result: any) => {
if (err) {
console.log(err);
return { status: 500, message: err.message, code: err.code };
}
if (result.changedRows !== 1) {
return { status: 500, message: "Password could not be updated!" };
}
return { status: 200 };
});
The function updatePassword jumps directly to the next line after this block, which is nothing. So it returns undefined.
You need to replace this block with async/await code. Something like :
try {
const result = await pool.query("UPDATE users SET password = ? WHERE userId = ?", [hashedPassword, userId]);
if (result.changedRows !== 1) {
return { status: 500, message: "Password could not be updated!" };
}
return { status: 200 };
}
catch (err){
console.log(err);
return { status: 500, message: err.message, code: err.code };
}
exports.updateUsuarioByEmail = function (req, res) {
console.log('updateUsuarioByEmail');
console.log("PARAM ID" + req.params.email);
return Usuario.find({ email: req.params.email }, function(err, usuario) {
if(!usuario) {
res.statusCode = 404;
return res.send({ error: 'Not found' });
}
if (req.body.email != null) usuario.email = req.body.email;
if (req.body.password != null) usuario.password = req.body.password;
if (req.body.listaCardsSorting != null) usuario.listaCardsSorting = req.body.listaCardsSorting;
return usuario.save(function(err) {
if(!err) {
console.log('Updated usuario');
return res.send({ status: 'OK', usuario:usuario });
} else {
if(err.name == 'ValidationError') {
res.statusCode = 400;
res.send({ error: 'Validation error' });
} else {
res.statusCode = 500;
res.send({ error: 'Server error' });
}
console.log('Internal error(%d): %s',res.statusCode,err.message);
}
res.send(usuario);
});
});
};
The error after to execute is :
I believe that the error is the line "return usuario.save(function(err)..."
find return an Array (list of documents) . you can't do save on an array object. Instead try findOne if your email field is unique.
findOne returns a single document, so you can save that.
Replace
Usuario.find({ email: req.params.email }, function(err, usuario)
with :
Usuario.findOne({ email: req.params.email }, function(err, usuario)
To update a model it's much easier to use the findOneAndUpdate() update API. The method finds a matching document, updates it according to the update arg, passing any options, and returns the found document (if any) to the callback. The query executes immediately if callback is passed.
The syntax is:
Model#findOneAndUpdate([conditions], [doc], [options], [callback])
Parameters:
[conditions] <Object> - the query to match
[doc] <Object> - the document to update
[options] <Object> - update options
[callback] <Function> - callback
For example, the above function can be re-written to use the findOneAndUpdate() method as:
exports.updateUsuarioByEmail = function (req, res) {
console.log('updateUsuarioByEmail');
console.log("PARAM ID" + req.params.email);
var doc = {},
conditions = { "email": req.params.email },
options = { "new": true };
if (req.body.email != null) doc.email = req.body.email;
if (req.body.password != null) doc.password = req.body.password;
if (req.body.listaCardsSorting != null)
doc.listaCardsSorting = req.body.listaCardsSorting;
Usuario.findOneAndUpdate(
conditions,
doc,
options,
function(err, usuario) {
if(!err) {
console.log('Updated usuario');
return res.send({
status: 'OK',
usuario: usuario
});
} else {
if(err.name == 'ValidationError') {
res.statusCode = 400;
res.send({ error: 'Validation error' });
} else {
res.statusCode = 500;
res.send({ error: 'Server error' });
}
console.log('Internal error(%d): %s',res.statusCode,err.message);
}
}
)
};
Here remained the solution:
exports.updateUsuarioByEmail = function (req, res) {
console.log('updateUsuarioByEmail');
return Usuario.findOne({email: req.params.email}, function (err, usuario) {
usuario.email = req.body.email || usuario.email;
usuario.password = req.body.password || usuario.password;
usuario.listaCardsSorting = req.body.listaCardsSorting || usuario.listaCardsSorting;
return usuario.save(function (err) {
if (!err) {
console.log('Updated');
return res.send({status: 'OK', usuario: usuario});
} else {
if (err.name == 'ValidationError') {
res.statusCode = 400;
res.send({error: 'Validation error'});
} else {
res.statusCode = 500;
res.send({error: 'Server error'});
}
console.log('Internal error(%d): %s', res.statusCode, err.message);
}
res.send(usuario);
});
});
};
I got a small problem. With this code I updating a existing document in mongodb using node.js and mongoose
router.route('/profile/:profile_id/:session_key')
.put(function(req, res) {
if (req._body == true && req.is('application/json') == 'application/json' ) {
// Get the profile to update
Profile.findOne({ profile_id: req.params.profile_id }, function(err, t_profile) {
if (err) {
res.send(err);
} else {
if(!t_profile) {
res.json({ status: 'CANT FIND PROFILE TO UPDATE' });
} else {
if (t_profile.session_key == req.params.session_key) {
// Update profile with new data
t_profile.name = setReq( t_profile.name, req.body.name );
t_profile.sex = setReq( t_profile.sex, req.body.sex );
t_profile.birthdate = setReq( t_profile.birthdate, req.body.birthdate );
t_profile.country = setReq( t_profile.country, req.body.country );
t_profile.password = setReq( t_profile.password, req.body.password );
// save updatd profile
t_profile.save( { _id: profile._id }, function(save_err, u_profile) {
if (save_err) {
res.json({ status: 'DB ERROR' });
} else {
res.json({ status: 'OK' });
}
});
} else {
res.json({ status: 'NOT LOGGED IN' });
}
//res.json({ status: "THIS RUNS"});
}
}
});
} else {
res.json({ status: 'ERROR', msg: 'Not application/json type'});
}
});
But my function inserted as a parameter in the .save() function neve runs, i need to uncomment the line res.json({ status: "THIS RUNS"}); to get som response back to the client. Why is not res.json({ status: 'DB ERROR' }); or res.json({ status: 'OK' }); sent back?
Stupid error, t_profile.save(function(save_err, u_profile) {...} fixed it.