反应警告:数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查`App`的渲染方法

Posted

技术标签:

【中文标题】反应警告:数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查`App`的渲染方法【英文标题】:React Warning: Each child in an array or iterator should have a unique "key" prop. Check the render method of `App` 【发布时间】:2017-05-02 12:33:40 【问题描述】:

我遇到了这个错误,但我正在定义一个键。这是我抱怨的App.js

import React from 'react';
import Relay from 'react-relay';
import AccountTable from './AccountTable';

class App extends React.Component 
  render() 
    return (
      <div>
        <h1>Account list</h1>
          this.props.viewer.accounts.edges.map(edge =>
            <AccountTable key=edge.node.id account=edge.node />
          )
      </div>
    );
  


export default Relay.createContainer(App, 
    fragments: 
        viewer: () => Relay.QL`
            fragment on User 
                accounts(first: 10) 
                    edges 
                        node 
                            $AccountTable.getFragment('account')
                        
                    
                
            
        `,
    ,
);

【问题讨论】:

bob ross 会为你的代码山感到自豪。但实际上你应该检查你的 edge.node.id 的唯一性。 我猜是做通常的健全性检查。上面的代码是错误的 100% 来源吗? ids真的是独一无二的吗?也许你有几个未定义/空值 查看是否有重复的ID:console.log(this.props.viewer.accounts.edges.map(edge =&gt; edge.node.id)) 所以,edge.node 对象此时没有定义 id。我认为这是因为节点引用了另一个片段。当我在这个片段中拼写出帐户时,我没有这个问题。当我将帐户 graphql 的东西分解成它自己的片段时,这出现了。你们中有人知道解决方法吗? 【参考方案1】:

纠正此问题的最简单方法是将键基于地图的索引:

this.props.viewer.accounts.edges.map((edge, i) =>
    <AccountTable key=i account=edge.node />
)

那么,您不必担心edge.node.id 的值有多独特。 key 只需要在所有 AccountTable 同级的上下文中是唯一的。它不需要是全球唯一的。所以,索引运行良好。

但是,如果您有一个基于对象的稳定 id,那显然更好。

【讨论】:

根据 react 文档:“当您没有用于渲染项目的稳定 ID 时,您可以使用项目索引作为键作为最后的手段”。因此,我想确保在执行此操作之前无法获得稳定的 id。在这方面有什么建议,还是因为我的节点引用了不同的片段而这不可能? 好吧,除非你有另一个 id,否则这可能是你的“最后手段”,对吧? 它确实解决了这个问题。我将进行更多挖掘,但如果我找不到获取对象 id 的方法,我会将其标记为解决方案。谢谢! 如果使用item index作为key,在数组重新排序的情况下可能会失效:***.com/a/43892905/960857【参考方案2】:

我使用的方案是把relay fragment的底层id提取为key

this.props.viewer.accounts.edges.map((edge) =>
    edge && e.node && <AccountTable key=edge.node.__id account=edge.node />
)

【讨论】:

以上是关于反应警告:数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查`App`的渲染方法的主要内容,如果未能解决你的问题,请参考以下文章

警告:数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查“搜索”的渲染方法

警告:数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查`Units`的渲染方法

警告:数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查`MovieResults`的渲染方法

数组或迭代器中的每个孩子都应该有一个唯一的“key”道具。检查 `Abstractfactory` 的渲染方法

在 li 中反应键

警告:列表中的每个孩子都应该有一个唯一的“关键”道具。反应.js