Firestore事务错误经functions.logger记录为空对象如何修复
问题原因
Firebase Cloud Functions 内置的 functions.logger 在记录传入的对象参数时,会通过类似JSON序列化的逻辑提取对象的可枚举自有属性。而 JavaScript 原生 Error 对象(包括Firestore事务抛出的各类自定义错误子类)的核心属性:name、message、stack、code 等,全部定义为不可枚举属性,直接将错误实例包裹在 { error: error } 这类普通对象中传递时,序列化过程会直接忽略这些不可枚举属性,最终日志里就只会显示空对象 {}。
console.log 能正常打印完整错误,是因为它不走JSON序列化逻辑,会直接读取对象的原型链属性、不可枚举属性做交互式输出,不受这个规则限制。
修复方案
你可以根据自己的日志格式需求选下面任意一种方案:
- 方案1:直接将错误实例作为独立参数传给logger,不要包裹在自定义对象中。logger对直接传入的Error实例做了特殊适配,会自动提取所有错误信息:
catch(error) { functions.logger.error(`Unexpected error occurred:`, error) }
- 方案2:手动提取错误的核心属性,显式传入logger,适合需要同时附带其他业务上下文日志的场景:
catch(error) { functions.logger.error(`Unexpected error occurred:`, { error: { name: error.name, message: error.message, stack: error.stack, code: error.code, // Firestore等服务抛出的错误会带错误码 details: error.details // 部分服务错误会带详细说明 }, // 其他需要记录的上下文参数可以正常追加 refPath: myRef?.path }) }
- 方案3:写一个通用的错误转普通对象工具方法,自动提取Error实例的所有自有属性(包括不可枚举属性),适合项目里统一处理错误日志的场景:
// 工具方法 const normalizeError = (err) => { const errObj = {} Object.getOwnPropertyNames(err).forEach(key => { errObj[key] = err[key] }) return errObj } // 使用示例 catch(error) { functions.logger.error(`Unexpected error occurred:`, { error: normalizeError(error), // 其他业务上下文 operation: 'runTransaction' }) }
注意:不要直接使用
JSON.stringify(error)尝试转换错误对象,该方法同样只会读取可枚举属性,最终得到的结果还是空对象。
内容的提问来源于stack exchange,提问作者Sam
相关产品推荐
相关产品推荐

