数据库返回值在 Node JS 中未定义

问题描述

我在学习 NodeJS 时遇到了一个问题。我是 javascript 新手,所以有人可以向我解释一下。

我正在从 index.js 调用一个函数,它将返回从数据库获取的值。但是我在返回时得到了未定义的对象。

index.js

const cron = require('node-cron');
const app = require('./app');
const port = process.env.PORT || 3000;
require('dotenv').config();

const { getRecentData } = require('./service/getRecentData')

var prev_id = 0;
cron.schedule('*/10 * * * * *',async() => {
    var row = await getRecentData();
    console.log(row);
    var new_id = row["id"];
    if (new_id == prev_id){
        new_id = prev_id;
    }
    else{
        console.log(row["date_time"]);
        prev_id = new_id;
    }
})

app.listen(port,() => {
  console.log(`Listening: http://localhost:${port}`);
});

getRecentData.js

const e = require("express")

const { Client } = require('pg');

const client = new Client({
    user: 'postgres',host: 'localhost',database: 'database',password: 'postgres',port: 5432,});

client.connect();

const getRecentData = async () => {
  const query = `
    SELECT *
    FROM test_table order by id desc limit 1
    `;

   const recentData =  await client.query(query,(err,res) => {
        if (err) {
            console.error(err);
            return;
        }
        return res.rows; 
  });

  return recentData;
}


module.exports = {
  getRecentData
}

但是我在调​​用 getRecentData() 函数时在 index.js 中得到了未定义的对象。

解决方法

您需要了解 await 仅适用于 Promise。如果函数返回 Promise,则可以使用 await。所有 async 函数都返回一个 Promise。在您的情况下, client.query 没有返回承诺,它有一个回调,它有自己的执行上下文,因此 return recentData 语句在 client.query 方法完成之前执行。您可以像这样修改您的 getRecentData 方法

const getRecentData = () => {
    return new Promise((resolve,reject) => {
        const query = `SELECT * FROM test_table order by id desc limit 1`;
        client.query(query,(err,res) => {
            if (err) {
                console.error(err);
                reject(err);
                return;
            }
            resolve(res);
        });
    });
};
,

不要使用recentData变量

await client.query(query,res) => {
        if (err) {
            console.error(err);
            return;
        }
        if(res){
             return res.rows; 
        }
  });