头图

The text starts here~

Overview

When we try to render objects or arrays directly in JSX code, it will generate "Objects are not valid as a React child" error. To resolve this error, in the JSX code, use the map() method to render the array or access the properties of the object.

objects-are-not-valid-as-react-child.png

Below is an example of how the error occurs.

 export default function App() {
  const employees = [
    {id: 1, name: 'Alice', country: 'Austria'},
    {id: 2, name: 'Bob', country: 'Belgium'},
    {id: 3, name: 'Carl', country: 'Canada'},
  ];

  const obj = {
    id: 4,
    name: 'Dean',
    country: 'Denmark',
  };

  // ⛔️ Uncaught Error: Objects are not valid as a React child (found: object with keys {id, name, country}).
  // If you meant to render a collection of children, use an array instead.

  return (
    <div>
      {employees}

      {obj}
    </div>
  );
}

map

The problem with the above code snippet is that in the JSX code we are trying to render arrays or objects directly.

To resolve this error, when rendering JSX code, use map() methods to render arrays or access object properties.

 export default function App() {
  const employees = [
    {id: 1, name: 'Alice', country: 'Austria'},
    {id: 2, name: 'Bob', country: 'Belgium'},
    {id: 3, name: 'Carl', country: 'Canada'},
  ];

  const obj = {
    id: 4,
    name: 'Dean',
    country: 'Denmark',
  };

  return (
    <div>
      {employees.map((employee, index) => {
        return (
          <div key={index}>
            <h2>name: {employee.name}</h2>
            <h2>country: {employee.country}</h2>

            <hr />
          </div>
        );
      })}

      <hr />
      <hr />
      <hr />

      <div>
        <h2>name: {obj.name}</h2>
        <h2>county: {obj.country}</h2>
      </div>

      <hr />
    </div>
  );
}

When debugging, you can use console.log to print the value that caused the error.

JSON.stringify

Alternatively, you can use JSON.stringify() in your JSX code to convert the value to make sure it is of the expected type.

 export default function App() {
  const employees = [
    {id: 1, name: 'Alice', country: 'Austria'},
    {id: 2, name: 'Bob', country: 'Belgium'},
    {id: 3, name: 'Carl', country: 'Canada'},
  ];

  const obj = {
    id: 4,
    name: 'Dean',
    country: 'Denmark',
  };

  return (
    <div>
      <h4>{JSON.stringify(employees)}</h4>

      <h4>{JSON.stringify(obj)}</h4>
    </div>
  );
}

JSON.stringify() method will convert the object to a string before rendering it.

You have to make sure that in JSX code, objects or arrays are not rendered. Instead, you must render primitive values, such as strings and numbers.

Date

Another common cause of this error is when in the JSX code we try to render the Date object directly.

 export default function App() {
  const date = new Date();

  // ⛔️ Objects are not valid as a React child (found: [object Date]).
  return (
    <div>
      <h4>{date}</h4>
    </div>
  );
}

To fix this, we have to access methods on the Date object, say, toLocaleDateString() .

 export default function App() {
  return (
    <div>
      <h4>{date.toLocaleDateString()}</h4>
    </div>
  );
}

Now we use strings instead of objects for rendering, so the bug is resolved.

curly braces

If the error persists, make sure you are not using double curly braces when rendering the variable.

 export default function App() {
  const message = 'hello world';

  // ⛔ Objects are not valid as a React child (found: object with keys {message}).
  return (
    <div>
      <h4>{{message}}</h4>
    </div>
  );
}

Note message variables are wrapped in two sets of curly braces, which is why React thinks it's trying to render an object. To solve this problem, you can just wrap the variable in a set of curly braces.

 export default function App() {
  return (
    <div>
      <h4>{message}</h4>
    </div>
  );
}

React now treats the message variable as an expression containing a string, not an object.

async

If the error persists, make sure that the async function is not called in the JSX code.

async function returns a Promise object, so in JSX code, if the async function is called, the error will occur.

 export default function App() {
  async function getData() {
    return Promise.resolve(42);
  }

  // ⛔ Objects are not valid as a React child (found: [object Promise]).
  return (
    <div>
      <h4>{getData()}</h4>
    </div>
  );
}

To fix this error, we have to call the async function in the useEffect hook or event handler, for example, onClick .

 import {useEffect, useState} from 'react';

export default function App() {
  const [num, setNum] = useState(0);

  useEffect(() => {
    async function getData() {
      const result = await Promise.resolve(42);

      setNum(result);
    }

    getData();
  }, []);

  return (
    <div>
      <h4>{num}</h4>
    </div>
  );
}

Calling the async function in the useEffect hook solves the error because we are now rendering a number, not a Promise object.

Summarize

The React error of "Objects are not valid as a React child" occurs for several reasons:

  • Render objects or arrays directly in JSX code;
  • Render Date object directly in JSX code;
  • Wrap the variable in two sets of curly braces, like: {{message}} instead of {message} ;
  • Call the async function in the JSX code.

chuck
300 声望41 粉丝