I have some trouble with my js callback, I can't understand why my callback of my function don't want execute all the code, just to give you an idea :
class LogsPortail {
static SetLogs(pool, req, res, callback) {
console.log('start log ');
var bCallBack = false;
var now = new Date();
var endpoint = req.originalUrl
endpoint = endpoint.split("?")[0]
endpoint = endpoint.replace("/", "")
var query = "INSERT INTO LOGS_PORTAIL (ENDPOINT, TYPE, DATE_HEURE_LOGS, LOGIN) VALUE ('" + endpoint + "','" + req.method + "','" + now.toISOString().slice(0, 19).replace('T', ' ') + "','" + 'API' + "')";
var queryParam = "INSERT INTO LOGS_PORTAIL_PARAM (IDLOGS_PORTAIL, NOM, VALEUR) VALUE ";
console.log('query 1 log ');
pool.query(query, function(err, results) {
if (err) {
console.log("Error : " + query);
bCallBack = true;
callback();
} else {
console.log('query log 2');
//On a bien inséré le logs portail, maintenant on ajout tous les paramètres
for (var key in req.query) {
if (queryParam != "INSERT INTO LOGS_PORTAIL_PARAM (IDLOGS_PORTAIL, NOM, VALEUR) VALUE ")
queryParam += ","
queryParam += " (" + results.insertId + ",'" + key.toLowerCase() + "', '" + req.query[key] + "')"
}
for (var key in req.body) {
if (queryParam != "INSERT INTO LOGS_PORTAIL_PARAM (IDLOGS_PORTAIL, NOM, VALEUR) VALUE ")
queryParam += ","
queryParam += " (" + results.insertId + ",'" + key.toLowerCase() + "', '" + req.body[key] + "')"
}
pool.query(queryParam, function(err, resultsParam) {
if (err) {
console.log("Error : " + queryParam);
console.log(err);
bCallBack = true;
callback();
} else {
bCallBack = true;
callback();
}
});
}
});
while (bCallBack === false) {}
console.log('call back end ');
//callback();
}
}
To explain you, my first query will be executed perfectly, and after that, the callback will not go through the condition but will go at the end where (for the test) I put an infinity while where my code will never exit.
This is what my log shows - we never see the logs "query log 2"
Thanks for your help
I have 2 different tables where the first table is used for retrieving the data to store in the second table, so for example, if there are 3 items in the first table, ill run a for loop 3 times to retrieve the information and storing it in the second table row by row, i also have to use a unique id for the primary key for the second table, so i have to run another mysql query to retrieve all the ID in the second table and add 1 to the id to generate a new ID, but the problem for me is that when i try to put a connection.query in another connection.query, the outer connection.query runs 3 time before running the inner connection.query, hence the items does not get stored and the id does not update, giving me a duplicate primary key error, i tried using functions but it doesnt help, here is
app.get('/submit-check', function (request, response) {
function insert(sql2) {
connection.query(sql2, function (err, result1) {
if (err) throw err;
});
}
function other(value, index) {
let sql = "SELECT * FROM ORDERS"
connection.query(sql, function (err, results) {
var id;
if (results.length == 0) {
id = 0
} else {
id = results[results.length - 1].orderID;
}
// for (let j = 0; j < results.length; j++) {
// list.push(results[j].orderID)
// }
// if (list.length == 0) {
// id = 0
// }
// else {
// var largest = 0;
// for (let i = 0; i <= list.length; i++) {
// if (parseInt(list[i]) > largest) {
// var largest = parseInt(list[i]);
// }
// }
// id = largest + 1
// }
id = id + 1;
var add = request.query.state + " " + request.query.address + " " + request.query.Unumber + " " + request.query.zip
var custID = value[index].custID
var bookID = value[index].bookID
var Email = request.query.email
var CardName = request.query.cardname
var CardNumber = request.query.cardnumber
var ExDate = request.query.expmonth + "/" + request.query.expyear
var CVV = request.query.cvv
var qty = 1
var sql2 = "INSERT INTO orders (orderID,custID, bookID, QTY, CardName, CardNumber, ExDate, CVV, Email, Address, createdAt, updatedAt) VALUES('" + id + "','" + custID + "', '" + bookID + "', '" + qty + "', '" + CardName + "', '" + CardNumber + "', '" + ExDate + "', '" + CVV + "', '" + Email + "', '" + add + "', CURDATE(), CURDATE() )"
insert(sql2)
})
}
function setValue(value) {
for (let index = 0; index < value.length; index++) {
other(value, index)
}
}
let sql3 = "SELECT * FROM carts"
var cart_db;
connection.query(sql3, function (err, result) {
cart_db = result
setValue(cart_db)
})
// console.log(cart_db)
response.render("aftercheck", { attributes: request.query, cardno: "****-****-****" + request.query.cardnumber.slice(-5,) });
})
thank you in advance
There are many, many things wrong with your code. I've peppered this await/async-based rewrite with TODO comments where you'll probably need to fix up things. Naturally I haven't been able to test this since I don't have your database.
async function queryP(connection, sql, parameters = undefined) {
return new Promise((resolve, reject) => {
connection.query(sql, parameters, function (err, results) {
if (err) return reject(err);
resolve(results);
});
});
}
app.get("/submit-check", async function (request, response) {
// TODO: these need to be validated
const {
address,
Unumber,
zip,
expyear,
state,
expmonth,
email: Email,
cardname: CardName,
cardnumber: CardNumber,
cvv: CVV,
} = request.query;
const add = `${state} ${address} ${Unumber} ${zip}`;
const ExDate = `${expmonth}/${expyear}`;
const cartData = await queryP(connection, "SELECT * FROM carts"); // TODO: this is not safe with multiple customers
const [maxOrderIdRow] = await queryP(connection, "SELECT MAX(id) as maxid FROM orders");
const orderId = (maxOrderIdRow.maxid || 0) + 1; // TODO: this is not safe in the face of concurrent requests
// Using a for loop rather than .map and await and so on is simpler here
for (let i = 0; i < cartData.length; i++) {
const cartRow = cartData[i];
const custID = cartRow.custID;
const bookID = cartRow.bookID;
const qty = 1;
// TODO: rethink how credit cards are saved – we can't save them in the database like this or we'll be out of business
await queryP(
connection,
`INSERT INTO orders (orderID, custID, bookID, QTY, CardName, CardNumber, ExDate, CVV, Email, Address, createdAt, updatedAt) VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, CURDATE(), CURDATE() )`,
[orderId, custID, bookID, qty, CardName, CardNumber, ExDate, CVV, Email, add],
);
}
response.render("aftercheck", {
attributes: request.query,
cardno: "****-****-****" + CardNumber.slice(-5),
});
});
Right now this section of code is passing along undefined to if(customerWaiting >0). It's an issue with async that I can't seem to figure out.
Based off the other threads I looked at, it's very basic and a newbie question, I just can't make it work.
I was seeing if you could find it for me
Edit 1:
the goal of the code is to see if there are customers in the firebase "customerWaiting" database, if there is then display the modal, if there is not then say there are no customers waiting
structure for database is
customerWaiting
-Automatically generated ID
-customer information
Here is the code
var customerWaiting;
var employeeWaiting;
var ref = firebase.database().ref();
$("#connectNextUser").click(function() {
{
ref.child("customerWaiting").on("value", function(snapshot) {
var customerWaiting = snapshot.numChildren();
console.log("There are " + snapshot.numChildren() + " customers waiting");
});
ref.child("employeeWaiting").on("value", function(snapshot) {
var employeeWaiting = snapshot.numChildren();
console.log("There are " + snapshot.numChildren() + " employees waiting");
});
}
if (customerWaiting > 0) {
$("#myModal").modal();
console.log("connect");
} else {
console.log("There are " + customerWaiting + " employees waiting");
console.log("no connect");
}
});
If I understand you correctly you want to do this:
var ref = firebase.database().ref();
$("#connectNextUser").click(function() {
// query how many customers are waiting
ref.child("customerWaiting").on("value", function(snapshot) {
// as soon as you have the result then get the numChildren
var customerWaiting = snapshot.numChildren();
console.log("There are " + snapshot.numChildren() + " customers waiting");
if (customerWaiting > 0) {
// show the modal if customerWaiting > 0
$("#myModal").modal();
console.log("connect");
} else {
console.log("There are " + customerWaiting + " employees waiting");
console.log("no connect");
}
});
});
If you want to use await/async then ref.child("customerWaiting").on("value", resolve) has to support Promises, or you need to convert it to one:
var ref = firebase.database().ref();
$("#connectNextUser").click(async function() {
var snapshot = await new Promise((resolve, reject) => {
ref.child("customerWaiting").on("value", resolve)
// you should also handle the error/reject case here.
})
var customerWaiting = snapshot.numChildren();
console.log("There are " + snapshot.numChildren() + " customers waiting");
if (customerWaiting > 0) {
$("#myModal").modal();
console.log("connect");
} else {
console.log("There are " + customerWaiting + " employees waiting");
console.log("no connect");
}
});
async run(message, args) {
LolApi.init('censored', 'na');
LolApi.setRateLimit(10, 500);
var input = '';
args = args.toLowerCase();
LolApi.Summoner.getByName(args, function (err, summoner) {
if (!err) {
Name = summoner[args].name;
Name = Name.toLowerCase();
Id = summoner[Name].id;
Level = summoner[Name].summonerLevel;
input += "Name: " + summoner[Name].name + '\n' +
"Level: " + Level + "\n";
console.log(input);
//message.reply(input);
process.nextTick(LolApi.getLeagueData);
}
else {
message.reply('Error fam.');
}
});
setTimeout(function(){console.log('Waiting...')},2000);
LolApi.getLeagueData(Id,'NA', function (err, summoner) {
if (!err) {
Tier = summoner[Id][0].tier;
Division = summoner[Id][0].entries[0].division;
input += "Tier: " + Tier + '\n' +
"Division: " + Division;
message.reply(input);
} else {
console.log(Name);
console.log(err);
message.reply('Error Fam' + Id + "test");
}
});
}
When i run this code up get an error 404 running the second part. It gives me an saying combinedTickCallback but im not sure what this means because i am a noob. I use node.js if that helps with anything
I cannot figure out when to close a db in node-sqlite3, or really how to use the package in general. It seems if I run this, I get "no such table:rooms". Eventually after running it enough times, I might manage to make the table.
var sqlite3 = require('sqlite3').verbose();
class RoomManager{
constructor(options){
this.db = this._createDb();
this.table = "rooms";
this._createTable();
this.addRoom({
name : 'test3'
}).getRooms()
this.deleteRoom({
name : 'test3'
}).getRooms();
return this;
}
_createDb() {
return new sqlite3.Database('chat');
}
_createTable(){
this.db.run("CREATE TABLE IF NOT EXISTS " + this.table + " (name TEXT, size INT)");
return this;
}
addRoom(options){
this.db.run("INSERT INTO " + this.table + " (name, size) VALUES ($name, $size)", {
$name : options.name,
$size : options.size || 1000
});
return this;
}
getRooms(){
this.db.all("SELECT rowid, name, size FROM " + this.table, function(err, rows) {
rows.forEach(function (row) {
console.log(row.rowid + ": " + row.name + " - " + row.size);
});
});
return this;
}
getRoom(options){
if(options.name){
this.db.get("SELECT * FROM " + this.table + " WHERE name = $name", {
$name : options.name
}, function(err, row){
return row;
});
}
}
deleteRoom(options){
this.db.run("DELETE FROM " + this.table + " WHERE name = $name", {
$name : options.name
});
return this;
}
}
module.exports = RoomManager;
Your problem that Node is asynchronous. So, you must wait end of command by callback function. e.g.
this.db.run(query, params, function(err) {
if (err)
return console.log(err);
// do next query here
})
Sqlite module can control flow by db.serialize. Imho it's useless in common cases. Better use async module or promises for it.