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

原生JavaScript访问React Props及函数的内部属性遍历问题

问题背景
  • 研究React运行机制过程中,正在开发Google Chrome扩展,无法直接获取React组件的访问权限,需要通过原生JavaScript访问props中封装的函数,实现测试场景下的点击自动化操作。已知安装React开发者工具扩展后可在Chrome开发者控制台查看相关内容,但该方案无法满足需求。
现象描述
  • 在Chrome开发者控制台中可通过如下代码选中目标DOM元素:
var elem = document.querySelector('.wrap-XdW9S1Ib');
  • 上述元素为目标操作对象,它的props中包含需要调用的onClick事件处理函数。在控制台交互界面手动输入如下代码:
elem.__reactProps$63clhtkk874

可以正常获取到包含onClick等React自动生成函数的props对象,可清晰看到React生成的onClick事件与其他函数。

  • 将完全相同的逻辑写入普通JS文件执行时,尤其是运行如下遍历代码:
for(key in elem){console.log(key);}

遍历元素所有属性时,__reactFiber和__reactProps这类属性完全不会出现在遍历结果中,仅能获取到align、title、lang等DOM原生属性,无法看到React相关属性。

  • 代码逻辑和控制台手动输入的逻辑完全一致,控制台打印功能运行正常,唯独无法获取到React挂载的事件相关属性。
核心疑问

为什么这类React内部属性在开发者控制台手动输入指令时可以正常访问,在普通JS文件(非控制台交互式输入环境)中运行相同代码时,无法通过遍历获取到这些属性?


原因说明

出现这个差异的核心原因有两个:

  1. React内部属性的不可枚举特性
    React 16及之后版本,挂载到真实DOM节点上的__reactFiber$[随机后缀]、__reactProps$[随机后缀]这类内部属性,都是通过Object.defineProperty方法定义的,默认设置了enumerable: false,也就是不可枚举属性。
    原生JS的for...in循环、Object.keys()方法,默认只会遍历对象自身及原型链上可枚举的属性,自然不会把这些不可枚举的React内部属性列出来。这不是属性不存在——只要你写对完整的属性名,哪怕是不可枚举属性,直接访问是可以正常拿到值的。
  2. Chrome控制台的执行环境特殊处理
    Chrome开发者工具的交互式控制台不是纯原生JS执行环境,它做了一层额外封装:当你在控制台输入代码访问DOM元素、打印元素属性时,控制台会主动读取元素上所有不可枚举的内部属性、甚至浏览器层面的内部绑定属性做展示,相当于帮你绕过了原生JS的可枚举属性遍历限制,所以你手动输入属性名访问、甚至在控制台展开元素看属性的时候,能看到这些React内部字段。
普通JS脚本中获取React内部属性的实现方案

不要用for...in遍历,直接通过获取对象自身所有属性(包含不可枚举属性)的方式匹配键名即可,适配Chrome扩展content script、普通页面JS场景:

// 选中目标元素
const elem = document.querySelector('.wrap-XdW9S1Ib');
// 获取元素自身的所有属性名,包含不可枚举属性
const ownPropNames = Object.getOwnPropertyNames(elem);
// 匹配React挂载的props、fiber对应的键名(同页面所有React元素的后缀一致)
const reactPropsKey = ownPropNames.find(key => key.startsWith('__reactProps'));
const reactFiberKey = ownPropNames.find(key => key.startsWith('__reactFiber'));
// 直接访问对应值
const reactProps = elem[reactPropsKey];
const reactFiber = elem[reactFiberKey];
// 比如要调用onClick,直接取即可
const onClickHandler = reactProps.onClick;
// 执行点击逻辑,注意要根据业务逻辑补全事件对象参数
onClickHandler?.();

注意:不要硬编码__reactProps后面的随机后缀,这个后缀是React初始化时随机生成的,不同页面、不同React版本的后缀都不一样,必须运行时动态匹配。


内容的提问来源于stack exchange,提问作者Joseph Astrahan

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 23:21:48