我有python背景,目前正在迁移到node.js。由于node.js的异步特性,我在调整它时遇到了问题。
例如,我试图从mysql函数返回一个值。
function getLastRecord(name)
{
var connection = getMySQL_connection();
var query_str =
"SELECT name, " +
"FROM records " +
"WHERE (name = ?) " +
"LIMIT 1 ";
var query_var = [name];
var query = connection.query(query_str, query_var, function (err, rows, fields) {
//if (err) throw err;
if (err) {
//throw err;
console.log(err);
logger.info(err);
}
else {
//console.log(rows);
return rows;
}
}); //var query = connection.query(query_str, function (err, rows, fields) {
}
var rows = getLastRecord('name_record');
console.log(rows);
经过一番阅读,我意识到上面的代码无法工作,由于node.js的异步特性,我需要返回一个承诺。我不能像python那样编写node.js代码。如何转换 getLastRecord()
返回一个承诺,如何处理返回的值?
事实上,我想做的是这样的事情;
if (getLastRecord() > 20)
{
console.log("action");
}
如何在node.js中以可读的方式实现这一点?
我想看看在这种情况下如何使用bluebird实现承诺。
8条答案
按热度按时间a0x5cqrl1#
这可以很简单地实现,例如使用bluebird,正如您所要求的:
pxq42qpu2#
我是node.js和promises的新手。我寻找了一段时间的东西,以满足我的需要,这是我最终使用后,结合几个例子,我发现。我希望能够获取每个查询的连接,并在查询完成后立即释放它(
querySql
),或者从池中获取连接并在promise.using范围内使用它,或者随时释放它(getSqlConnection
). 使用此方法,您可以一个接一个地连接多个查询,而无需嵌套它们。数据库.js
用法\u route.js
bq8i3lrv3#
您不需要使用承诺,您可以使用回调函数,类似于:
4uqofj5v4#
这会有点分散,原谅我。
首先,假设这段代码正确地使用了mysql驱动程序api,下面有一种方法可以将其 Package 起来,以使用本机承诺:
所以有一件事:你仍然有回调。回调只是一个函数,您可以在将来的某个时候用它选择的参数将它交给要调用的对象。所以函数参数
xs.map(fn)
,的(err, result)
在node中看到的函数以及promise result和error处理程序都是回调。人们把一种特定的回调称为“回调”,即(err, result)
在节点核心中使用的是所谓的“延续传递风格”,有时被不太喜欢它们的人称为“节点回退”。至少现在(async/await最终会到来),不管您是否接受承诺,您都会被回调所困扰。
另外,我会注意到,承诺并不是立即的,显然在这里有帮助,因为你仍然有一个回调。只有当你把承诺和承诺结合起来时,它们才会真正发光
Promise.all
答应我去洛杉矶Array.prototype.reduce
. 但它们有时确实会发光,值得学习。xxhby3vn5#
使用包promise mysql,逻辑是使用then(function(response){your code})链接承诺
以及
catch(函数(响应){your code})从catch块前面的“then”块捕获错误。
按照这个逻辑,您将在块的末尾使用return在对象或数组中传递查询结果。返回值将有助于将查询结果传递给下一个块。然后,结果将在函数参数中找到(这里是test1)。使用这个逻辑,您可以链接几个mysql查询以及操作结果和执行任何操作所需的代码。
创建的连接对象是全局的,因为每个块中创建的每个对象和变量都是局部的。别忘了,你可以链更多的“然后”块。
k4ymrczo6#
我对node还是有点陌生,所以也许我错过了什么让我知道它是如何运作的。而不是触发异步节点只是强迫你,所以你必须提前考虑和计划。
在这里,我像普通人一样使用mysql模块,但是我创建了一个新函数,通过将它添加到db const中来提前处理这个承诺(在很多节点示例中,您将其视为“连接”。
现在让我们使用promise调用一个mysql查询。
我发现这对于需要基于第一个查询执行第二个查询非常有用。
您实际上应该使用mysql变量,但这至少应该为您提供一个在mysql模块中使用promises的示例。
同样有了上面的内容,您仍然可以继续使用db.query,在这些承诺范围内的任何时候,它们都可以正常工作。
希望这对死亡三角有帮助。
wd2eg0qa7#
我已经修改了你的代码使用q(npm模块)的承诺。我假设您在上述代码段中指定的“getlastrecord()”函数工作正常。
你可以参考下面的链接来获得q模块
单击此处:q文档
gajydyqb8#
回答您最初的问题:如何在node.js中以可读的方式完成此操作?
有一个图书馆叫
co
,这使您可以在同步工作流中编写异步代码。看一看就知道了npm install co
.这种方法经常面临的问题是,你得不到
Promise
从所有你喜欢使用的图书馆回来。所以你要么自己 Package (见@joshua holbrook的答案),要么找一个 Package 器(例如:npm install mysql-promise
)(顺便说一句:es7的路线图上已经有了对这种带有关键字的工作流的本地支持
async
await
,但它还不在node:node feature列表中。)