I am used to java and I recently started a project in NodeJS and I encountered some problems with the logic behind NodeJS I think.
I have this function that needs to execute a query multiple times (changing the parameters at every iteration) and store the result in an array.
I created an array variable let FINAL = []
and i am trying to push in data when the data is retrieved per iteration.
const fluxAccesParPeriode = async (req, res) => {
try {
const db = res.locals.db;
const {date_debut, date_fin} = req.body;
if (!date_debut || !date_fin) {
res.status(400).json({error: 'One or more informations are missing.'});
return;
}
// SQL
const queryText = "SELECT COUNT(id_pointage) AS nbreAcces FROM pointage_adherents PA, adherents A WHERE PA.id_adherent=A.id_adherent AND date BETWEEN ? AND ? AND heure_entree BETWEEN ? AND ?";
let FINAL = [];
for (let i = 0; i < 24; i += 3) {
let heure_debut = i + ":00:00";
let heure_fin = (i + 3) + ":00:00";
await db.execute(queryText,
[date_debut, date_fin, heure_debut, heure_fin],
(err, results) => {
if (err) {
console.error('Error executing SQL query:', err);
res.status(500).json({error: 'Internal Server Error'});
return;
}
console.log(heure_debut + " / " + heure_fin + " / " + results[0]["nbreAcces"]);
FINAL.push({heure_debut: heure_debut, heure_fin: heure_fin, result: results[0]["nbreAcces"]});
});
}
console.log("RESULT : " + FINAL);
if (FINAL.length > 0) {
res.status(200).json(FINAL);
} else {
res.status(400).json({error: 'Error while executing your query: fluxAccesParPeriode'});
}
} catch (error) {
console.error(error.stack);
res.status(500).json({message: 'Erreur lors de l'exécution de la requête'});
}
}
What i noticed is that the last console.log
is printed first before the console.log
inside the loop. I tried to add await
but still the same issue.
Here is an image of what I am getting in the terminal:
What am I missing ?
2
Answers
This is how node js event loop works. For loop will run and put all the db query in a queue and surpass the loop and print the last "RESULT" log.
Then whatever query is resolved and get the response from DB, that particular query will print the log. thats why you have random sequence.
Best Solution for this will be to use promise all method something like:
Your call to
await db.execute(query,variable,callback)
looks like it is using the callback paradigm instead of promises, so the await doesn’t do anything since the call todb.execute
isn’t returning a promise.I’m not sure if promisify promisify will work, since it probably needs the binding to
db
, but it is easy to promisify the call on the fly.Since you have the for-loop inside a try/catch block I remove the exit from inside the lopp to throwing an exception with
reject
.A suggestion: You can probably rewrite the SQL query to let the database do the grouping. That will improve performance and only requires one call to the database.