Если вы думаете, что код будет работать так, как вы его написали, я боюсь, вы не совсем поняли, что такое обещания, какие проблемы они решают и как работают.
Давайте разберем ваш код. Вы экспортируете функцию своего дизайна getUsers
, которая должна возвращать последовательность пользовательских объектов. Но это не так - db.any(...)
возвращает Promise
. Как еще, по вашему мнению, можно вызвать then
для возвращенного объекта? then
является функцией-членом класса Promise
, и вы передаете другую функцию then
для работы с фактическими данными (переданными как параметр функции, которую вы передаете then
). Это означает, что на самом деле data
, переданное вызову then
, вызванному возвращаемым значением вызова db.any(...)
, является последовательностью пользователей, которые вам нужны.
Ошибка, которую вы делаете, заключается в предположении что если вы return data
из обратного вызова передали в then
, оно станет возвращаемым значением вызова then(...)
. Это не будет . then
всегда возвращает Promise
- все, что вы вернете из обратного вызова в then
, станет разрешенным значением возвращенного обещания, но это обещание, которое возвращается, и поэтому ваш Переменная users
- это Promise
.
Вам нужно больше узнать о обещаниях и о том, как они обрабатываются асинхронно ( между запуском ваших скриптов) и как синхронизировать ваш код при их разрешении.
Подсказка: используйте ключевое слово await
, чтобы дождаться и использовать значение данного обещания, например значение, которое вы возвращаете из обратного вызова, который вы передаете своему then(...)
call, или , примите дизайн вашей getUsers
функции, возвращающей обещание, и адаптируйте остальную часть вашего кода для работы с этим, без использования await
.
Your getAllUsers
функция может быть уменьшена до:
exports.getAllUsers = function () {
return db.any("SELECT * FROM users;");
}
... а с await
вы можете использовать ее как:
let users = await getUsers();
Вышеприведенный оператор должен быть частью функции, которая помечен как async
, хотя для ECMAScript требуется marki ng явно, чтобы разрешить использование await
выражений (и подразумевая, что вы не можете использовать await
на верхнем уровне ваших скриптов):
async function whatever() {
let users = await getUsers();
/// ...
}
Выполнение скрипта, который вызывает async
функция, такая как та, которая содержит приведенный выше оператор, будет прерываться интерпретатором JavaScript в каждом выражении await
и возобновляться, когда обещание, выраженное после ключевого слова await
, преобразуется в значение, при этом значение присваивается users
переменная.
Для использования async
и await
требуется версия Node.js, которая может их поддерживать, но текущий выпуск поддерживает (на момент написания этой статьи).
В противном случае вы все равно можете сохранить функцию getUsers
, но вам нужно использовать ее по-другому, поскольку вы не можете использовать await
- необходимость использовать обещания, как это было до введения await
и async
, например:
getUsers().then(users => {
/// Do something with the `users` array.
});
В любом случае, похоже, у вас есть некоторые дыры в понимании того, как работают обещания, и я рекомендую вам заполнить эти дыры, прочитав о них это время, а не просто переход к pg-promise
API, который основан на них.