Object.hasOwn 对 null 或 undefined 抛出 TypeError 并非什么 bug,而是设计上故意为之——它就是要严格校验参数类型,让数据问题及早暴露;它不做隐式转换,只接受真实对象。配合 `obj != null && Object.hasOwn(obj, 'key')`
Object.hasOwn 处理 null/undefined 对象的安全性
作者:技术拾光
时间:2026-07-06
浏览:501
文章目录
Object.hasOwn 对 null 或 undefined 抛出 TypeError 并非什么 bug,而是设计上故意为之——它就是要严格校验参数类型,让数据问题及早暴露;它不做隐式转换,只接受真实对象。配合 `obj != null && Object.hasOwn(obj, 'key')` 这种写法,就能稳稳地安全使用。

直接说结论:Object.hasOwn 对 null 或 undefined 会直接抛出 TypeError。这并非设计缺陷,而是刻意为之——它只认对象类型,不进行隐式转换。
为何不自动处理 null/undefined
与传统的 obj.hasOwnProperty() 不同,Object.hasOwn 是静态方法,不依赖目标对象的原型链或内部结构。但它更为严格——仅对真实对象有效。这种"遇错即报"的机制,有助于尽早发现数据源问题,避免 bug 在深层逻辑中蔓延。
Object.hasOwn(null, 'key')→ 直接报TypeError: Cannot convert undefined or null to objectObject.hasOwn(undefined, 'key')→ 同样报错Object.hasOwn({}, 'key')、Object.hasOwn(new Date(), 'getTime')→ 正常工作
安全写法:先判空再检测
实际开发中,对象可能来自 API 响应、用户输入或可选参数,因此主动防护是必要的:
- 推荐:使用
obj != null && typeof obj === 'object'前置判断 - 简洁组合:
obj != null && Object.hasOwn(obj, 'prop') - 避免:
Object.hasOwn(obj || {}, 'prop')—— 若obj为字符串或数字,obj || {}会掩盖类型错误,且字符串/数字对象可能包含意外的自有属性(如'abc'.length)
与其他方式的容错差异
这种严格性恰恰是它的优势:
'prop' in obj:对 null/undefined 返回false,看似安全,但会查询原型链,可能误判继承属性obj.prop !== undefined:可防崩溃,但无法区分"属性不存在"与"属性存在但值为undefined"Object.prototype.hasOwnProperty.call(obj, 'prop'):对 null/undefined 同样报错,行为一致,但写法繁琐,且依赖Object.prototype未被篡改
Symbol 键也需注意类型
传入 Symbol 时,对象参数也必须有效:
-
const sym = Symbol('id'); Object.hasOwn({[sym]: 1}, sym) -
Object.hasOwn(null, sym)→ 报错,与字符串键一致 -
Object.hasOwn(obj, 'Symbol(id)')→ 不会匹配 Symbol 键,因为字符串与 Symbol 属于不同类型
实用工具推荐
电子包浆
使用 ›绿化、压缩、噪点和虚拟水印,自由调节做旧程度。
图片压缩
使用 ›选择画质和输出格式,预览压缩前后的大小。