Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Cannot add property key, object is not extensible error Apollo Client with antd

I get an error Cannot add property key, object is not extensible using "@apollo/client": "^3.0.2" with ant design.

I can successfully obtain data from the server with my graphql query, however, the problem is that, the data inside the return object is somehow unextendable. This never used to be a problem prior to using apollo client (using apollo boost).

In order to make my data work in a table in ant design, I have to pass in the array data obtained from the data object returned from the server. The part where I get the error is when I attempt to iterate through the items array, and add a key to each object, so that react won't complain in the console of a missing key element for the html.

  const items = [...data.items];
  console.log("items:", items);

  // Add a key for each item to make React stop complaining
  // Erorr occurs here!!!
  items.forEach(item => {
    item.key = item.id;
  });

Is there a way we can remove this unnecessary functionality that's hindering our ability in modifying and extending results obtained from the server? Also I tried spreading the array making a deep copy, but that's not working either.

What do I need to do to make sure that I can add an additional key field in each array item, based on the id?

Addendum:

I don't actually need the code that does the items.forEach() stuff. However, if I don't add it, react will complain that the entries in the table are all missing a key value. This is my workaround since tables in ant design get their data from an array of objects, and thus, need to have a key value in there. Since querying data from the server typically doesn't include a key property in an object, this has to be manually added.

like image 713
pizzae Avatar asked Oct 27 '25 06:10

pizzae


1 Answers

Managed to figure it out by deep copying the array data, via lodash.

Use _.cloneDeep() on the returned data's object that is the name of the object/table you are querying for.

import * as _ from "lodash";
import { Table } from "antd";

function Component({ id, query }) {
  const { loading, error, data } = useQuery(query, {
    variables: { id }
  });

  if (loading) return <div />;
  if (error) return `Error! ${error}`;

  const items = _.cloneDeep(data.items);
  console.log("items:", items);

  // Add a key for each item to make React stop complaining
  items.forEach(item => {
    item.key = item.id;
  });

  return (
          <Table
            dataSource={items}
          />
  );

like image 84
pizzae Avatar answered Oct 28 '25 19:10

pizzae



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!