Подождать выполнение запроса sqlite на node.js

Хочу чтобы результатом выполнения функции был массив массивов с объектами, которые получены из БД.

function cat () {
    var keyboard = []
    var res = []
    db.each('SELECT id, Name FROM Categories', (err, row) => {
        var obj = {}
        obj.text = row.Name
        obj.callback_data = row.id
        res.push(obj)
        keyboard.push(res)
        res = []
    })
    return keyboard
}

Но db.each работает асинхронно и результат выполнения функции пустой массив. Как подождать выполнение запроса? То, что ожидаю от выполнения функции:

[
  [ { text: 'Кот 1', callback_data: 'cat_1' } ],
  [ { text: 'Кот 2', callback_data: 'cat_2' } ]
]

Ответы (2 шт):

Автор решения: DiD

Используйте better-sqlite3. Он в десятки раз быстрее и там нет проблем с асинхронностью.

→ Ссылка
Автор решения: nörbörnën

Вы должны сделать свою функцию асинхроной и работать с ней как с асинхронной функцией:

async function cat() {
    return new Promise((resolve, reject) => {
        db.all('SELECT id, Name FROM Categories', [], (err, rows) => {
            if (err) {
                return reject(err);
            }

            const arr = rows.reduce((acc, row) => {
                acc.push({
                    text: row.Name,
                    callback_data: row.id
                });
                return acc;
            }, []);

            resolve(arr);
        });
    });
}

Использование, вариант 1:

cat()
  .then((objects) => console.log(objects))
  .catch((err) => console.error(err));

Использование, вариант 2:

(async () {

  try {
    const objects = await cat();
    console.log(objects);
  } catch (err) {
    console.error(err);
  }

})();
→ Ссылка