0

I have a json file that looks similar to this:

[
 {
  "January": [
      {
           "Date": "Jan 1st",
           "Event": "New Years"
      },
      {
           "Date": "Jan 17th",
           "Event": "Chinese New Year"
      }
    ],
  "February": [
      {
           "Date": "Feb 14th",
           "Event": "Valentine's Day"
      },
      {
           "Date": "Feb 29th",
           "Event": "Leap Year"
      }
    ]
 }
]

The json file is structured like this but has many more events and months.

I've tried using a nested loop, and nothing is being returned in JSX. I'm able to get results if I console log it, so I'm not sure if maybe I'm using the wrong functions and if I should use two map loops instead of a forEach with a map loop inside. Here's what I've tried so far:

{EventsList.forEach((monthObj) => {
    const monthObjKeys = Object.keys(monthObj);
    monthObjKeys.map((monthKey) => {
        const monthArr = monthObj[monthKey];
        return (
            <div className='Events__ItemList'>
                <h1 className='Events__Month'>{monthObjKeys}</h1>
                <div className='Events__Item'>
                    <p className='Events__Date'>{monthArr.Date}</p>
                    <p className='Events__Name'>{monthArr.Name}</p>
                </div>
            </div>
        );
    });
})}

Any help/suggestions would be much appreciated

0

2 Answers 2

2

The main problem is .forEach() does not return anything so either you can use .map() or .flatMap().

I would suggest a much simpler way to resolve your issue as the following:

const eventList = [{"January": [{"Date": "Jan 1st","Event": "New Years"},{"Date": "Jan 17th","Event": "Chinese New Year"}],"February": [{"Date": "Feb 14th","Event": "Valentine's Day"},{"Date": "Feb 29th","Event": "Leap Year"}]}]

const events = eventList[0];
const months = Object.keys(events);

const result = months.flatMap(key => events[key]);

console.log(result);

Thus with the result you can .map() through as the following with your JSX:

{
   result.map(({Date, Event}, index) =>
     <div className='Events__ItemList' key={index}>
         <div className='Events__Item'>
            <p className='Events__Date'>{Date}</p>
            <p className='Events__Name'>{Event}</p>
         </div>
     </div>
   ) 
}

You need to use index attribute on every iterated elements as I suggest above.

Read further about List and Keys in the documentation.

Sign up to request clarification or add additional context in comments.

Comments

0

Using a forEach doesn't return an array of React component instances, like using .map would. I might recommend trying this (note:untested) :

{EventsList.flatMap((monthObj) => {
    const monthObjKeys = Object.keys(monthObj);
    return monthObjKeys.map((monthKey) => {
        const monthArr = monthObj[monthKey];
        return (
            <div className='Events__ItemList'>
                <h1 className='Events__Month'>{monthObjKeys}</h1>
                <div className='Events__Item'>
                    <p className='Events__Date'>{monthArr.Date}</p>
                    <p className='Events__Name'>{monthArr.Name}</p>
                </div>
            </div>
        );
    });
})}

So two changes mainly: I used flatMap at the top, since each element of this array is itself returning an array, and I RETURNED the result of the .map() call you had.

If I had used .map at the top instead of .flatMap, it would have been an array of arrays of Components, and I don't think React accepts that -- it wants an array of Components - just 1 layer.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.