使用Create-React-App 16.2与Jest 22时快照测试未完整渲染组件
快照测试仅捕获Accordion组件,Modal未写入快照的问题排查
嘿,我来帮你分析下这个问题——你用Create-React-App 16.2搭配Jest 22跑快照测试,结果只有<Accordion>被记录进快照,<Modal>部分完全没出现,对吧?
问题根源
你的<Modal>组件渲染是依赖组件内部state的open字段的,初始状态里open被设为false,这意味着首次渲染时Modal是处于隐藏状态的。Jest的快照测试只会捕获当前实际渲染到虚拟DOM中的内容,没被渲染的元素自然不会出现在快照文件里。
解决办法
这里有两种可行的方案,你可以根据自己的需求选择:
方案一:在测试中手动触发Modal打开
利用React Test Renderer的instance()方法获取组件实例,调用组件里的show()方法或者直接修改state,让Modal处于打开状态后再生成快照:it('should match its snapshot including modal content', () => { const component = renderer.create(<Summary />); // 调用组件的show方法打开Modal(参数对应dimmer类型,比如'blurring') component.getInstance().show('blurring')(); // 或者直接修改state:component.getInstance().setState({ open: true }); const tree = component.toJSON(); expect(tree).toMatchSnapshot(); })方案二:将Modal状态改为props控制(推荐长期维护)
把Modal的显示状态从组件内部state迁移到props中,这样测试时可以直接通过传入props强制Modal打开,同时也让组件的可控性更强:
先修改Summary.js的部分代码:export default class ItemGroup extends Component { static propTypes = { open: PropTypes.bool, // ...其他props定义 }; static defaultProps = { open: false, }; constructor(props) { super(props); this.state = { // 优先使用props传入的open状态,没有则用默认值 open: props.open, dimmer: 'blurring', }; } // ...其他代码 }然后在测试中直接传入
open={true}:it('should match its snapshot with modal open', () => { const tree = renderer .create(<Summary open={true} />) .toJSON(); expect(tree).toMatchSnapshot(); })
小提示
另外注意下,你的组件类名是ItemGroup,但导入时用的是Summary,虽然因为是默认导出所以没问题,但最好保持类名和导出/导入名称一致,避免后续维护时产生混淆哦~
内容的提问来源于stack exchange,提问作者Sylwek
相关产品推荐
相关产品推荐

