gpt4 book ai didi

mysql - Node.js - 使用异步函数以同步方式获取返回值,无需回调

转载 作者:行者123 更新时间:2023-11-29 09:50:04 24 4
gpt4 key购买 nike

我有一个函数可以从 mysql 数据库检索 UserID 列表。

function GetUsers(callback) {
UpdateLogFile('Function Call: GetUsers()')
var users = []
Database.execute( connectionStr,
database => database.query('select UserID from Users')
.then( rows => {
for (let i = 0; i < rows.length; i++){
users.push(rows[i].UserID)
}
return callback(users)
})
).catch( err => {
console.log(err)
})
}

供引用:

数据库类来自 here

const mysql = require( 'mysql' )
class Database {
constructor( config ) {
this.connection = mysql.createConnection( config )
}
query( sql, args ) {
return new Promise( ( resolve, reject ) => {
this.connection.query( sql, args, ( err, rows ) => {
if ( err )
return reject( err )
resolve( rows )
})
})
}
close() {
return new Promise( ( resolve, reject ) => {
this.connection.end( err => {
if ( err )
return reject( err )
resolve()
})
})
}
}

Database.execute = function( config, callback ) {
const database = new Database( config )
return callback( database ).then(
result => database.close().then( () => result ),
err => database.close().then( () => { throw err } )
)
}

经过几个小时的学习 Promise 和回调之后,我终于能够让 GetUsers() 至少工作并返回我正在寻找的内容。但是,我似乎只能这样使用它:

GetUsers(function(result){
// Do something with result
})

但我真的希望能够在函数中使用传统的 return 语句,以便我可以像这样使用它:var users = GetUsers()。我看过帖子说由于异步函数的性质,这是不可能的,但我仍然充满希望,因为我真的希望能够避免 callback hell 。我尝试了下面的代码,但“用户”在执行后结果只是未定义。因此,我的主要目标是能够从 GetUsers() 获取返回值,而无需将回调链接在一起,因为我还有其他行为类似的函数。这可能吗?

var users
GetUsers(function(result){
users = result
})
console.log(users)

最佳答案

这是一个非常令人困惑的话题,我花了一段时间才真正理解为什么你所要求的根本不可能(至少以你所要求的方式)。对于示例,我将使用 python Django 和 Node.js 进行比较。

同步

def synchronous():
print('foo') //this will always print first
print('bar')

def getUsers():

with connection.cursor() as cursor:
cursor.execute('SELECT * FROM USERS') //this query is executed
users = cursor.fetchall()

print('foo') //this doesn't trigger until your server gets a response from the db, and users is defined
print(users)

异步

function asynchronous() {
console.log('foo'); //this will also always print first
console.log('bar');
}

function getUsers() {
var connection = mysql.createConnection(config);
connection.query('SELECT * FROM USERS', function(error, users) { //this is a "callback"
console.log(users); //this will print
//everything inside of here will be postponed until your server gets a response from the db

});
console.log('foo') //this will print before the console.log above
console.log(users); //this will print undefined
//this is executed before the query results are in and will be undefined since the "users" object doesn't exist yet.
}

回调只是您的服务器在收到响应后应该运行的函数。我们通常使用实际的“回调”一词,如下所示:

function getUsers(callback) {
var connection = mysql.createConnection(config);
connection.query('SELECT * FROM USERS', function(error, users) {
if (error) throw error; //always do your error handling on the same page as your query. Its much cleaner that way

callback(users) //server asks what to do with the "users" object you requested
});
}

现在在服务器上的其他地方:

getUsers(function(users) {// the callback gets called here
console.log(users); //do what you want with users here
});

getUsers 函数采用其他函数(即回调)作为其参数,并在执行查询后执行该函数。如果您想在不使用“回调”这个词的情况下做同样的事情,您可以使用像 fsociety 这样的等待/异步函数,或者您明确地写出您的代码,而不是创建将其他函数作为参数的函数。

这与上面的代码功能相同:

var connection = mysql.createConnection(config);
connection.query('SELECT * FROM USERS', function(error, users) {
if (error) throw error;
console.log(users);
});

回调 hell 是不可避免的,但一旦掌握了它的窍门,它真的不算太糟糕。

关于mysql - Node.js - 使用异步函数以同步方式获取返回值,无需回调,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54966242/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com