You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node.js中helper函数返回值设为全局变量返回[object Promise]如何解决

问题根因

你封装的getNotification是async异步函数,所有async函数执行后默认返回Promise对象,你在server.js中直接调用赋值时没有等待异步操作完成,所以全局变量存的是Promise实例而非查询结果,渲染时就会显示[object Promise]。其他控制器中可以正常返回是因为你在调用时用了await或者.then()处理了异步结果。

解决方案

根据你的业务场景可以选择以下两种方案:

方案1:服务启动时预加载通知数据,赋值全局

修改server.js代码,等待异步查询完成后再赋值全局变量,再启动服务:

global.appRoot = path.resolve(__dirname);
const helpersService = require(appRoot + '/services/helpers.service');
// 自执行async函数处理异步逻辑
(async () => {
  // 加await等待数据库查询完成后再赋值
  global.notifcations = await helpersService().getNotification();
  // 原有服务启动逻辑必须放在该函数内部,确保启动时全局变量已赋值
  app.listen(3000, () => {
    console.log('服务启动完成')
  })
})()

如果你的Node.js版本在v14.8及以上,支持顶层await,可以简化为:

global.appRoot = path.resolve(__dirname);
const helpersService = require(appRoot + '/services/helpers.service');
global.notifcations = await helpersService().getNotification();
// 后面正常编写app.listen启动逻辑即可

方案2:渲染时动态查询(更推荐,适配通知需要实时更新的场景)

全局变量只存服务实例,不要直接存固定的查询结果,在渲染ejs模板的控制器中异步获取最新数据后传给模板:

  1. 修改server.js全局赋值逻辑:
global.appRoot = path.resolve(__dirname);
const helpersService = require(appRoot + '/services/helpers.service');
// 全局存服务实例而非固定查询结果
global.helpers = helpersService();
// 后面正常启动服务
app.listen(3000)
  1. 在对应路由的控制器中查询数据再渲染:
// 渲染页面对应的控制器必须是async函数
async function renderNotificationPage(req, res) {
  const notifcations = await global.helpers.getNotification();
  // 把查询结果传给ejs模板
  res.render('view', { notifcations });
}
  1. 原有ejs模板无需修改即可正常渲染数据。

注意事项

  • 如果通知是和用户身份绑定的,绝对不要存在全局变量中,全局变量是所有访问用户共享的,会出现数据串号的问题,这种情况必须使用方案2,每次请求时单独查询当前用户的通知数据。
  • 你现有代码中findStatus被写死为0,if判断永远命中成立分支,这段逻辑可以简化。

内容的提问来源于stack exchange,提问作者sam curb

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.09 07:57:03