Getting Return from an DB.ALL called - javascript

Trying to get the rows values from the DB all function. Unable to get that out of the DB.All function or pull it away from the arrow. The console log that I got will return the output I desire but I want it pull it out so I can use the JSON value.
Any idea how to do this?
handler: (request, h) => {
let sql = `SELECT TRIAL_ID as indexTrial, URL as urlImage FROM TRIAL`;
var test ='hi';
db.all(sql, (err, rows) => {
if (err) {
throw err;
}
test= JSON.stringify(rows);
console.log(test);
test =rows;
//return rows;
});
return test;
}

Needed a promise because it was going to fast to get the value
handler: (request, h) => {
let sql = `SELECT TRIAL_ID as indexTrial, URL as urlImage FROM TRIAL`;
var result =[];
var test ='hi';
return new Promise((resolve) => {
db.all(sql,[], (err, rows) => {
if (err) {
throw err;
}
resolve(rows);
})
}).then((rows) => {
return h.response(rows);
});

Related

Function is returning before SqlQuery finishes

I have a function that has a query that connects to a database and does a basic SELECT query, The query works fine, however the function appears to be returning before the query finishes all of its steps. In this case I have the Hello World Console log and the array is undefined. But if I setTimeout for one second and then log out the "NewArray" it has all the data from the query. So my question is: How do I return this data after the query has finished doing its magic.
async function getData() {
let newArray = []
let db = new sqlite3.Database('PATHTODB',sqlite3.OPEN_READWRITE, (err) => {
if (err) {
return console.error(err.message);
}
});
let selectQuery = `SELECT * FROM TableName;`
await db.all(
`${selectQuery}`,
(err, row) => {
console.log(row)
row.forEach(x => {
newArray.push(x)
})
}
)
console.log("Hello World", newArray)
return newArray
}
Tried using ASYNC/AWAIT
db.all(query, callback) is not an async function to await. It's just invoking it's callback asynchronously. Try promisfying it as follows;
async function getData() {
let newArray = []
let db = new sqlite3.Database('PATHTODB',sqlite3.OPEN_READWRITE, (err) => {
if (err) {
return console.error(err.message);
}
});
let selectQuery = `SELECT * FROM TableName;`,
row = await new Promise((resolve,reject) =>
db.all(`${selectQuery}`, (err,row) => err ? reject(err)
: resolve(row)));
console.log(row);
row.forEach(x => newArray.push(x));
console.log("Hello World", newArray);
return newArray
}

How to add a subquery to the results of a query with axis

I am querying an objects table based no an id. Then I want to query the same table with the id of my result and add it result object as a new property. Hope, that makes sense:
app.get(`/details`, (req, res) => {
const { id } = req.query;
connection.query(
`SELECT
objects.*
FROM objects
WHERE id = ${id}
LIMIT 1`,
(err, results) => {
if (err) {
return res.send(err);
} else {
let result = results[0];
result.relationships = [];
connection.query(
`SELECT
objects.*
FROM objects
WHERE relationship = ${result.id}`,
(err, rel_results) => {
if (err) {
return res.send(err);
} else {
rel_results.forEach((el) => {
result.relationships.push(el);
});
// This log looks fine. result.relationhips is an array of objects.
console.log(result);
}
}
);
// Here, the result has an empty array for result.relationhips
return res.json(result);
}
}
);
});
When you look at the comments, why is the result correct in the log but not in the return?
You dont acutally have to build a promise. You can simply send your results when they are available within your second query callback:
(err, results) => {
if (err) {
return res.send(err);
} else {
let result = results[0];
result.relationships = [];
connection.query(
`SELECT
objects.*
FROM objects
WHERE relationship = ${result.id}`,
(err, rel_results) => {
if (err) {
return res.send(err);
} else {
rel_results.forEach((el) => {
result.relationships.push(el);
});
// This log looks fine. result.relationhips is an array of objects.
console.log(result);
res.json(result);
}
}
);
}
You need to place the return statement within the nested callback, this is main
because of early return:
result.relationships = [];
connection.query(
`SELECT
objects.*
FROM objects
WHERE relationship = ${result.id}`,
(err, rel_results) => {
if (err) {
return res.send(err);
} else {
rel_results.forEach((el) => {
result.relationships.push(el);
});
// This log looks fine. result.relationhips is an array of objects.
console.log(result);
return res.json(result);
}
}
);

whats wrong with put rows into array sqlite3 nodejs

I want to save sqlite3 row values into an array. I followed what was discussed here:
Can't put rows into array using sqlite3 on Node.js
However when I console.log my would-be-array records, I obtain:
console.log(records) => an array with values [1,1,2]
console.log(records[1]) => undefined
There must be a mistake in my understanding of what's going on. What is wrong?
Full code below:
const sqlite3 = require('sqlite3').verbose();
let db = new sqlite3.Database('src/db/ksbib.db', (err) => { if (err) { return console.log(err.message); } });
let result = [];
let records = [];
function catchResult (err, row)
{
if (err) { return console.log(err.message); }
else { return result.push(row.objektid); }
}
function getData ()
{
return new Promise ((resolve, reject) =>
{
db.parallelize ( () =>
{
db.each(sqlTitel(param), catchResult);
db.each(sqlAutor(param), catchResult);
});
resolve(result);
})
}
async function res ()
{
records = await getData();
console.log(records);
console.log(records[1]);
return records;
};
let x = res();
console.log(x);
The contradiction between console.log(records) and console.log(records[1]) does not exist in the commandline. It seems that some other code interferes in the console.
Moreover, the promise as implemented above resolves with the emtpy result-array before the database request is finished. One can introduce a timeout to play with the code.
In order to resolve the promise after the database request, one should resolve it in the callback function of the request. That's also the reason why db.all is much easier to handle than db.each.
Instead of a series of database requests one can then use a series of promises. Thereby it is important to wait for every single promise to be resolved (just coupling them like this return await sqr(sqlTitle(y), []).then(sqr(sqlAuthor(y), [])) gives no unique result). The result-array is completed bit by bit.
const sqlite3 = require('sqlite3').verbose();
let db = new sqlite3.Database('ksbib.db', (err) => { if (err) { return console.log(err.message); } });
let result = [];
let p;
function sqr (sql, x)
{
return new Promise(function (resolve, reject)
{
db.all(sql, x, (err, rows) =>
{
if (err) {
reject(err);
} else {
rows.forEach( (row) => {result.push(row.objektid)} );
resolve(result);
}
});
});
}
( async () =>
{
p = await sqr(sqlTitle(y), []);
p = await sqr(sqlAuthor(y), []);
return p; //the final result
})();

Update multiple SQL records with single query MySQL query with npm mysql

Thanks for taking a look at this! I am attempting to update a few records in MySQL with a single query; however, I am using a class with Promises to create a group of synchronis queries and I cannot seem to get this to work. Here is what I currently have:
req.body is an array of objects with two key/value pairs...
API:
router.post('/verified', (req, res) => {
let database = new Database(dbOptions);
let verifiedItemsArray = [];
let sqlQueryArray = [];
let updateQuery = 'UPDATE `raw_unverified` SET `funding_source` = ? WHERE `ritm_number` = ?';
let verifiedItemArray = [req.body[0].funding_source, req.body[0].ritm_number];
database.beginTransaction([updateQuery], verifiedItemArray)
.then(response => console.log(response))
.catch(error => console.log(error));
res.send('Update Successful');
});
database class:
class Database {
constructor(config) {
this.connection = mysql.createConnection(config);
}
query(sqlQuery, sqlArgs) {
console.log(sqlQuery);
return new Promise( (resolve, reject) => {
this.connection.query(sqlQuery, ((sqlArgs) ? [sqlArgs] : null), (error, results) => {
if (error) return reject(error);
resolve(results);
});
});
}
beginTransaction(sqlQueries, sqlArgs) {
return new Promise( (resolve, reject) => {
let allResults = [];
this.connection.beginTransaction( (error) => {
if (error) return reject(error);
for (let i = 0; i < sqlQueries.length; i++) {
this.query(sqlQueries[i], ((sqlArgs) ? sqlArgs[i] : null))
.then((results) => {
allResults.push(results);
})
.catch((error) => {
throw error;
});
}
this.connection.commit( (error) => {
if (error) return reject(error);
resolve(allResults);
});
});
});
}
}
module.exports = Database;
And here is the error that I get:
UPDATE raw_unverified SET funding_source = ? WHERE ritm_number = ?
(node:8216) UnhandledPromiseRejectionWarning: Error: ER_PARSE_ERROR: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '?' at line 1
Any help will be much appreciated and anything that I could do better, please feel free to point out!
Thanks in advance everyone!
In this line
this.query(sqlQueries[i], ((sqlArgs) ? sqlArgs[i] : null))
you're passing arguments to queries by index - that means you need to change
database.beginTransaction([updateQuery], verifiedItemArray)
to
database.beginTransaction([updateQuery], [verifiedItemArray])

Returning an array from mongodb connect and find

I have the following code that I use to connect to my MongoDB instance and return some recored. I need to iterate over the cursor results to create a suitable data structure for my application. However, I struggling to work out how to return the contents of the table array to the calling function. It works if I predefine a table variable but that is not what I need to achieve.
How can I get the findUsage function to return the table array to the callingMongoClient.connect code?
const MongoClient = require('mongodb').MongoClient
const assert = require('assert')
const url = 'mongodb://localhost:27017/test'
const table = []
const findUsage = function (db, callback) {
const cursor = db.collection('usage')
.find({ },
{'customer': 1})
cursor.each(function (err, doc) {
assert.equal(err, null)
if (doc != null) {
table.push(
[doc.customer]
)
} else {
callback(table)
}
})
}
MongoClient.connect(url, function (err, db) {
assert.equal(null, err)
findUsage(db, function () {
// console.log("Session: %j", table);
console.log(table)
db.close()
})
})
Use the method toArray to deal with the find cursor. Then use the callback, either if there is data or not.
const findUsage = function (db, callback) {
const cursor = db.collection('usage')
.find({}, {
'customer': 1,
});
cursor.toArray(function (err, docs) {
assert.equal(err, null);
if (docs) {
return callback(docs.map(x => x.customer));
}
return callback([]);
});
}
MongoClient.connect(url, function (err, db) {
assert.equal(null, err);
findUsage(db, function (docs) {
// ...
db.close();
});
});

Categories

Resources