Error missing key prop for element in iterator

I am new to React, and I'm trying to output a table containing the information of users. But Eslint is keep giving me the following error: [eslint] Missing "key" prop for element in iterator [reac...

I am new to React, and I’m trying to output a table containing the information of users. But Eslint is keep giving me the following error:

[eslint] Missing "key" prop for element in iterator [react/jsx-key]

I am not sure if I did this properly, but I have assigned a unique ID number for each person in the user list, but not sure why the error is persistent.

So in my PeopleCard.js I have the following:

import React from "react";
import {
  Card,
  CardImg,
  CardText,
  CardBody,
  CardTitle,
  CardSubtitle,
  Button
} from "reactstrap";
import PropTypes from "prop-types";

class PeopleCard extends React.Component {
  static propTypes = {
    person: PropTypes.object,
    id: PropTypes.number,
    name: PropTypes.string,
    company: PropTypes.string,
    description: PropTypes.string
  };
  render() {
    return (
      <div>
        <Card>
          <CardImg
            top
            width="100%"
            src="https://via.placeholder.com/318x180.png"
            alt="Card image cap"
          />
          <CardBody>
            <CardTitle>{this.props.person.name}</CardTitle>
            <CardSubtitle>{this.props.person.company}</CardSubtitle>
            <CardText>{this.props.person.description}</CardText>
            <Button>Button</Button>
          </CardBody>
        </Card>
      </div>
    );
  }
}

export default PeopleCard;

And in my MainArea.js, I have the following:

import React from "react";
import { Container, Row, Col } from "reactstrap";
import PeopleCard from "./PeopleCard";

class MainArea extends React.Component {
  constructor() {
    super();
    this.state = {
      people: [
        {
          id: 1,
          name: "John",
          company: "Some Company, Inc",
          description: "Met at a party."
        },
        {
          id: 2,
          name: "Mary",
          company: "Some Company, Inc",
          description: "Met at a party."
        },
        {
          id: 3,
          name: "Jane",
          company: "Some Company, Inc",
          description: "Met at a party."
        }
      ]
    };
  }
  render() {
    let peopleCard = this.state.people.map(person => {
      return (
        <Col sm="4">
          <PeopleCard key={person.id} person={person} />
        </Col>
      );
    });
    return (
      <Container fluid>
        <Row>{peopleCard}</Row>
      </Container>
    );
  }
}

export default MainArea;

The following line is throwing the error, and I cannot figure out why:

<Col sm="4">
   <PeopleCard key={person.id} person={person} />
</Col>

How can I prevent this error from appearing?

First of all, great work on the jsx-key rule. I think this will save people a lot of time.

Now, I have the following code:

<TransitionMotion
  styles={this._getStyles()}
  willEnter={this._willEnter}
  willLeave={this._willLeave}
  >
  {styles =>
    <div>
      {Object.keys(styles).map(key =>
        <Toast
          action={styles[key].action}
          key={key}
          message={styles[key].message}
          opacity={styles[key].opacity}
          translateY={`${styles[key].translateY}%`}
        />
      )}
    </div>
  }
</TransitionMotion>

using the jsx-key rule, I am getting the missing key prop on the line that has the opening <div>. I might be misunderstanding when key should be used, but I don’t think I need one here. And, if I do, then the error message that this rule outputs is misleading since it claims that I am in an iterator when I am not.

I noticed in the documentation:

Also, if you have some prevalent situation where you use arrow functions to return JSX that will not be held in an iterable, you may want to disable this rule.

which I believe is referring to this situation, but I figured I’d open an issue for this anyway in case there happens to be a solution lurking.

I am new to React, and I’m trying to output a table containing the information of users. But Eslint is keep giving me the following error:

[eslint] Missing "key" prop for element in iterator [react/jsx-key]

I am not sure if I did this properly, but I have assigned a unique ID number for each person in the user list, but not sure why the error is persistent.

So in my PeopleCard.js I have the following:

import React from "react";
import {
  Card,
  CardImg,
  CardText,
  CardBody,
  CardTitle,
  CardSubtitle,
  Button
} from "reactstrap";
import PropTypes from "prop-types";

class PeopleCard extends React.Component {
  static propTypes = {
    person: PropTypes.object,
    id: PropTypes.number,
    name: PropTypes.string,
    company: PropTypes.string,
    description: PropTypes.string
  };
  render() {
    return (
      <div>
        <Card>
          <CardImg
            top
            width="100%"
            src="https://via.placeholder.com/318x180.png"
            alt="Card image cap"
          />
          <CardBody>
            <CardTitle>{this.props.person.name}</CardTitle>
            <CardSubtitle>{this.props.person.company}</CardSubtitle>
            <CardText>{this.props.person.description}</CardText>
            <Button>Button</Button>
          </CardBody>
        </Card>
      </div>
    );
  }
}

export default PeopleCard;

And in my MainArea.js, I have the following:

import React from "react";
import { Container, Row, Col } from "reactstrap";
import PeopleCard from "./PeopleCard";

class MainArea extends React.Component {
  constructor() {
    super();
    this.state = {
      people: [
        {
          id: 1,
          name: "John",
          company: "Some Company, Inc",
          description: "Met at a party."
        },
        {
          id: 2,
          name: "Mary",
          company: "Some Company, Inc",
          description: "Met at a party."
        },
        {
          id: 3,
          name: "Jane",
          company: "Some Company, Inc",
          description: "Met at a party."
        }
      ]
    };
  }
  render() {
    let peopleCard = this.state.people.map(person => {
      return (
        <Col sm="4">
          <PeopleCard key={person.id} person={person} />
        </Col>
      );
    });
    return (
      <Container fluid>
        <Row>{peopleCard}</Row>
      </Container>
    );
  }
}

export default MainArea;

The following line is throwing the error, and I cannot figure out why:

<Col sm="4">
   <PeopleCard key={person.id} person={person} />
</Col>

How can I prevent this error from appearing?

Answer by Emberly Cox

You are rendering an array of elements, so React needs a key prop (1) to identify elements and optimize things.,

3

That doesn’t sound right, unless you render inner elements in an array.

– kLabz
Apr 3 ’20 at 9:00

,

Maybe you are right, I am new to react. Maybe something else was at play too, and setting key to child elements was just superfluous.

– Sahil Singh
Apr 6 ’20 at 5:41

Add key={topic.id} to your jsx:

return (
    <div>
        <h2>Results List</h2>
        {topics.map((topic: any) =>
            <div className="panel panel-default" key={topic.id}>
                <div className="panel-heading">{topic.name}</div>
                <div className="panel-body">{topic.description}</div>
            </div>
        )}
    </div>
);

Answer by Emelia Kent

You should put the key on the outer element:

const peopleCard = this.state.people.map(person => (
  <Col key={person.id} sm="4">
    <PeopleCard person={person} />
  </Col>
));

Answer by Lance Correa

eslint-plugin-react naively checks just if the element is a part of an arrow expression. I’m setting up a PR…,

Sponsor

Sponsor yannickcr/eslint-plugin-react

,I am also noticing that this gives false errors on pure functional stateless components that are now available as of React 0.14:

<TransitionMotion
  styles={this._getStyles()}
  willEnter={this._willEnter}
  willLeave={this._willLeave}
  >
  {styles =>
    <div>
      {Object.keys(styles).map(key =>
        <Toast
          action={styles[key].action}
          key={key}
          message={styles[key].message}
          opacity={styles[key].opacity}
          translateY={`${styles[key].translateY}%`}
        />
      )}
    </div>
  }
</TransitionMotion>

Answer by Zeke Wood

key prop should be defined at each element inside the children of a React element,This rule applies when key prop is missing at each element inside the children of a React element.,React Warning: Each child in an array or iterator should have a unique «key» prop. Check the render method of Hello. See https://fb.me/react-warning-keys for more information.

import React from 'react';

export class Hello extends React.Component {
    render() {
        var childs = this.props.greetings.map((greeting) => <li value={greeting.name}>{greeting.name}</li>); // REACT_MISSING_KEY_PROP alarm

        return (
            <ul>
                {childs}
            </ul>
        );
    }
}

Answer by Spencer Cuevas

The file is as below «Results.tsx»,
reactjs — Extend HTML elements in react and typescript while retaining props
,
reactjs — Typescript solution for the remaining props in react

Is there a way to fix this issue?

npm start

client/src/Results.tsx
(32,21): Missing "key" prop for element.

The file is as below «Results.tsx»

import * as React from 'react';
 class Results extends React.Component<{}, any> {

constructor(props: any) {
    super(props);

    this.state = {
        topics: [],
        isLoading: false
    };
}

componentDidMount() {
    this.setState({isLoading: true});

    fetch('http://localhost:8080/topics')
        .then(response => response.json())
        .then(data => this.setState({topics: data, isLoading: false}));
}

render() {
    const {topics, isLoading} = this.state;

    if (isLoading) {
        return <p>Loading...</p>;
    }

    return (
        <div>
            <h2>Results List</h2>
            {topics.map((topic: any) =>
                <div className="panel panel-default">
                    <div className="panel-heading" key={topic.id}>{topic.name}</div>
                    <div className="panel-body" key={topic.id}>{topic.description}</div>
                </div>
            )}
        </div>
    );
}
}

export default Results;

Answer by Kellen Sims

Let’s assign a key to our list items inside numbers.map() and fix the missing key issue.,A good rule of thumb is that elements inside the map() call need keys.,We include the entire listItems array inside a <ul> element, and render it to the DOM:

const numbers = [1, 2, 3, 4, 5];
const doubled = numbers.map((number) => number * 2);console.log(doubled);

Answer by Cadence Bradley

React uses the key prop create a relationship between the component and the DOM element. The library uses this relationship to determine whether or not the component should be re-rendered.,It is not recommended to use the index of the array as the key prop if you know the array will not be static. If the key is an index, reordering an item in the array changes it. Then React will get confused and re-render the incorrect element.,When creating a list in the UI from an array with JSX, you should add a key prop to each child and to any of its’ children.

The Problem

Warning: Each child in a list should have a unique "key" prop
Warning: Each child in a list should have a unique "key" prop
<ul>
  {["Item1", "Item2", "Item3"].map(item =>
  <li>{item}</li>
  )}
</ul>

Keys do not have to be unique globally. They just need to be unique across sibling elements.

<ul>
  {["Item1", "Item2", "Item3"].map(item =>
  <li key="{item}">{item}</li>
  )}
</ul>

Answer by Xiomara Coleman

For React, intrinsic elements are emitted as strings (React.createElement(«div»)), whereas a component you’ve created is not (React.createElement(MyComponent)).,For intrinsic elements, it is the type of the property on JSX.IntrinsicElements,As the name suggests, the component is defined as a JavaScript function where its first argument is a props object.
TS enforces that its return type must be assignable to JSX.Element.

Recall how to write a type assertion:

tsvar foo = <foo>bar;

Since the above syntax cannot be used in .tsx files, an alternate type assertion operator should be used: as.
The example can easily be rewritten with the as operator.

tsvar foo = bar as foo;

Intrinsic elements are looked up on the special interface JSX.IntrinsicElements.
By default, if this interface is not specified, then anything goes and intrinsic elements will not be type checked.
However, if this interface is present, then the name of the intrinsic element is looked up as a property on the JSX.IntrinsicElements interface.
For example:

tsdeclare namespace JSX {  interface IntrinsicElements {    foo: any;  }}<foo />; // ok<bar />; // error

Note: You can also specify a catch-all string indexer on JSX.IntrinsicElements as follows:

tsdeclare namespace JSX {  interface IntrinsicElements {    [elemName: string]: any;  }}

Value-based elements are simply looked up by identifiers that are in scope.

tsimport MyComponent from "./myComponent";<MyComponent />; // ok<SomeOtherComponent />; // error

As the name suggests, the component is defined as a JavaScript function where its first argument is a props object.
TS enforces that its return type must be assignable to JSX.Element.

tsinterface FooProp {  name: string;  X: number;  Y: number;}declare function AnotherComponent(prop: { name: string });function ComponentFoo(prop: FooProp) {  return <AnotherComponent name={prop.name} />;}const Button = (prop: { value: string }, context: { color: string }) => (  <button />);

Because a Function Component is simply a JavaScript function, function overloads may be used here as well:

tsinterface ClickableProps {  children: JSX.Element[] | JSX.Element;} interface HomeProps extends ClickableProps {  home: JSX.Element;} interface SideProps extends ClickableProps {  side: JSX.Element | string;} function MainButton(prop: HomeProps): JSX.Element;function MainButton(prop: SideProps): JSX.Element;function MainButton(prop: ClickableProps): JSX.Element {  // ...}

Once the class type is established, the instance type is determined by the union of the return types of the class type’s construct or call signatures (whichever is present).
So again, in the case of an ES6 class, the instance type would be the type of an instance of that class, and in the case of a factory function, it would be the type of the value returned from the function.

tsclass MyComponent {  render() {}}// use a construct signaturevar myComponent = new MyComponent();// element class type => MyComponent// element instance type => { render: () => void }function MyFactoryFunction() {  return {    render: () => {},  };}// use a call signaturevar myComponent = MyFactoryFunction();// element class type => MyFactoryFunction// element instance type => { render: () => void }

The element instance type is interesting because it must be assignable to JSX.ElementClass or it will result in an error.
By default JSX.ElementClass is {}, but it can be augmented to limit the use of JSX to only those types that conform to the proper interface.

tsdeclare namespace JSX {  interface ElementClass {    render: any;  }}class MyComponent {  render() {}}function MyFactoryFunction() {  return { render: () => {} };}<MyComponent />; // ok<MyFactoryFunction />; // okclass NotAValidComponent {}function NotAValidFactoryFunction() {  return {};}<NotAValidComponent />; // error<NotAValidFactoryFunction />; // error

For intrinsic elements, it is the type of the property on JSX.IntrinsicElements

tsdeclare namespace JSX {  interface IntrinsicElements {    foo: { bar?: boolean };  }}// element attributes type for 'foo' is '{bar?: boolean}'<foo bar />;

For value-based elements, it is a bit more complex.
It is determined by the type of a property on the element instance type that was previously determined.
Which property to use is determined by JSX.ElementAttributesProperty.
It should be declared with a single property.
The name of that property is then used.
As of TypeScript 2.8, if JSX.ElementAttributesProperty is not provided, the type of first parameter of the class element’s constructor or Function Component’s call will be used instead.

tsdeclare namespace JSX {  interface ElementAttributesProperty {    props; // specify the property name to use  }}class MyComponent {  // specify the property on the element instance type  props: {    foo?: string;  };}// element attributes type for 'MyComponent' is '{foo?: string}'<MyComponent foo="bar" />;

The element attribute type is used to type check the attributes in the JSX.
Optional and required properties are supported.

tsdeclare namespace JSX {  interface IntrinsicElements {    foo: { requiredProp: string; optionalProp?: number };  }}<foo requiredProp="bar" />; // ok<foo requiredProp="bar" optionalProp={0} />; // ok<foo />; // error, requiredProp is missing<foo requiredProp={0} />; // error, requiredProp should be a string<foo requiredProp="bar" unknownProp />; // error, unknownProp does not exist<foo requiredProp="bar" some-unknown-prop />; // ok, because 'some-unknown-prop' is not a valid identifier

The spread operator also works:

tsvar props = { requiredProp: "bar" };<foo {...props} />; // okvar badProps = {};<foo {...badProps} />; // error

In TypeScript 2.3, TS introduced type checking of children. children is a special property in an element attributes type where child JSXExpressions are taken to be inserted into the attributes.
Similar to how TS uses JSX.ElementAttributesProperty to determine the name of props, TS uses JSX.ElementChildrenAttribute to determine the name of children within those props.
JSX.ElementChildrenAttribute should be declared with a single property.

tsdeclare namespace JSX {  interface ElementChildrenAttribute {    children: {}; // specify children name to use  }}

ts

declare namespace JSX {

interface ElementChildrenAttribute {

children: {}; // specify children name to use

}

}

ts<div>  <h1>Hello</h1></div>;<div>  <h1>Hello</h1>  World</div>;const CustomComp = (props) => <div>{props.children}</div><CustomComp>  <div>Hello World</div>  {"This is just a JS expression..." + 1000}</CustomComp>

You can specify the type of children like any other attribute. This will override the default type from, eg the React typings if you use them.

tsinterface PropsType {  children: JSX.Element  name: string}class Component extends React.Component<PropsType, {}> {  render() {    return (      <h2>        {this.props.children}      </h2>    )  }}// OK<Component name="foo">  <h1>Hello World</h1></Component>// Error: children is of type JSX.Element not array of JSX.Element<Component name="bar">  <h1>Hello World</h1>  <h2>Hello World</h2></Component>// Error: children is of type JSX.Element not array of JSX.Element or string.<Component name="baz">  <h1>Hello</h1>  World</Component>

JSX allows you to embed expressions between tags by surrounding the expressions with curly braces ({ }).

tsvar a = (  <div>    {["foo", "bar"].map((i) => (      <span>{i / 2}</span>    ))}  </div>);

The above code will result in an error since you cannot divide a string by a number.
The output, when using the preserve option, looks like:

tsvar a = (  <div>    {["foo", "bar"].map(function (i) {      return <span>{i / 2}</span>;    })}  </div>);

To use JSX with React you should use the React typings.
These typings define the JSX namespace appropriately for use with React.

ts/// <reference path="react.d.ts" />interface Props {  foo: string;}class MyComponent extends React.Component<Props, {}> {  render() {    return <span>{this.props.foo}</span>;  }}<MyComponent foo="bar" />; // ok<MyComponent foo={0} />; // error

Answer by Alayah Beasley

https://stackoverflow.com/questions/48266018/missing-key-prop-for-element-reactjs-and-typescript,When rendering an array of elements, React needs a key prop (1) to identify elements and optimize things.,Add key={topic.id} to your element in jsx:

return (
    <div>
        <h2>Results List</h2>
        {topics.map((topic: any) =>
            <div className="panel panel-default" key={topic.id}>
                <div className="panel-heading">{topic.name}</div>
                <div className="panel-body">{topic.description}</div>
            </div>
        )}
    </div>
);

Answer by Canaan Daugherty

More Details Refer


Answer by Alexis Bentley

More Details Refer


Я новичок в React, и я пытаюсь вывести таблицу, содержащую информацию пользователей. Но Эслинт продолжает давать мне следующую ошибку:

[eslint] Missing "key" prop for element in iterator [react/jsx-key]

Я не уверен, что сделал это правильно, но я назначил уникальный идентификационный номер для каждого человека в списке пользователей, но не уверен, почему ошибка не устранена.

Так что в моем PeopleCard.js у меня есть следующее:

import React from "react";
import {
Card,
CardImg,
CardText,
CardBody,
CardTitle,
CardSubtitle,
Button
} from "reactstrap";
import PropTypes from "prop-types";

class PeopleCard extends React.Component {
static propTypes = {
person: PropTypes.object,
id: PropTypes.number,
name: PropTypes.string,
company: PropTypes.string,
description: PropTypes.string
};
render() {
return (
<div>
<Card>
<CardImg
top
width="100%"
src="https://via.placeholder.com/318x180.png"
alt="Card image cap"
/>
<CardBody>
<CardTitle>{this.props.person.name}</CardTitle>
<CardSubtitle>{this.props.person.company}</CardSubtitle>
<CardText>{this.props.person.description}</CardText>
<Button>Button</Button>
</CardBody>
</Card>
</div>
);
}
}

export default PeopleCard;

И в моем MainArea.js у меня есть следующее:

import React from "react";
import { Container, Row, Col } from "reactstrap";
import PeopleCard from "./PeopleCard";

class MainArea extends React.Component {
constructor() {
super();
this.state = {
people: [
{
id: 1,
name: "John",
company: "Some Company, Inc",
description: "Met at a party."
},
{
id: 2,
name: "Mary",
company: "Some Company, Inc",
description: "Met at a party."
},
{
id: 3,
name: "Jane",
company: "Some Company, Inc",
description: "Met at a party."
}
]
};
}
render() {
let peopleCard = this.state.people.map(person => {
return (
<Col sm="4">
<PeopleCard key={person.id} person={person} />
</Col>
);
});
return (
<Container fluid>
<Row>{peopleCard}</Row>
</Container>
);
}
}

export default MainArea;

Следующая строка выдает ошибку, и я не могу понять, почему:

<Col sm="4">
<PeopleCard key={person.id} person={person} />
</Col>

Как я могу предотвратить появление этой ошибки?

Понравилась статья? Поделить с друзьями:

Читайте также:

  • Error missing in texturedef u
  • Error missing from clause entry for table users
  • Error missing from clause entry for table rank
  • Error missing from clause entry for table postgres
  • Error missing description in mod

  • 0 0 голоса
    Рейтинг статьи
    Подписаться
    Уведомить о
    guest

    0 комментариев
    Старые
    Новые Популярные
    Межтекстовые Отзывы
    Посмотреть все комментарии