如何使用Mysql和node.js进行同步数据库查询?

时间:2019-06-14 20:25:14

标签: javascript node.js es6-promise

我正在尝试使用mysql nodejs模块在数据库中进行SELECT查询。问题是connection.query函数是一个异步函数,因此我将其放在这样的promise中:

function execQuery(query, fields){
    const connection = mysql.createConnection({
        host: process.env.DB_HOST,
        port: process.env.DB_PORT,
        user: process.env.DB_USER,
        password: process.env.DB_PASSWORD,
        database: process.env.DB_DATABASE,
    });

    return new Promise((resolve, reject) => {
        connection.query(query, fields, (err, results) => {
            connection.end();
            if (err){
                return reject(err);
            }else{
                return resolve(results);
            }
        }
    ) 

此函数由另一个函数调用:

function getPasswordFromUser(username){
    query = 'SELECT password FROM User WHERE username=?'
    parameters = [username]

    execQuery(query, parameters)
        .then(result => {
            if (result !== undefined && result.length === 1){
                console.log('here1')
                return result
            }
        })
        .catch(err => console.log(err))

    console.log('here2')
}

问题是,尽管我返回了承诺并使用then,但在控制台中仍收到:

here2
here1

所以我的查询一直以异步模式运行,我无法获得结果。

使用诺言做到这一点的最佳方法是什么?

3 个答案:

答案 0 :(得分:1)

您只是没有兑现承诺,仅此而已。

执行: return execQuery(query, parameters)

您可以像简单的承诺一样使用它。

getPasswordFromUser('userid')
.then((result)=>{
  ..do stuff..
});

,或者如果您正在使用async-await,请使用异步函数并等待getPasswordFromUser函数。例如快速路线。

app.post('/getPassword', async (req,res) =>{
    const userID = req.body.userID;
    const password = await getPasswordFromUser(userID);
    res.send(password);
});

注意:,这只是个玩笑,我希望您不要以纯文本格式存储密码,如果要匹配密码(例如登录名),则应执行以下操作:{{1 }},或者您正在使用select count(*) from user where username=username and password=hash(password);或其他方式匹配密码。

答案 1 :(得分:0)

您首先看到here2,因为它不在then内。程序在启动execQuery函数之后继续执行。

您可以返回承诺:

function getPasswordFromUser(username){
    query = 'SELECT password FROM User WHERE username=?'
    parameters = [username]

    return execQuery(query, parameters)
        .then(result => {
            if (result !== undefined && result.length === 1){
                console.log('here1')
                return result
            }
        })
        .catch(err => console.log(err))
}

然后将.then(result => { ... })添加到函数调用中以获取结果。

答案 2 :(得分:0)

如果您绝对希望使其同步,则可以使用async-await作为异步操作结果。

const res = await yourAsyncDbCallFn();
doTheNextThing();

thenables和callbacks行为也可以完美地处理异步操作,但是它们本质上不会使您的代码执行同步。

注释:由于await使您的代码同步并等待执行,因此您可能不想在独立逻辑的情况下过度使用它。