I'm very new to coding servers and javascript in general but I'm currently trying to set up a REST api server and connect it to my sql database, for the moment I am doing everything locally. I am running ubuntu 18.04 while using NODE js. I have been able to successfully create a REST api and connect to it through an url of a webpage or with Postman. I have created a sql server database through my cmd terminal and have created test data on it. I've been looking at guides to connect the REST api to the database but I think the info I'm giving the api to connect is where my issue is occurring. I am starting with this below as my server.js where i have a folder Controller and a ProductController.js file where I'm handling the route /api/products .
var http = require('http');
var express = require('express');
var app = express();
var port = process.env.port || 3000;
var productController = require('./Controller/ProductController')();
app.use("/api/products", productController);
app.listen(port, function(){
var datetime = new Date();
var message = "Server running on Port:- " + port + " Started at :- " +
datetime;
console.log(message);
});
Below is my ProductController.js file. The issue might be here but I believe it is my next file called connect.js the table in my sql database is called 'data' hence the "SELECT * FROM data" part. when I try to GET this data in postman it displays the error i set up "Error while inserting data". so I believe when running I'm not getting data from sql so conn.close() is not being reached.
var express = require('express');
var router = express.Router();
var sql = require("mssql");
var conn = require("../connection/connect")();
var routes = function()
{
router.route('/')
.get(function(req, res)
{
conn.connect().then(function()
{
var sqlQuery = "SELECT * FROM data";
var req = new sql.Request(conn);
req.query(sqlQuery).then(function (recordset)
{
res.json(recordset.recordset);
conn.close();
})
.catch(function (err) {
conn.close();
res.status(400).send("Error while inserting data");
});
})
.catch(function (err) {
conn.close();
res.status(400).send("Error while inserting data");
});
});
return router;
};
module.exports = routes;
This is my connect.js file below. I have a password for root which is not *** but is correct on my machine. I have changed root's plug in to mysql_native_password in the mysql terminal. I think the server: part is wrong, I've tried commenting it out but still no connection. I do not have SQL Server Management Studio and have not found a way to get my sql server's name through the terminal. I've seen examples that seem to range of what info you need to give the api to connect. If someone has insight on that too that would be appreciated as well. My end goal is to eventually create GET and POST routes for the database and a function to manipulate the POST data but for now I'm just trying to get things connected so I can play around with the data being GET'ed. Thanks for any insight you can give, it is much appreciated.
var sql = require("mssql");
var connect = function()
{
var conn = new sql.ConnectionPool({
host: 'localhost'
user: 'root',
password: '********',
server: 'mysql',
database: 'test'
});
return conn;
};
Looks like you may have some errors in your connect.js file:
var conn = new sql.ConnectionPool({
host: 'localhost'
user: 'root',
password: '********',
server: 'mysql',
database: 'test'
});
should be in the format of:
const pool = new sql.ConnectionPool({
user: '...',
password: '...',
server: 'localhost',
database: '...'
})
Note that you currently have both host and server, looks like only server is needed. Also, server: 'mysql' doesn't make sense if you are connecting to a MSSQL database.
Source: node-mssql documentation
To diagnose the errors you should add some logging to your catch blocks:
.catch(function (err) {
console.log('connection error', err); //or Bunyan, Winston, Morgan, etc. logging library
conn.close();
let message = "Error while inserting data"
if (process.env.NODE_ENV === 'development') { //conditionally add error to result message
message += "\n"+err.toString());
}
res.status(500).send(message); //use 5xx for server problems, 4xx for things a user could potentially fix
});
And set NODE_ENV in your environment, for example in package.json:
"scripts": {
"start": "NODE_ENV=production node app.js"
"start-dev": "NODE_ENV=development node app.js"
}
So I've looked around all over the place for an answer for this but I cannot find one anywhere.
so I'm trying to setup a PostgreSQL database with nodeJS and I've installed pgadmin3 etc.
here is my code
const express = require("express");
const pg = require("pg");
const connect = "postgres://sean:sean#localhost/karls"
var pool = new pg.Pool(connect);
router.route("/").get((req, res) => {
pool.connect(function(err, client, done){
if(err) return console.error("the error ocurred on: " + err);
client.query("SELECT * FROM Recipe", function(err, result) {
if(err) console.error(error);
console.log(results)
done();
})
})
});
on my pgadmin3 I have a login role named sean as a super user so I don't know why it's not connecting I have the password correct but it keeps spitting out this error:
error: password authentication failed for user "sean";
I've been trying to fix this for ages if you need any more information let me know and ill update the question
I've solved this problem :)
can't get data from mysql db in nodejs in routes '/users'
app.get('/users', function(req,res){
connection.query("select * from users",function(err,rows){
if(!err) {
res.json(rows);
}else{
console.log(err);
res.send('err here !!' + err);
}
connection.end();
});
});
take much time and then response with
ERR_EMPTY_RESPONSE
db connection
var connection = mysql.createConnection({
host : 'localhost',
port : port,
database : 'test',
user : 'root',
password : 'root'
});
can some one help me to track this issue ,
Thanks in advance.
This issue has been resolved: I defined the MySql port as 8080 by mistake.
I corrected the port to 3306.
My code:
var mysql = require('mysql');
var connection = mysql.createConnection({
host : '192.168.2.20',
user : 'test',
password : '123123123',
database : 'dbtest',
});
connection.connect(function(err) {
// connected! (unless `err` is set)
});
var query = connection.query('INSERT INTO posts (title) VALUES("data1");');
Everytime I run this SELECT * FROM dbtest.posts; using MySQL Workbench I never see any changes or results.
What am I doing wrong that NodeJS using mysql-node is not correctly editing my DB?
EDIT:
admin$ node debug test.js
< debugger listening on port 5858
connecting... ok
break in test.js:1
1 var mysql = require('mysql');
2 var connection = mysql.createConnection({
3 host : '192.168.2.20',
debug>
Do I have a problem in calling my files? They are kept under node_modules and the file is in the same root directory as node_modules
You are not being able to insert data with the code in your example probably because your MySQL server is with the autocommit system variable set to false.
What you can do in this case is to set this variable to true (see de docs) or change your code to force the commit, like:
connection.query('INSERT INTO posts (title) VALUES("data1");', function(err, result) {
if (err) {
connection.rollback(function () {
throw err;
});
}
connection.commit(function (err) {
if (err) {
connection.rollback(function () {
throw err;
});
}
console.log('Commited!');
});
});
Question Updated:
The solution should detail a simplified, proper model of a Node connection module allowing for the re-use of the connection by any module of a Node application needing to connect to a database. That way, the question might be useful for anyone with connection module issues in Node.
The answer might even include a way to pass in different credentials in order to connect to different tables or databases with a single function call from anywhere in an app.
I wrote a script that utilized a number of simple modules to allow a user to post login data, have that data validated on the server, and if correct, receive a response of success. A very basic login functionality.
The problem: One user can log-in, but any more log-in attempts before I restart the server fail to connect to the database.
It appears that, because I'm declaring the connection in a variable in my module db_connect and requiring that module, the connection can't be re-used. It's being declared in the required module, and I had mistakenly believed that calling the variable in each connection attempt would recreate the connection. It doesn't.
The solution: As suggested by barry in the comments, in the db_connect module, I need to make the connection functionality a function rather than a variable, so I can then create the connection from within my validation script.
How can I do this? I'm trying to output the connection object when calling the createConnection() function, which is an exported method of db_connect.
db_connect:
console.log('db_connect module initialized');
var mysql = require('mysql');
function createConnection(){
var connection = mysql.createConnection({
host : 'localhost',
user : 'root',
password : '',
database : 'officeball'
});
}
exports.createConnection = createConnection();
exports.mysql = mysql;
validator:
console.log('validator module initialized');
var connect = require("./db_connect");
function validate(username, password, callback){
var createConnection = connect.createConnection();
//the idea is for this to return the object, connection,
//which opens a new connection
connection.connect(function (err){
if (err) return callback(new Error('Failed to connect'), null);
console.log('Connection with the Officeball MySQL database openned...');
connection.query('select username,password,fname,lname,rank,active from users where username=?',
username,
function(err,rows,fields) {
connection.destroy();
console.log('...Connection with the Officeball MySQL database closed.');
if (err)
return callback(new Error ('Error while performing query'), null);
if (rows.length !== 1)
return callback(new Error ('- [Anomaly] - Failed to find exactly one user'), null);
if (rows[0].password === password & rows[0].active === "yes") {
var result = new Object;
result.username = rows[0].username;
result.password = rows[0].password;
result.fname = rows[0].fname;
result.lname = rows[0].lname;
result.rank = rows[0].rank;
return callback(null, result);
} if(rows[0].active !== "yes"){
return callback(new Error ('User account not active.'), null);
}else {
return callback(new Error ('Login credentials did not match.'), null);
}
});
});
};
exports.validate = validate;
Console log (originally, there was a connection error, but after my fix-attempt, the error is about the method):
C:\xampp\htdocs\officeball\node_scripts>node index.js
application initialized
server module initialized
login module initialized
validator module initialized
db_connect module initialized
sale module initialized
Server running at http://127.0.0.1:8080/
User username1 is attempting login...
TypeError: Property 'createConnection' of object #<Object> is not a function
at Object.validate (C:\xampp\htdocs\officeball\node_scripts\custom_modules\v
alidator.js:6:33)
at C:\xampp\htdocs\officeball\node_scripts\custom_modules\login.js:61:13
at callbacks (C:\xampp\htdocs\officeball\node_scripts\node_modules\express\l
ib\router\index.js:164:37)
at param (C:\xampp\htdocs\officeball\node_scripts\node_modules\express\lib\r
outer\index.js:138:11)
at pass (C:\xampp\htdocs\officeball\node_scripts\node_modules\express\lib\ro
uter\index.js:145:5)
at Router._dispatch (C:\xampp\htdocs\officeball\node_scripts\node_modules\ex
press\lib\router\index.js:173:5)
at Object.router (C:\xampp\htdocs\officeball\node_scripts\node_modules\expre
ss\lib\router\index.js:33:10)
at next (C:\xampp\htdocs\officeball\node_scripts\node_modules\express\node_m
odules\connect\lib\proto.js:193:15)
at multipart (C:\xampp\htdocs\officeball\node_scripts\node_modules\express\n
ode_modules\connect\lib\middleware\multipart.js:93:27)
at C:\xampp\htdocs\officeball\node_scripts\node_modules\express\node_modules
\connect\lib\middleware\bodyParser.js:64:9
Your problem was primarily what I mentioned in my comment, so I will make it an answer. Don't hurt yourself slapping your forehead. :-) See my inline comments below. You had one method invocation too many, an unreturned result, and a misnamed variable - otherwise, it works just fine.
db_connect.js
console.log('db_connect module initialized');
var mysql = require('mysql');
function createConnection(){
var connection = mysql.createConnection({
host : 'localhost',
user : 'root',
password : '',
database : 'officeball'
});
// ************ NOTE BELOW FOR CHANGE **************
// You didn't return anything from this function. You need to return the connection
return connection;
}
// ************ NOTE BELOW FOR CHANGE **************
// You are exporting a single connection by invoking createConnection();
// exports.createConnection = createConnection();
// what you want is:
exports.createConnection = createConnection;
exports.mysql = mysql;
validator.js
function validate(username, password, callback){
// ************ NOTE BELOW FOR CHANGE **************
// You had:
// var createConnection = connect.createConnection();
// but based on your code, you wanted to write this instead:
var connection = connect.createConnection();
/// ... REMAINDER OMITTED, because it was A-OK and this is already a long page
};
If you make those two three changes, you should be good to go. As ever, feel free to ask for any clarifications if it would be helpful.
Update This is how I am calling it - as you can see, I had it try to do it ever 2 seconds.
jt-test.js
var v = require('./validator');
var timers = require('timers');
var connections = 0;
timers.setInterval(function(){
v.validate('bagehot','foo',function(err,result){
if (err)
console.log('failed', err);
else
console.log('success! ',result);
});
},2000);
result
Connection with the Officeball MySQL database openned...
...Connection with the Officeball MySQL database closed.
success! { username: 'bagehot',
password: 'foo',
fname: 'walter',
lname: 'bagehot',
rank: 12 }
Connection with the Officeball MySQL database openned...
...Connection with the Officeball MySQL database closed.
success! { username: 'bagehot',
password: 'foo',
fname: 'walter',
lname: 'bagehot',
rank: 12 }
Connection with the Officeball MySQL database openned...
...Connection with the Officeball MySQL database closed.
success! { username: 'bagehot',
password: 'foo',
fname: 'walter',
lname: 'bagehot',
rank: 12 }
Connection with the Officeball MySQL database openned...
...Connection with the Officeball MySQL database closed.
success! { username: 'bagehot',
password: 'foo',
fname: 'walter',
lname: 'bagehot',
rank: 12 }
And so on. It runs indefinitely. Complete code for the three files is in this gist
You can checkout my emysql package.
https://www.npmjs.org/package/emysql
https://github.com/yanke-guo/enhanced-mysql-pool
Maybe it's some kind of outdated with the most recent node-mysql package, but still functional.