Search code examples
reactjsrestdictionaryspread

Understand the usage of rest and spread parameters with the map function


I want to understand how to properly use the ... operator in js, especially with the js map function.

Say we have the following data:

const SHOP_DATA = [
    {
      id: 1,
      title: 'Hats',
      routeName: 'hats',
      items: [
        {
          id: 1,
          name: 'Brown Brim',
          imageUrl: 'https://i.ibb.co/ZYW3VTp/brown-brim.png',
          price: 25
        }]
    }
]

Now I want to send values as props to another component:

SHOP_DATA.map(({ id, ...otherProps }) => (
          <CollectionPreview key={id} {...otherProps} />

If I understood correctly the first ... is a rest operator, which means we are pooling the values to a new array. and the second ... is a spread operator which means we are spreading those values from the array

And then we need to use the ... operator one more time inside the ColectionPreview to spread them out.

const CollectionPreview = ({ id, ...otherProps }) => {

I don't understand the data flow, why what we just did is equivalent to do :

SHOP_DATA.map(({ id, title , items }) => (
          <CollectionPreview key={id} title = {title} items = {items} />


Solution

  • SHOP_DATA.map(({ id, ...otherProps })

    Here you're destructuring each SHOP_DATA's objects attributes, and using the object's rest operator which inits an object called otherProps with all of the object attributes minus the ones specified before ("id" in this case) :

    otherProps = {
        title: 'Hats',
        routeName: 'hats',
        items: [
            {
                id: 1,
                name: 'Brown Brim',
                imageUrl: 'https://i.ibb.co/ZYW3VTp/brown-brim.png',
                price: 25,
            },
        ],
    };
    

    <CollectionPreview key={id} {...otherProps} />

    Here you are using the JSX spread operator, this is a bit different than the object spread operator, it spreads all attributes of an object to the component props naming them by the attributes names, result :

    <CollectionPreview key={id} title="Hats" routeName="hats" items={[{ id: 1, name: "Brown Brim", etc.. }]} />
    

    const CollectionPreview = ({ id, ...otherProps }) => {

    In the component declaration you're not forced to use the object rest operator, if you know your props names you can use them individually like this :

    const CollectionPreview = ({ id, title, routeName, items }) => {