简体   繁体   中英

React: props are undefined, even though they should be

my props in the children class is supposed to be an array of Event objects.

I am checking beforehand, if the array is empty in App.js like this:


function App() {

  class Event {
    constructor(id, title, date){
      this.id = id;
      this.title = title;
      this.date = date;
    }
  }

  const [events, setEvents] = useState([])
  const [ids, setIds] = useState([])
  const [safedIds, setSafedIds] = ([])
  const [eventsPrep, setEventsPrep] = useState([Event])

  useEffect(() => {
      fetch('https://someAPI.com')
      .then(response => response.json())
      .then(
        res => {setEvents(res); 
        console.log(res);
      })
      .catch(err => console.log(err))
      .then(handleIncomingData())
      //.then(console.log("was here"))
  }, [])

  function handleIncomingData () {
    if(events.length > 0) {
      events.forEach(event => {
        ids.push(event["_id"]);
        let date = new Date(event["date"]);
        eventsPrep.push(new Event(event["_id"], event["title"], date.toDateString()))
      })
    } 
  }

  return (
    <>  
      <Navbar/>
      {eventsPrep.length > 0 ? <Home events={eventsPrep}/> : <></>}
    </>
    
  );
}

export default App;

but whenever I try to reach the props in the child component it is considered undefined.

My child component:

import React from 'react'
import SingleEvent from '../../event/SingleEvent'


export const Home = (props) => {
    console.log(props.events)
    return (
        <>
          {props?.events
            ? props.events.forEach((event) => {
                console.log('was here 2');
                return <SingleEvent title={event.title} start={event.date} />;
              })
            : 'no upcomming events'}
        </>
    );
  
}

Even if I only pass a string down, it is still undefined.

Thanks for help!

In your useEffect() you update events via setEvents(res) and call handleIncomingData() after that.

In handleIncomingData() you use events , but it will still hold the value from previous render / from the initialization as setEvents(res) will not change events immidiately. You can console.log(events) inside that function to investigate this. Instead you can pass res into handleIncomingData() and use it instead of events inside that function. So in you useEffect you would have:

.then(response => response.json())
.then(
    res => {
      setEvents(res); 
      handleIncomingData(res);
    })

In addition in handleIncomingData() use setEventsPrep(...) instead of eventsPrep.push() , as mentioned in the comment.

You are returning 2 return statments in the component. Only need to return 1 return statement in component

export const Home = (props) => {
  return (
    <>
      {props?.events && Object.values(props.events).length > 0
        ? props.events.forEach((event) => {
            console.log('was here 2');
            return <SingleEvent title={event.title} start={event.date} />;
          })
        : 'no upcomming events'}
    </>
  );
};

Also to check whether eventsPrep has a length > 0 then try it this way if eventsPrep is an object

eventsPrep && Object.values(eventsPrep).length > 0

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM