React 16.2中含条件式三插值的<option>导致React DOM崩溃问题咨询
React 16.2:
NotFoundError When <option> Contains Three Interpolations Including a Conditional Expression 我碰到过这个一模一样的问题!当 <option> 标签内包含三个插值内容,且其中一个是条件表达式时,切换 <select> 的值会抛出 NotFoundError: Node was not found 错误。这个场景在 React 15 中运行完全正常,但在 React 16.2 版本中会触发异常。
问题复现的核心代码
class App extends React.Component { constructor(props) { super(props); this.state = { value: 'a' }; } handleChange = (e) => { this.setState({ value: e.target.value }); } render() { return ( <select value={this.state.value} onChange={this.handleChange}> {/* 这个option的混合插值结构就是问题根源 */} <option value="a"> {'Prefix '} {true ? 'Conditional' : 'Else'} {' Suffix'} </option> <option value="b">Option B</option> </select> ); } } ReactDOM.render(<App />, document.getElementById('root'));
问题原因
这是 React 16.2 在 DOM diff 算法上的一个特定 bug:当 <option> 的子节点是「文本插值 + 条件表达式插值 + 文本插值」这种混合结构时,React 在更新 DOM 节点的过程中无法正确追踪节点的存在状态,导致尝试操作一个已经被移除的节点,最终抛出 NotFoundError。
可行的解决办法
这里有几个快速修复的方案,按推荐程度排序:
- 升级 React 版本:这个 bug 在 React 16.3 及后续版本中已经被官方修复,升级到新版本是最彻底的解决方式。
- 合并插值内容:把多个插值合并成单个表达式,避免拆分的多节点混合:
<option value="a"> {`Prefix ${true ? 'Conditional' : 'Else'} Suffix`} </option> - 用单个元素包裹所有内容:给
<option>里的所有插值套一个行内元素(比如<span>),让<option>只包含单个子节点:<option value="a"> <span> {'Prefix '} {true ? 'Conditional' : 'Else'} {' Suffix'} </span> </option>
内容的提问来源于stack exchange,提问作者Melchia
相关产品推荐
相关产品推荐

