I am using: node-mysql
arrtickers got around 200 values.
arrtickers closure pass in values into sym.
sym will pass in value to each function (running in async mode, each fn will start running on its own without waiting for the previous fn to complete)
problem here is mysql seems unable to handle multiple calls?
events.js:48
throw arguments[1]; // Unhandled 'error' event
^
Error: reconnection attempt failed before connection was fully set up
at Socket.<anonymous> (/home/ubuntu/node/node_modules/mysql/lib/client.js:67:28)
at Socket.emit (events.js:64:17)
at TCP.onread (net.js:398:51)
arrtickers.forEach(function(value) {
var sym= value;
(function(sym) {
url2= "http://test2.com/quote.ashx?t="+sym+"&ty=c&ta=1&p=d&b=1";
request({ uri:url2 }, function (error, response, body) {
jsdom.env({
html: body,
scripts: [
jqlib
]
}, function (err, window) {
var $ = window.jQuery;
var data= $('body').html();
//some scrapping
var client2 = mysql.createClient({
user: 'root',
password: '123',
host: '127.0.0.1',
port: '3306'
});
client2.query('USE testtable');
sql= "update tbla SET a='"+a+"', b='"+b+"', c='"+c+"', d='"+d+"' where ticker='"+sym+"'";
client2.query(
sql, function(err, info){
if (err) {
throw err;
}
}
);
client2.end();
});
});
})(sym);
(function(sym) {
url= "http://test3.com/quote.ashx?t="+sym+"&ty=c&ta=1&p=d&b=1";
request({ uri:url3 }, function (error, response, body) {
jsdom.env({
html: body,
scripts: [
jqlib
]
}, function (err, window) {
var $ = window.jQuery;
var data= $('body').html();
//some scrapping
var client3 = mysql.createClient({
user: 'root',
password: '123',
host: '127.0.0.1',
port: '3306'
});
client3.query('USE testtable');
sql= "update tbla SET a='"+a+"', b='"+b+"', c='"+c+"', d='"+d+"' where ticker='"+sym+"'";
client3.query(
sql, function(err, info){
if (err) {
throw err;
}
}
);
client3.end();
});
});
})(sym);
(function(sym) {
url= "http://test4.com/quote.ashx?t="+sym+"&ty=c&ta=1&p=d&b=1";
request({ uri:url4 }, function (error, response, body) {
jsdom.env({
html: body,
scripts: [
jqlib
]
}, function (err, window) {
var $ = window.jQuery;
var data= $('body').html();
//some scrapping
var client4 = mysql.createClient({
user: 'root',
password: '123',
host: '127.0.0.1',
port: '3306'
});
client4.query('USE testtable');
sql= "update tbla SET a='"+a+"', b='"+b+"', c='"+c+"', d='"+d+"' where ticker='"+sym+"'";
client4.query(
sql, function(err, info){
if (err) {
throw err;
}
}
);
client4.end();
});
});
})(sym);
//same function repeat for test5.com, test6.com, test7.com, test8.com, test9.com
});
Below is portion of the code from client.js (part of node-mysql)
I don't really understand how the whole process get linked together, any idea guys?
Client.prototype._connect = function() {
this.destroy();
var socket = this._socket = new Socket();
var parser = this._parser = new Parser();
var self = this;
socket
.on('error', this._connectionErrorHandler())
.on('data', parser.write.bind(parser))
.on('end', function() {
if (self.ending) {
// #todo destroy()?
self.connected = false;
self.ending = false;
if (self._queue.length) {
self._connect();
}
return;
}
if (!self.connected) {
this.emit('error', new Error('reconnection attempt failed before connection was fully set up'));
return;
}
self._connect();
})
.connect(this.port, this.host);
parser.on('packet', this._handlePacket.bind(this));
};
You can use node-mysql-queues module, which is a wrapper for the current module you are using. Here is the information: https://github.com/bminer/node-mysql-queues
Sample Multi-Query from their page:
var q = client.createQueue();
q.query(...);
q.query(...);
q.execute();
client.query(...); //Will not execute until all queued queries (and their callbacks) completed.
Related
I want to access to Azure Postgres DB from an Azure function.
Below is the node.js source code of Azure function.
module.exports = async function (context, req) {
try {
context.log('Start function!');
var pg = require('pg');
const config = {
host: 'taxiexample.postgres.database.azure.com',
user: 'postgres#taxiexample',
password: 'QscBjk10;',
database: 'taxi',
port: 5432,
ssl: false
};
var client = new pg.Client(config);
const query = 'insert into taxi values (\'2\');';
context.log(query);
client.connect();
var res = client.query(query);
await client.end();
context.log(res);
} catch (e) {
context.log(e);
} finally {
context.res = {
status: 200,
body: "ok"
};
}
};
The record doesn't insert, the res object returns the following error:
2020-03-04T23:03:59.804 [Information] Promise {
<rejected> Error: Connection terminated
at Connection.<anonymous> (D:\home\site\wwwroot\HttpTrigger1\node_modules\pg\lib\client.js:254:9)
at Object.onceWrapper (events.js:312:28)
at Connection.emit (events.js:228:7)
at Socket.<anonymous> (D:\home\site\wwwroot\HttpTrigger1\node_modules\pg\lib\connection.js:78:10)
at Socket.emit (events.js:223:5)
at TCP.<anonymous> (net.js:664:12)
}
2020-03-04T23:03:59.811 [Information] Executed 'Functions.HttpTrigger1' (Succeeded, Id=944dfb12-095d-4a28-a41d-555474b2b0ee)
Can you help me? Thanks
I've resolve it, it was a trivial programming error.
Below is the correct source code
module.exports = async function (context, req) {
try {
context.log('Start function!');
var pg = require('pg');
const config = {
host: 'example.postgres.database.azure.com',
user: 'postgres#example',
password: 'passwd;',
database: 'test',
port: 5432,
ssl: true
};
var client = new pg.Client(config);
const query = 'insert into test values (\'2\');';
context.log(query);
client.connect(err => {
if (err) {
console.error('connection error', err.stack);
} else {
console.log('connected');
client.query(query, (err, res) => {
if (err) throw err;
console.log(res);
client.end();
})
}
});
} catch (e) {
context.log(e);
} finally {
context.res = {
status: 200,
body: "ok"
};
}
};
I have a code that reads unseen emails and creates pdf.
The problem is;
I cannot pull email if any new unseen email exist without executing code again.
var Imap = require('imap');
const MailParser = require('mailparser').MailParser;
var pdf = require('html-pdf');
var fs = require('fs');
var Promise = require("bluebird");
Promise.longStackTraces();
var imapConfig = {
user: '*****',
password: '*****',
host: 'imap.gmail.com',
port: 993,
tls: true
};
var imap = new Imap(imapConfig);
Promise.promisifyAll(imap);
imap.once("ready", execute);
imap.once("error", function(err) {
log.error("Connection error: " + err.stack);
});
imap.connect();
function execute() {
imap.openBox("INBOX", false, function(err, mailBox) {
if (err) {
console.error(err);
return;
}
imap.search(["UNSEEN"], function(err, results) {
if(!results || !results.length){console.log("No unread mails");imap.end();return;}
var f = imap.fetch(results, { bodies: "" });
f.on("message", processMessage);
f.once("error", function(err) {
return Promise.reject(err);
});
f.once("end", function() {
console.log("Done fetching all unseen messages.");
imap.end();
});
});
});
}
const options = { format: 'A2', width:"19in", height:"17in", orientation: "portrait" };
function processMessage(msg, seqno) {
console.log("Processing msg #" + seqno);
// console.log(msg);
var parser = new MailParser();
parser.on("headers", function(headers) {
console.log("Header: " + JSON.stringify(headers));
});
parser.on('data', data => {
if (data.type === 'text') {
console.log(seqno);
console.log(data.html); /* data.html*/
var test = data.html
pdf.create(test, options).toStream(function(err, stream){
stream.pipe(fs.createWriteStream('./foo.pdf'));
});
}
});
msg.on("body", function(stream) {
stream.on("data", function(chunk) {
parser.write(chunk.toString("utf8"));
});
});
msg.once("end", function() {
// console.log("Finished msg #" + seqno);
parser.end();
});
}
Also I have tried to use setInterval to check new unseen emails but I get
'Error: Not authenticated'
How can I pull new unseen emails in a loop and create pdf from that email?
Your observation is correct. You must poll your IMAP (or POP3) server on a regular schedule to keep up with incoming messages. Depending on your requirements, a schedule of once every few minutes is good.
continous polling, or polling every second or so, is very rude. The operator of the IMAP server may block your application if you try to do that: it looks to them like an attempt to overload the server.
So I have done C++ Java and PHP and wanted to give a crack at Node.js. Below I have a very simple and unsecured SQL query.
module.exports = {
LoginCheck: function(data,cb){
console.log(data.password);
console.log(data.username);
if(data.username && data.password){
console.log('we have arrived');
var config = require(__dirname+'/../Config/config.json');
var mysql = require('mysql');
var con = mysql.createConnection({
host: config.LoginDBhost,
port: config.LoginDBport,
user: config.LoginDBusername,
password: config.LoginDBpassword,
database: config.LoginDB
});
con.connect(function(err) {
if (err) throw err;
console.log('we have connected');
con.query("SELECT * FROM `Users` WHERE `Username` = '"+data.username+"'", function (err, result) {
if (err) console.log(err);
if(result.Password){
if(result[0].Password){
if(result[0].Password == data.password){
console.log('true');
cb(true);
}
}
}
});
});
}
//either password is null or didnt match on file... if we are this far its a fail
console.log('false');
cb(false);
},
bar: function () {
// whateverss
}
};
The code does not wait for the sql connection and skips to being false. I been banging my head on a desk for days trying to figure out how promises and callbacks works after years of having my code follow steps layed.
Could someone convert this and explain how to force my code to be synchronous when I need it to be?
Try this code :
module.exports = {
LoginCheck: function(data,cb){
console.log(data.password);
console.log(data.username);
if(data.username && data.password){
console.log('we have arrived');
var config = require(__dirname+'/../Config/config.json');
var mysql = require('mysql');
var con = mysql.createConnection({
host: config.LoginDBhost,
port: config.LoginDBport,
user: config.LoginDBusername,
password: config.LoginDBpassword,
database: config.LoginDB
});
con.connect(function(err) {
// I think cb(false) here but you use throw err.
if (err) throw err;
console.log('we have connected');
con.query("SELECT * FROM `Users` WHERE `Username` = '"+data.username+"'", function (err, result) {
if (err) console.log(err);
if(result.Password){
if(result[0].Password){
if(result[0].Password == data.password){
console.log('true');
cb(true);
}
}
}
//either password is null or didn't match on file... if we are this far its a fail
console.log('false');
cb(false);
});
});
}
},
bar: function () {
// whateverss
}
};
I have seen multiple answers for the question but I am not able to solve this issue, so I am re-posting it with my code. I am new to this and need help to understand and fix this.
My Code
// Get logs from DB
router.get("/getlogs/:dbtype", function (req, res, next) {
var dbtype = req.params.dbtype;
if (dbtype == "mongodb") {
list = Logs.find(function (err, log) {
res.json(log);
})
} else if (dbtype == "mssql") {
var config = {
userName: 'user',
password: 'pass',
server: 'server',
options: {
instanceName: 'instance',
database: 'db',
}
};
// SQL Server connection
var connection = new Tedious.Connection(config);
connection.on('connect', function (err) {
// if (err) { console.log(err); res.json(err);}
// If no error, then good to proceed.
//console.log("SQL Server Connected SQL SQL");
//connection.on('debug', function(err) { console.log('debug:', err);});
var request = new Tedious.Request(`select top 1 * from table1`, function (err) {
//if (err) { console.log(err); res.json(err);}
});
request.on('row', function (columns) {
var row = {};
columns.forEach(function (column) {
row[column.metadata.colName] = column.value;
});
rows.push(row);
res.json(rows); **<-- this is where I get error**
});
request.on('end', function () {
res.json(rows);
})
connection.execSql(request);
});
}
});
It's because you are sending response every time you recive row.
Change this:
request.on('row', function (columns) {
var row = {};
columns.forEach(function (column) {
row[column.metadata.colName] = column.value;
});
rows.push(row);
res.json(rows);
});
to:
request.on('row', function (columns) {
var row = {};
columns.forEach(function (column) {
row[column.metadata.colName] = column.value;
});
rows.push(row);
});
request.on('doneInProc', function () {
res.json(rows);
});
how can i monitor multiple email accounts using imap at the same time using node.js?
I have a program to get notifications for single account using node-imap module and parsed emails using mail-parser.
var Imap = require('imap'),
inspect = require('util').inspect;
var MailParser = require('mailparser').MailParser;
var fs = require('fs');
var imap = new Imap(
{
user: 'any_email_address',
password: 'password',
host: 'imap.host.com',
port: 993,
tls: true,
tlsOptions:
{
rejectUnauthorized: false
}
});
function openInbox(cb)
{
imap.openBox('INBOX', true, cb);
}
var messages = []
imap.once('ready', function ()
{
openInbox(function (err, box)
{
console.log("open")
if (err) throw err;
imap.search(['ALL', []], function (err, results)
{
if (err) throw err;
var f = imap.fetch(results,
{
bodies: ''
});
f.on('message', function (msg, seqno)
{
var mailparser = new MailParser()
msg.on('body', function (stream, info)
{
stream.pipe(mailparser);
mailparser.on("end", function (mail)
{
fs.writeFile('msg-' + seqno + '-body.html', mail.html, function (err)
{
if (err) throw err;
console.log(seqno + 'saved!');
});
})
});
msg.once('end', function ()
{
console.log(seqno + 'Finished');
});
});
f.once('error', function (err)
{
console.log('Fetch error: ' + err);
});
f.once('end', function ()
{
console.log('Done fetching all messages!');
imap.end();
});
});
});
});
imap.once('error', function (err)
{
console.log(err);
});
imap.once('end', function ()
{
console.log('Connection ended');
});
imap.connect();
this is simple
first, make a function that makes your connection and Global variable to put your connection on that and handle theme where ever you want
var Connection = [];
function connectImap(username, password, address, port, tls) {
if (typeof Connection[username] != typeof undefined &&
typeof Connection[username].state == typeof '' &&
Connection[username].state == 'authenticated' &&
Connection[username]._config.user == username &&
Connection[username]._config.password == password) {
console.log('IMAP-CLIENT-USE-AUTHENTICATED-CONNECTION ' + username);
} else {
port = port || 993;
tls = tls || true;
Connection[username] = new Imap({
user : username,
password : password,
host : address,
port : port,
authTimeout : 10000,
connTimeout : 10000,
keepalive : true,
tls : tls
});
console.log('IMAP-CLIENT-CONNECTED : ' + username);
}
}
now you have an array of different connection that means you can find the one you wanted.
i hope it helps
You have to create separate connections to monitor multiple accounts.