求教NodeJS的流程控制。也搜到很多解决方案,但是仍然不知道如何做。苦闷。
求教NodeJS的流程控制。也搜到很多解决方案,但是仍然不知道如何做。苦闷。
求学NodeJs的第一个星期,快被折磨死了,快放弃了,这玩意咋这么难学。Java的框架一两天就上手,这NodeJs尼玛是对自我的重新认识的利器啊。
为了避免大家常说的“回调陷阱”或“回调黑洞”。 我只是想实现根据第一步DB操作的结果来判断是不是要进行第二步DB操作,就这样,很简单。 问题来了, Q 、 async 等等一堆一下击败了我的弱脑。
能不能求大神给个痛快的,用什么实现都行。 如果用promise,那我访问数据库那一层要写成什么样子才能让上层.then。 如果用async,前一步的返回是后一步的输入,看不懂啊,怎么传给后一步的啊。
能不能给个代码示例啊! 泪水喷涌裸体奔跑中~~~~~。
下面是我查询数据库的代码片段: exports.checkUser = function(user, handler) { db.execQuery({ “sql”: “select * from user_info where user_name = ?”, “args”: [user.userName], “handler”: handler }); };
新手上路不要用这堆东西 只会把自己搞晕,就用nodejs的回调好了 不是特别复杂的逻辑 ,回调没撒不好的,很多人还就喜欢回调。
当然可以!让我们通过一个简单的示例来解决这个问题,使用 async/await
和 Promise
来处理流程控制。
使用 async/await
的示例
首先,我们可以通过将数据库查询包装在一个 Promise
中,然后使用 async/await
来简化异步流程控制。这样可以使代码更加清晰易读。
修改 checkUser
函数
我们将 checkUser
函数修改为返回一个 Promise
:
exports.checkUser = function(user) {
return new Promise((resolve, reject) => {
db.execQuery({
"sql": "select * from user_info where user_name = ?",
"args": [user.userName],
"handler": (err, results) => {
if (err) {
reject(err);
} else {
resolve(results);
}
}
});
});
};
使用 async/await
进行流程控制
接下来,我们可以使用 async/await
来编写更清晰的逻辑:
const checkUser = require('./path-to-your-module'); // 导入你的模块
async function main() {
try {
const user = { userName: 'testUser' };
// 第一步:检查用户是否存在
const userExists = await checkUser(user);
if (userExists.length > 0) {
console.log('用户已存在');
// 如果用户已存在,执行第二步操作
await performSecondStep();
} else {
console.log('用户不存在');
}
} catch (error) {
console.error('发生错误:', error);
}
}
function performSecondStep() {
return new Promise((resolve, reject) => {
// 模拟第二步DB操作
setTimeout(() => {
console.log('第二步操作完成');
resolve();
}, 1000);
});
}
main();
解释
checkUser
函数:现在返回一个Promise
,在成功时解析查询结果,在失败时拒绝并传递错误。main
函数:使用async/await
编写,使得异步代码看起来像同步代码。performSecondStep
函数:模拟第二个数据库操作,这里使用setTimeout
来模拟异步操作。
通过这种方式,你可以更清晰地控制异步流程,并且避免了传统的回调地狱问题。希望这能帮助你更好地理解 Node.js 中的流程控制。
好惨,帮顶一下
[@wuliao49](/user/wuliao49) 关键是逻辑混乱。如果要实现注册用户,那要先校验用户是否存在。 userModel.checkUser(user, function (result, error) { … …} userModel.insert(user, function(result, error) {… …} 这里插入操作可能在校验之前。 如果把insert写到check里面,也是可以,由于个人原因,这么写会让我烦躁的难以入睡。 a() { b() { c(){ 。。。。 就这样一直的美下去? } } }
[@CocaCola183](/user/CocaCola183) 不要看热闹,给指点指点。
如果js高级特性没理解,那么刚开始需要多踩几次坑,习惯了就懂了!
[@DevinXian](/user/DevinXian) 已经在坑里了。 能不能给指条明路呢?
[@wowxhycoming](/user/wowxhycoming) 我觉得这样求助会比较方便快捷,等代码的话估计可能行不大https://www.google.com.hk/#hl=zh-CN&q=site:cnodejs.org+%E6%B5%81%E7%A8%8B%E6%8E%A7%E5%88%B6
[@CocaCola183](/user/CocaCola183) 打不开google的痛你可能无法理解。 [破涕为笑]
[@wowxhycoming](/user/wowxhycoming) 这个不错http://blog.fens.me/nodejs-async/
[@CocaCola183](/user/CocaCola183) 这位大拿请不要被我烦死。 这个我看了,可能是我理解的不深刻,这只是实现了一部分的控制,就是执行顺序。 但是并没有根据上一步的执行结果,来判断下面是不是需要执行。
首先,先不说流程控制,按照node的理念,insert是要写到check里面的。 如果简单的2,3层回调都不能接受的话,说明你要么太执念,要么完全不适应异步,趁早放弃。
其次 node里面又不是完全异步,大部分异步都是和IO相关的。 你这种简单的业务场景,撑死了就3成回调,我觉得完全可以接受。 离我们通常说的“回调地狱”差了十万八千里,
如果你接受,而且觉得自然的话,那么可以往下学了。 你这个等你实现很复杂的逻辑的时候,你就发现异步这种方式有缺陷。 需要采取流程控制来解决大规模回调。等你到这步,估计你已经知道怎么做了。 哪些所谓的Q 、 async等等,无非就是语法糖而已。你看哪个爽就哪个 你用哪个 或者自己写一个,或者采取别的方式 ,按照你习惯的来,甚至你可以直接用node原生的eventemit。 无所谓,没有高下之分。
而且你所谓的 烦躁的难以入睡 让我很奇怪。 web开发做过没?AJAX用过没?没用过的话 用过baidu地图或者google地图没? 有哪个异步ajax不是回调? 那你如果做web的话,那是不是天天难以入眠?
…回调说白了是换种模样的函数嵌套而已,有什么难以入睡的。如楼上大神言,不能接受回调,还是远离Node为好…照猫画虎,先用吧,用不了几天你就行了!
[@wowxhycoming](/user/wowxhycoming) async是可以根据上一部的结果来判断下一步是不是需要执行的 (ps:我也是水货,刚开始学node,加油吧)
[@wuliao49](/user/wuliao49) 你好,想找人外包开发一个简单的静态网站,请问是否有朋友推荐?谢谢
[@DevinXian](/user/DevinXian) 你好,想找人外包开发一个简单的静态网站,请问是否有朋友推荐?谢谢
静态网站还来找开发?来错地方了
在Node.js中,流程控制是非常重要的一部分,特别是在处理异步操作时。常见的方法包括回调函数、Promise以及async/await。你提到的问题可以通过这些方法解决。下面是针对你问题的几个解决方案,以及一些示例代码。
使用Promise
如果你选择使用Promise,你需要修改你的数据库查询函数,使其返回一个Promise对象,这样你就可以使用.then
来链式调用。
function checkUser(user) {
return new Promise((resolve, reject) => {
db.execQuery({
"sql": "select * from user_info where user_name = ?",
"args": [user.userName],
"handler": (err, results) => {
if (err) {
reject(err);
} else {
resolve(results);
}
}
});
});
}
// 使用示例
checkUser({ userName: 'test' })
.then(results => {
if (results.length > 0) {
// 进行下一步操作
return nextStep();
}
})
.catch(err => console.error(err));
使用async/await
如果你更喜欢同步风格的代码,可以使用async/await。这种方式更加直观,也避免了回调地狱。
async function checkUserAndNext(user) {
try {
const results = await checkUser(user);
if (results.length > 0) {
// 进行下一步操作
await nextStep();
}
} catch (err) {
console.error(err);
}
}
// 使用示例
checkUserAndNext({ userName: 'test' });
总结
无论是Promise还是async/await,它们都能有效地帮助你处理异步流程控制。推荐使用async/await,因为它使代码更加清晰易读。你可以根据自己的需求选择合适的方法。希望这能帮到你!