如何将CategoryModel.find返回的categories数组拿到函数外部?
解决Mongoose查询结果无法在函数外部访问的问题
嘿,作为JavaScript新手,我刚踩完一个异步操作的坑——用CategoryModel.find()查询数据库所有记录后,没法在函数外部拿到结果数组categories,折腾了好一会儿终于解决了!我来把过程分享给同样遇到这个问题的小伙伴~
问题场景
最开始我写的代码是这样的:
let categories; // 查询数据库所有分类 CategoryModel.find({}, (err, docs) => { if (err) { console.error('查询出错:', err); return; } categories = docs; // 这里拿到了查询结果 }); console.log(categories); // 结果输出undefined!
明明在回调里已经把结果赋值给categories了,但是外部打印出来却是undefined,当时完全搞不懂哪里出问题。
原因分析
其实核心问题就是异步操作的执行顺序!CategoryModel.find()是一个异步方法,它不会阻塞后续代码的执行——也就是说,代码会先跑console.log(categories),这时候回调函数还没执行,categories自然还没被赋值,所以输出undefined。
解决方法
我试了两种有效的写法,都能解决这个问题:
方法1:用async/await(最直观,推荐新手用)
async/await是ES8的语法,能让异步代码看起来像同步代码一样,可读性超高:
// 定义一个异步函数 async function fetchCategories() { try { // 用await等待查询完成,直接拿到结果 const categories = await CategoryModel.find({}); return categories; // 把结果返回出去 } catch (err) { console.error('查询失败:', err); throw err; // 抛出错误方便上层处理 } } // 调用异步函数的方式1:用.then()处理结果 fetchCategories().then(categories => { console.log(categories); // 这里就能正常拿到结果数组了 // 所有需要用到categories的逻辑都可以放在这里 }); // 调用异步函数的方式2:在另一个async函数里用await async function main() { const categories = await fetchCategories(); console.log(categories); // 在这里处理业务逻辑 } main();
方法2:用Promise链式调用
因为Mongoose的查询方法本身就会返回Promise,所以我们可以直接用.then()来处理结果:
CategoryModel.find({}) .then(categories => { console.log(categories); // 成功拿到结果 // 在这里处理categories的逻辑,比如赋值给外部变量或者渲染页面 }) .catch(err => { console.error('查询出错:', err); });
总结
JavaScript里的异步操作(比如数据库查询、网络请求)都不会等它执行完再跑后续代码,所以绝对不能像同步代码那样直接在外部拿结果。必须在异步操作完成的回调里,或者用async/await等待操作结束后,再去处理拿到的结果。
内容的提问来源于stack exchange,提问作者Berkin
相关产品推荐
相关产品推荐

