如何让electron-preload与Quasar渲染进程异步运行(Nodemailer场景)
问题场景
用Quasar+Electron结合Nodemailer开发桌面SMTP邮件发送功能,功能本身可正常运行,但preload脚本里的邮件发送错误无法被渲染进程的.vue页面捕获——因为transporter.sendMail是回调式异步操作,渲染进程的.vue页面会先执行完毕,等preload里的错误抛出时,页面已无法接收并展示错误,仅能在控制台看到日志。
需要将从数据库读取的SMTP配置及其他参数传给preload完成邮件发送,同时让渲染进程能等待preload的执行结果,捕获错误并反馈给用户。
解决方法
核心是把Nodemailer的回调式调用包装成Promise,让preload暴露的方法返回Promise,这样渲染进程的await就能真正等待异步操作完成,同时用try/catch捕获错误。
修改后的代码
1. electron-preload.js
contextBridge.exposeInMainWorld('myAPI', { sendTheEmail: ( numOfAttach, stringifiedEemailInfoArray, stringifiedemailDetailsArray, stringifiedEtheEmailArray, theEventType, emailType ) => { // 将回调式sendMail包装为Promise return new Promise((resolve, reject) => { transporter.sendMail(mailOptions, (error, info) => { if (error) { console.log("发送错误: " + error) reject(error) // 抛出错误供渲染进程捕获 } else { console.log('邮件发送成功: ' + info.response) resolve(info.response) // 返回成功结果 } }) }) } })
2. 渲染进程.vue文件
try { const res = await myAPI.sendTheEmail( this.attachButtonToggle, this.stringifiedemailSMTPLoginArray, this.stringifiedemailsSubjBodyArray, this.stringifiedemailSendToPeopleArray, this.theEventType, emailType, ) console.log('邮件发送成功响应: ', res) // 此处可添加成功提示,比如弹窗通知用户 } catch (error) { console.error('邮件发送失败: ', error) // 此处把错误展示给用户,比如用Quasar的QNotify弹窗 // this.$q.notify({ type: 'negative', message: `发送失败: ${error.message}` }) }
关键说明
- preload里的方法必须返回Promise,否则渲染进程的
await会直接跳过异步操作,无法获取结果 - 渲染进程用
try/catch包裹await调用,才能捕获preload里reject抛出的错误,进而展示给用户 - 原代码里的
return result无效,因为回调函数的返回值无法传递到外层方法,必须用Promise的resolve/reject传递结果和错误
内容的提问来源于stack exchange,提问作者Cynthia
相关产品推荐
相关产品推荐

