NodeJS Express REST API insert into MYSQL error - mysql

Hi I am trying to insert a record into a MySQL DB from a post (using postman to test) for a REST API. I keep receiving a server error. Here is my code (using async and await and expecting a promise in return). Here is the router:
* Creates a new user.
*/
router.post('/', async (req, res, next) => {
const options = {
body: req.body
};
try {
const result = await user.createUser(options);
res.status(result.status || 200).send(result.data);
} catch (err) {
next(err);
}
});
And here is the Service (UPDATED - STILL ERROR):
sql = "INSERT INTO users (AccountHolderUserID, isSubUser, parentUsersID, appBrand, accessLevel, accessToken, tempPassword, email, firstName, lastName) VALUES ?";
values = [
[options.body.AccountHolderUserID, options.body.isSubUser, options.body.parentUsersID, options.body.appBrand, options.body.accessLevel, options.body.accessToken, options.body.tempPassword, options.body.email, options.body.firstName, options.body.lastName]
];
console.log(values);
pool.query(sql, [values], function (error, result, fields) {
if (error) {
reject(new ServerError({
status: 500, // Or another error code.
error: 'Server Error' // Or another error message.;
}));
return
}
resolve({
status: 200,
data: result
});
})
});
}
I added a console log right before the pool.query, and here is the response when I try to post. Data is making it from the form to the query, but getting an Cannot convert object to primitive value Error???
App listening on port 8082!
[
[
'1234, ',
'true,',
'1,',
'1,',
'1,',
'1312,',
'1234,',
'notifications#answeringmobile.com,',
'Nancy,',
'Flannagan'
]
]
TypeError: Cannot convert object to primitive value
Please let me know if anyone knows what I am doing wrong. Thank you!

I think MySQL expects each individual value to have its own question mark. You are passing an array of values expecting that it will substitute the whole VALUES clause, but AFAIK it has never worked this way. The error message says that it expects a primitive value and not an object (not an array, it probably wanted to say).
Try this:
sql = "INSERT INTO users " +
"(AccountHolderUserID, isSubUser, parentUsersID, appBrand, " +
" accessLevel, accessToken, tempPassword, email, " +
" firstName, lastName) " +
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
values = [
options.body.AccountHolderUserID, options.body.isSubUser,
options.body.parentUsersID, options.body.appBrand,
options.body.accessLevel, options.body.accessToken,
options.body.tempPassword, options.body.email,
options.body.firstName, options.body.lastName
];
pool.query(sql, values, ......); // note: just values, no extra square brackets

SOLVED AS FOllOWS:
/**
* #param {Object} options
* #param {Object} options.body Created user object
* #throws {Error}
* #return {Promise}
*/
module.exports.createUser = async (options) => {
return new Promise((resolve, reject) => {
const User = {
"AccountHolderUserID": options.body.ctiAccountHolderUserID,
"isSubUser": options.body.isSubUser,
"parentUsersID": options.body.parentUsersID,
"appBrand": options.body.appBrand,
"accessLevel": options.body.accessLevel,
"accessToken": options.body.accessToken,
"tempPassword": options.body.tempPassword,
"email": options.body.email,
"firstName": options.body.firstName,
"lastName": options.body.lastName
}
console.log(User);
pool.query('INSERT INTO users set ?', User, function (error, result, fields) {
if (error) {
reject(new ServerError({
status: 500, // Or another error code.
error: 'Server Error' // Or another error message.;
}));
return
}
resolve({
status: 200,
data: result
});
})
});
}

Related

Data inserted in MYSQL DB from Node.js is undefined

When I insert data into my DB it says that it was successful but upon checking my DB, all of my fields are null. I am getting undefined values on my firstName,lastName, mobile, and email columns.
I'm really having a hard time debugging as I'm pretty new to JS. I hope anyone can point out what's the problem.
This is the model for Guest
var Guest = function(guest) {
this.firstName = guest.firstName;
this.lastName = guest.lastName;
this.mobile = guest.mobile;
this.email = guest.email;
}
// Insert Guest Data to DB
Guest.createGuest = (guestRequestData, result) => {
db.query('INSERT INTO guest SET ? ', guestRequestData, (error, response) => {
if(error){
console.log('Error while inserting data');
result(null, error);
}else{
console.log('Guest created successfully');
result(null, response);
}
})
}
module.exports = Guest;
And this the controller
// Create New Guest
exports.createNewGuest = (request, response) => {
const guestRequestData = new GuestModel(request.body);
console.log('Request Data', guestRequestData);
// Check Null
if(request.body.constructor === Object && Object(request.body).length === 0){
response.send(400).send({success: false, message: 'Please fill all fields'});
}else{
GuestModel.createGuest(guestRequestData, (error, guest) => {
if(error)
response.send(error);
response.json({status: true, message: 'Guest Created Successfully', data: guest.insertId})
})
}
}
There is a clear example how to insert data into MySQL database using node.js: https://www.mysqltutorial.org/mysql-nodejs/insert/
So in your case would look something like this:
db.query('INSERT INTO guest (firstName, lastName, mobile, email) VALUES (?, ?, ?, ?)', guestRequestData, (error, response) => {
if(error){
console.log('Error while inserting data');
result(null, error);
}else{
console.log('Guest created successfully');
result(null, response);
}
})
where the guestRequestData has the following structure:
["Your first name", "Your last name", "Your mobile", "Your email"]
Make sure you convert the guestRequestData to this format.

Node.js post API is not working with MySQL database?

I am trying to make a post API using Node.js using MySQL database, API is giving no response only throwing error - code: 204
I am inserting data using Postman -
{
"articleid":"1233wawdasyyyd4",
"userid": "123uu"
}
In MySQL table there are 4 fields.
id(unique and incrementing) articleid (varchar) userid (varchar) datetime (current timestamp)
var deletelog = (req, res) => {
const articleid = req.body.articleid;
const userid = req.body.userid;
var sql = `INSERT INTO deletearticles_log (articleid, userid)
VALUES ('"+articleid+"', '"+userid+"')`;
connection.query(sql,[articleid, userid], function (error, results, fields) {
if (error) {
res.send({
"code":400,
"failed":"error ocurred",
"error": error
})
}else{
if(results.length >0){
res.send({
"code":200,
result : results
});
}
else{
res.send({
"code":204,
"success":"Record insertion Failed!"
});
}
}
});
}
I don't figured out what's the issue in this code, I appreciate if you could help me, Cheers!!
There are parameters passed for the query [articleid, userid], yet no parameters appear in the SQL. Replace the concatenation in the SQL with question marks.
var sql = `INSERT INTO deletearticles_log (articleid, userid) VALUES (?, ?)`;

User entries not updating in database

I am using postman to send a request and I see Success message but in the database, it's not updated at all.
PostMAN request
database Snap shot
update services object: from this file I have used a database query to insert data in the database and set callBack funtion
const pool = require('../../config/database')
module.exports = {
updateUser: (data, callBack) => {
pool.query(
`UPDATE users SET firstName=?,email=?,password=?,lastName=?,phoneNumber=?, sex=? WHERE id=?`, [
data.firstName,
data.email,
data.password,
data.lastName,
data.phoneNumber,
data.sex,
data.id
], (error, results, fields) => {
if (error) {
return callBack(error)
}
return callBack(null, results)
}
)
}
}
update user controller here I have added a controller to update the user details which receive the data from update user services.
const {
create,
getUserbyID,
getUsers,
updateUser,
deleteUser,
getUserByEmail
} = require('./userService')
const {genSaltSync, hashSync, compareSync} = require('bcrypt')
const { sign } = require('jsonwebtoken')
module.exports ={
updateUser: (req, res) => {
const body = req.body;
const salt = genSaltSync(10);
body.password = hashSync(body.password, salt);
updateUser(body, (err, results) => {
if (err) {
console.log(err)
return false;
} // added
console.log("this is the body: "+JSON.stringify(req.body))
console.log("this is the results: "+ JSON.stringify(results))
if (!results) {
return res.json({
success:0,
message: "failed to update user"
})
}
return res.json({
success: 1,
message: "Updated Sucessfully"
})
})
},
}
router.js
router.patch('/update',checkToken, updateUser)
ADDED console.log
this is the body: {"Id":15,"firstName":"joey","email":"joey.chandler357#gmail.com","password":"$2b$10$ZBnRppSKAfQ1TrzGvs/wqOrVx/shb6ESJ7emXnC7IlWRN3VUGgfK2","lastName":"chandler","phoneNumber":"9860316634","sex":"Male"}
this is the results: {"fieldCount":0,"affectedRows":0,"insertId":0,"serverStatus":2,"warningCount":0,"message":"","protocol41":true,"changedRows":0}
I can see your console.log message
this is the results: {"fieldCount":0,"affectedRows":0,"insertId":0,"serverStatus":2,"warningCount":0,"message":"","protocol41":true,"changedRows":0}
Here you can notice affectedRows: 0 it means no row updated this happens when condition is not matched with any of the records. In postman you are passing "Id" I is in capital format but at the time of accessing this in service you are using "data.id" id is small latter so this is creating problem
we can handle this
instead of
if (!results) {
return res.json({
success:0,
message: "failed to update user"
})
}
use
if (!results.affectedRows) {
return res.json({
success:0,
message: "failed to update user"
})
}
this will be much better then previous check
I think you need to use an "insert" to add the db record. It's using an update... so it's looking for a pre-existing record.
Try two things:
wrap “users” in quotes on your update query. I’ve seen this w Postgres where some words are reserved in raw queries.
Examine the database response from your update. See what is console logged.

Node mysql cannot get a response on a query

I have a trouble when i pass a function inside my query. When i run my code without the function just work without any problem. With it on postman is stuck on "Sending request"
Example:
save() {
return db.query(
{
sql: "INSERT INTO contenido (titulo, extencion_archivo, fecha_publicacion) VALUES (?, ?, ?)",
values: [this.titulo, this.extension, this.fecha]
}, function(err, res, fields) {
//More code
}
);
}
Following code work without any problem:
save() {
return db.query(
{
sql: "INSERT INTO contenido (titulo, extencion_archivo, fecha_publicacion) VALUES (?, ?, ?)",
values: [this.titulo, this.extension, this.fecha]
}
);
}
How i call save method:
exports.addVideo = (req, res, next) => {
const titulo = req.body.titulo;
const extension = req.file.mimetype.split("/")[1];
const fecha = new Date();
const videoUrl = req.file.filename;
const video = new Videos(null, titulo, extension, fecha, videoUrl);
video.save().then(() => {
res.json('sending')
})
};
You are using .then on function save() which is not promise returning function. I think that may be the reason for you not getting any response for your postman request.
Try running this code :
function save() {
return new Promise((resolve, reject) => {
db.query(
{
sql: "INSERT INTO contenido (titulo, extencion_archivo, fecha_publicacion) VALUES (?, ?, ?)",
values: [this.titulo, this.extension, this.fecha]
}, function (err, res, fields) {
if (err) {
console.log("Error Occurred :", err);
reject();
}
console.log("Successfully Sent :", res);
resolve();
}
);
})
}
and
exports.addVideo = (req, res, next) => {
const titulo = req.body.titulo;
const extension = req.file.mimetype.split("/")[1];
const fecha = new Date();
const videoUrl = req.file.filename;
const video = new Videos(null, titulo, extension, fecha, videoUrl);
video.save().then(() => {
res.json('sending')
}).catch(() =>{
res.json('Error Occurred')
})
};
Please try this if it works well and good else let me know I will try to help you around this.

How do I manage mysql query errors from express in a React form?

I am trying to send users to two different pages based on whether an SQL query is successful or not on an express backend. But only the success route is showing when I use this code.
I previously did not have the await statement in, but had the same issue. I'm not sure whether the react side is taking in the error message as a response, as it's still logging into the console from the backend.
Here is the method in the frontend which is called when the form is submitted:
e.preventDefault();
console.log(this.state);
const newPost = {
pet_name : this.state.pet_name,
content : this.state.content,
content : this.state.content,
owner : 'testOwner',
email : 'test#gmail.com',
img_path : this.state.upload_image
};
//fetch instead of this to talk about in diss
try {
const postData = await axios.post('http://localhost:3306/reportpet', newPost)
.then(res=>console.log(res.data));
this.props.history.push('/postsubmitted')
} catch(error) {
console.log("Catch = ", error.response);
this.props.history.push('/posterror')
}```
The route on the backend is as follows:
```router.post('/reportpet', function (req, res) {
var pet_name = req.body.pet_name,
content = req.body.content,
date = req.body.date,
owner = req.body.owner,
email = req.body.email,
img_path = req.body.img_path;
const query = "INSERT INTO `posts` (`post_id`, `pet_name`, `content`, `date`, `owner`, `email`, `img_path`) VALUES (?, ?, ?, UTC_TIMESTAMP(),?, ?, ?);"
console.log(query);
connection.query(query, [pet_name, pet_name, content, owner, email, img_path ], function(err, result) {
(err)?res.send(err+'error was created'):res.json(result);
if (err) throw err;
console.log('rows inserted')
})
})
module.exports = router
When the data is not added to the database, I expect the user to be sent to the error component. When it is successful, I expect the success component to display.
Try to skip using .then() in await.
And be sure that your backend returns the response with proper HTTP error code (4xx or 5xx) so the axios knows that error happened.
try {
const postData = await axios.post('http://localhost:3306/reportpet', newPost)
console.log(postData);
this.props.history.push('/postsubmitted')
} catch(error) {
console.log("Catch = ", error.response);
this.props.history.push('/posterror')
}
Mykola Prymak answered this. I had a response sending the error instead of throwing it, removing that and adding the response underneath the throw fixed it.
Code in the backend is now this:
const query = "INSERT INTO `posts` (`post_id`, `pet_name`, `content`, `date`, `owner`, `email`, `img_path`) VALUES (null, ?, ?, UTC_TIMESTAMP(),?, ?, ?);"
console.log(query);
connection.query(query, [pet_name, content, owner, email, img_path ], function(err, result) {
// (err)?res.send(err+'error was created'):res.json(result); {removed code}
if (err) throw err;
res.json(result);
console.log('rows inserted')
})
```