vietanhyt
vietanhyt

Reputation: 668

Unique "key" prop warning in render method - ReactJS

My app have a warning say that: Each child in an array or iterator should have a unique "key" prop. Check the render method of 'SortableTable' Hear is my SortableTable file:

import React from 'react';
import {Link} from 'react-router';
import {v4 as uuid} from 'node-uuid';

export default class SortableTable extends React.Component {
    render() {

        return (
            <table style={{width: '100%'}} className={this.props.className} id={this.props.id}>
                <thead>
                    <tr>
                        {this.props.headers.map(this.generateHeaders)}
                    </tr>
                </thead>
                <tbody>
                    {this.props.children}
                </tbody>
            </table>
        );
    }

    generateHeaders = (value) => {
        if (Object.keys(value).length === 0) return
        let sort, colspan
        if(value.sort) {

            let {query} = this.props;
            let nQuery, title, icon, colspan = 1;
            if(query.sort === value.sort && query.sortDirection === 'desc') {
                nQuery = Object.assign({}, query, {sort: value.sort, sortDirection: 'asc', page: 1})
                title = 'asc';
                icon = String.fromCharCode(0xe630)
            } else {
                nQuery = Object.assign({}, query, {sort: value.sort, sortDirection: 'desc', page: 1})
                title = 'desc';
                icon = String.fromCharCode(0xe62d)
            }
            sort = <Link to={this.props.link} query={nQuery} className="icon order active" title={title} data-icon={icon} />

        }
        let className = value.className ? value.className : ''
        if(value.colspan) {
            colspan = value.colspan
        }
        return <th className={className} colSpan={colspan}><span>{value.name}</span>{sort}</th>
    }

Can someone show me how to set key prop to resolve this warning?

Upvotes: 0

Views: 1355

Answers (3)

Tom Fenech
Tom Fenech

Reputation: 74645

The <th> element returned by generateHeaders needs to have a key attribute set on it, since you're returning an array of them from your render method.

The simplest way to achieve this is to use the index:

generateHeaders = (value, index) => {
// ...
    return <th key={index} //...

This will make the warning go away but it's better to use a unique property of each value, if one exists. This is because React uses the key to determine whether two items are the same. If you're using the array index and you insert a new value somewhere into the array, the indexes will change, causing the items to be re-rendered unnecessarily.

Upvotes: 1

inthedark122
inthedark122

Reputation: 104

You should insert key into th tag:

generateHeaders = (value, index) => { ... return <th key={index} className={className} colSpan={colspan}><span>{value.name}</span>{sort}</th> }

Upvotes: 0

Pavlo
Pavlo

Reputation: 44917

The idea is to have a key attribute with a unique value. You can use index, the second argument of Array#map callback:

generateHeaders = (value, index) => {
    // ...
    return <th key={index} className={className} colSpan={colspan}><span>{value.name}</span>{sort}</th>
}

Alternatively, if value object has a unique property like id, you may use it instead.

Upvotes: 1

Related Questions