Node JS Error: write after end - mysql

In the following code, I am trying to retrieve data from MySQL database and show them to a user by using response write. The error that I got is Error: write after end:
var http = require("http");
var mysql = require('mysql');
var express = require('express');
var app = express();
var bodyParser = require('body-parser');
var urlencodedParser = bodyParser.urlencoded({ extended: false })
app.use(express.static('public'));
app.get('/Search.html', function (req, res) {
res.sendFile( __dirname + "/" + "Search.html" );
})
var connection = mysql.createConnection(
{
host : 'localhost',
user : 'root',
password : 'somepass',
database : 'SocialQuery',
}
);
connection.connect();
app.post('/process_post', urlencodedParser, function (req, res) {
// Prepare output in JSON format
response = {
SearchType:req.body.SearchTypes,
Term:req.body.term
};
//var vas = JSON.stringify(response);
var search = req.body.SearchTypes;
var term = req.body.term;
var query = connection.query('Select * from ?? where Lable = ?', [search, term], function(err, rows) {
res.write(rows);
});
console.log(query.sql);
res.end();
})
//}).listen(8081);
http.createServer(app).listen(8081);
console.log('Server running at http://127.0.0.1:8081/');
I changed res.write(rows); to res.end(rows); but didn't work. Can someone help me solving this problem.

The problem is that MySQL queries are asynchronous in node.js. so, the result won't be in the variable query, but retrieved in the callback, to the variable rows. So what happens is that res.end() is called, and then the callback returns and res.write() is called, so it's called after end().

You are doing an Asynchronous call when fetching data from database. res.write() is inside callback function so before fetching data it would call res.end() and res.write() will be called after the data has been fetched. That's why you are getting Error: write after end . You can use res.end() in the same callback function.
var query = connection.query('Select * from ?? where Lable = ?', [search, term], function(err, rows) {
res.write(rows, function(err){
res.end();
});
});
Now the res.end() function will be called after the write process has been done.

It worked after I made two changes:
var query = connection.query('Select * from ?? where Lable = ?', [search, term], function(err, rows) {
console.log(rows);
res.write(JSON.stringify(rows));
res.end();
});
First, I moved res.end(); inside the connection.query part.
Second, instead of writing rows only, I changed to res.write(JSON.stringify(rows));

Related

Angular 4 - display date from database

I need display data in table from MySql database, but I dont know how it do this.
I tried found something example or example application with source code, but I nothing found.
Maybe someone help me with this?
I tried with node.js express:
var mysql = require('mysql');
var https = require('https');
var con = mysql.createConnection({
host: "https://adress to database",
user: "user",
password: "password",
database: "db"
});
con.connect(function(err) {
if (err) throw err;
console.log("Connected!");
});
But i get error:
Error: getaddrinfo ENOTFOUND
here is a simple way to get data from mySQL and export it as json:
var http = require('http');
var mysql = require('mysql');
var bodyParser = require("body-parser");
var express = require('express');
var app = express();
var pool = mysql.createPool({
host: 'db location',
user: 'username od db',
password: 'something',
database: 'yourdatabase',
port:3306
});
// define rute
var apiRoutes = express.Router();
var port = 9000;
apiRoutes.get('/', function (req, res) {
res.json({ message: 'API works' });
});
apiRoutes.get('/data', function (req, res, next) {
pool.getConnection(function (err, connection) {
if (err) {
console.error("error hapened: " + err);
}
var query = "SELECT * FROM imena ORDER BY id ASC";
var table = ["imena"];
query = mysql.format(query, table);
connection.query(query, function (err, rows) {
connection.release();
if (err) {
return next(err);
} else {
res.json({
success: true,
list_users: rows
});
}
});
});
});
app.use('/api', apiRoutes);
// starting
app.listen(port);
console.log('API radi # port:' + ' ' + port);
But i still suggest that you start using noSQL databases like firebase because of they are simple and faster.
In order to show data from MySQL Database, you need to provide application interface(s) to Angular environment and only then Angular can use the data. There are few techniques in which you can design interfaces, REST is the most popular though.
First you need to understand that Angular is Front-End framework and it can only send requests to backend such as Node js, PHP etc.Thus, first you need to chose your backend. Node is popular with express js module, but if you still don't have mySQL set, go for firebase real time database. If you decide node js => express => mySQL check tutorial online.

Object is null when reading from JSON in NodeJs

I got this server code running
const fs = require('fs');
const express = require('express');
const app = express();
app.get('/profile/:id', function (req, res) { // A route with a parameter
res.render('profile', {
user: getUserById(req.params.id)
});
});
app.listen(8888, function () {
console.log('Server running on port 8888');
});
function getUserById(userId){
fs.readFile('./database.json', 'utf8', function (err, data) {
var json = JSON.parse(data);
var users = json.users;
return users.find(u => u.id === userId);
});
}
And when calling the route, the function getUserById gets called. In my database, I have this data
{
"users": [
{
"id": 2312,
"name": "Foo Bar",
}
]
}
so the route would be /profile/2312 for example.
req.params.id returns the value 2312.
In the loop at var currentUser = users[0]; currentUser.id will return 2312 and the parameter passed in is 2312.
But when assigning user = currentUser; the object user is null.
Do I miss a module? Is the code wrong?
user object is null because you are returning it before your code actually reads the file.
fs.readFile('./database.json', 'utf8', function (err, data) { }
fs.readFile is asynchronous, so in order to return correct value you have to move the return statement inside fs.readFile block.
Also since getUserById is calling an asynchronous function, you have to call res.render after 'getuserById' finishes executing.
const fs = require('fs');
const express = require('express');
const app = express();
app.get('/profile/:id', getUserById);
app.listen(8888, function () {
console.log('Server running on port 8888');
});
function getUserById(req,res){ // Get a user from the database by userId
const userId = req.params.id;
fs.readFile('./database.json', 'utf8', function (err, data) {
var json = JSON.parse(data); // get the JSON object
var users = json.users; // convert the object to a user array
var match = users.find(u=>u.id.toString()===userId.toString());
//Call render after the asynchronous code finishes execution.
res.render('profile', {
user: match
});
});
}
How does Asynchronous Javascript Execution happen? and when not to use return statement?

nodejs res.json display in html

trying to display data queried from mongo db via nodejs to html index.html.
What the script does? it open the server connection , connect to mongodb and from the webform with datapicker it display the result query, via console i can see the result and it is working perfectly, now i need to display the data to web.
So far no result. Any suggestion?
var express = require("express");
var app = express();
var router = express.Router();
var path = __dirname + '/views/';
var fs = require("fs");
const util = require('util')
//lets require/import the mongodb native drivers.
var mongodb = require('mongodb');
//We need to work with "MongoClient" interface in order to connect to a mongodb server.
var MongoClient = mongodb.MongoClient;
// Connection URL. This is where your mongodb server is running.
var url = 'mongodb://localhost/klevin';
router.use(function (req,res,next) {
console.log("/" + req.method);
next();
});
router.get("/",function(req,res){
res.sendFile(path + "index.html");
var data_e_fillimit = req.param('start_time');
//console.log(params.startDate)
console.log('Data e fillimit '+data_e_fillimit)
var data_e_mbarimit= req.param('endtime_time');
//console.log(params.startDate)
console.log('Data e mbarimit '+data_e_mbarimit)
// Use connect method to connect to the Server
MongoClient.connect(url, function (err, db) {
if (err) {
console.log('Unable to connect to the mongoDB server. Error:', err);
} else {
//HURRAY!! We are connected. :)
console.log('Connection established to', url);
// Get the documents collection
var collection = db.collection('frames');
//We have a cursor now with our find criteria
var cursor = collection.find({
tv: 'tematv',
date_created: {"$gte": new Date(data_e_fillimit) , "$lte": new Date(data_e_mbarimit) }});
//We need to sort by age descending
cursor.sort({_id: -1});
//Limit to max 10 records
cursor.limit(50);
//Skip specified records. 0 for skipping 0 records.
cursor.skip(0);
//Lets iterate on the result
cursor.each(function (err, doc) {
if (err) {
console.log(err);
//res.json(err);
} else {
console.log('Fetched:', doc);
// res.json({ user: 'tobi' })
}
});
}
});
});
/*router.get("/about",function(req,res){
res.sendFile(path + "about.html");
});
router.get("/contact",function(req,res){
res.sendFile(path + "contact.html");
});*/
app.use("/",router);
/*app.use("*",function(req,res){
res.sendFile(path + "404.html");
});*/
app.listen(3000,function(){
console.log("Live at Port 3000");
});
use ejs (npm install ejs --save) package try like this:
app.engine('html', require('ejs').renderFile);
app.set('view engine', 'ejs');
app.get('/', function (req, res){
res.render('index.html',{
foo:bar
});
});
now use can use this object that passed to the index.html

How to connect mysql with nodejs?

I just started to learn nodejs with express framework.In my app there are two pages app.js and db.js..I need to post data from form and insert to register table
In db.js
var mysql = require('./node_modules/mysql');
var connection = mysql.createConnection({
host: '127.0.0.1',
user: 'root',
password: '',
database: 'nodeapp'
});
connection.connect(function (err) {
if (err)
throw err;
});
module.exports = connection;
// In my app.js page
var express = require('./lib/express');
var app = express();
var bodyParser = require('body-parser')
var db = require('/db');
app.get('/', function (req, res) {
res.sendFile('/NodeProj/views/' + 'index.html');
});
/** bodyParser.urlencoded(options)
* Parses the text as URL encoded data (which is how browsers tend to send form data from regular forms set to POST)
* and exposes the resulting object (containing the keys and values) on req.body
*/
app.use(bodyParser.urlencoded({
extended: true
}));
/**bodyParser.json(options)
* Parses the text as JSON and exposes the resulting object on req.body.
*/
app.use(bodyParser.json());
app.post('/process_form', function (req, res) {
var response = {
"firstname": req.body.fst_name,
"email": req.body.fst_email,
"password": req.body.fst_password
};
var query = connection.query('INSERT INTO register SET?',response,function(err,result){
if(err) throw err;
if(result) console.log(result);
});
res.end(JSON.stringify(response));
});
app.listen(8081);
But when I run the code I got the following error
Refference error: connection is not defined
Please help me .Thanks in advance.
As mentioned in the comments, you've called connection db.
So if you replace var db = require('/db'); with var connection = require('./db'); then your connection will be defined.

Node.js - SQL function doesn't return value

i want to get a data from a MySQL database and i use Node.js with SQL for it, this is my server code:
var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);
var mysql = require('mysql');
var connection = mysql.createConnection({
host : '127.0.0.1',
user : 'root',
password : '',
database : 'temp'
});
function getData(res){
var tempVal = 1377;
connection.connect();
connection.query('SELECT * FROM tempvalues ORDER BY datetime DESC LIMIT 1', function(err, rows){
console.log(rows);
tempVal = rows;
});
connection.end();
return tempVal;
}
app.get('/', function(req, res){
res.sendfile('index.html');
});
io.on('connection', function(socket){
socket.on('clientSent', function(data){
if(data == "GET")
socket.emit("serverSent", getData());
})
})
http.listen(3000, function(){
console.log('listening on *:3000');
});
If i go to localhost:3000 i only get 1377 as value but not the actual value from the database, even though the console prints the correct values. Why is that?
There's some things bad in your code.
First. Think that queries to database, in most of cases are asynchronous.
Your code explained :
function getData(res){
var tempVal = 1377; // Create tempVal with 1377 as value initially.
connection.connect(); // Connect to the database.
// Run the query
connection.query('SELECT * FROM tempvalues ORDER BY datetime DESC LIMIT 1', function(err, rows){
// Here you are inside the callback executed asynchronously.
console.log(rows);
// You modify the top-level variable.
tempVal = rows;
});
connection.end(); // End connection
return tempVal; // You return 1377 since the callback is not yet finish and the value of tempVal not changed
}
One simple way to fight with async code are the callbacks. Let your getData function look like :
function getData(callback){
var tempVal = 1377;
connection.connect();
connection.query('SELECT * FROM tempvalues ORDER BY datetime DESC LIMIT 1', function(err, rows){
console.log(rows);
return callback(err, rows);
});
connection.end();
}
Then use the function as follows:
io.on('connection', function(socket){
socket.on('clientSent', function(data){
if(data == "GET")
getData(function(error, result){
if(!error) socket.emit("serverSent", result);
});
})
});