So I am building a React Ionic Typescript project. I am using the React hooks to set an array of objects. I then map through that array of objects and am trying to access a certain key in that object but it is saying that it doesn't exist (challenge.name).
const FindChallenges: React.FC = () => {
const { isAuthenticated } = useAuth0();
const [searchedChallenge, setSearchedChallenge] = useState<string>(); // what user searched.
const [allChallenges, setAllChallenges] = useState<Array<Object>>([]); // the challenges that match search.
// const [test, setTest] = useState<Array<Object>>([{1:"test"}, {2: "hello"}, {3: "world"}]);
// Only works for web right now.
// Will need to set up PORT forwarding for ios/android.
const API_URL = "http://localhost:3001";
useEffect(() => {
// if (!isAuthenticated) return;
fetch(API_URL "/api/getAllChallenges", {
headers: {
'Content-Type': 'application/json',
'Accept': 'application/json'
}
})
.then(data => data.json())
.then(res => {
let results = [];
for (let key in res) {
results.push(res[key])
}
setAllChallenges(results);
})
}, []);
if (!isAuthenticated) return (<PageLock />);
const handleSubmit = (e: React.FormEvent) => {
e.preventDefault();
console.log("FORM SUBMITTED");
// setSearchedChallenge("");
}
return (
<IonPage>
<IonHeader>
<IonToolbar>
<IonTitle className="ion-text-center">Find a Challenge</IonTitle>
</IonToolbar>
</IonHeader>
<IonContent fullscreen>
{/* <IonHeader collapse="condense">
<IonToolbar>
<IonTitle size="large">Find ChallengesTab</IonTitle>
</IonToolbar>
</IonHeader> */}
<IonCard>
{/* <IonItem>
<IonLabel className="ion-text-center" id="profileLabel">Your Challenges</IonLabel>
</IonItem> */}
<IonCardContent id="ionCardContent">
<form onSubmit={handleSubmit}>
<IonInput clear-input="true" id="search-challenge-input" value={searchedChallenge} placeholder="Enter Input" onIonChange={e => setSearchedChallenge(e.detail.value!)}></IonInput>
<IonButton expand="block" type="submit" className="ion-margin-top">
Search
</IonButton>
</form>
</IonCardContent>
</IonCard>
<br></br>
{console.log(allChallenges)}
<IonCard>
{allChallenges.map(challenge => (
// <IonItem href="#" className="ion-activated">
// <IonLabel>{challenge}</IonLabel>
// </IonItem>
<div>
<>{console.log(challenge)}</>
<>{console.log(challenge.name)}</>
{/* <>{challenge.key}</> */}
</div>
))}
</IonCard>
</IonContent>
</IonPage>
);
};
This is how the object is structured (when you console.log(challenges) in the map function), and it clearly has the "name" key, so why is it coming up as unknown??
CodePudding user response:
before the allchallenges state set in the useEffect it's empty and it doesn't have any name in it you can do two things first:
const [allChallenges, setAllChallenges] = useState<Array<Object>>([{name:"", key:0}]);
and the second one you can set a boolean state after fetch like isOK and then turn it true after you got the result and use it like this:
const [isOK , SetIsOK] = useState(false);
{isOK && allChallenges.map(challenge => (
// <IonItem href="#" className="ion-activated">
// <IonLabel>{challenge}</IonLabel>
// </IonItem>
<div>
<>{console.log(challenge)}</>
<>{console.log(challenge.name)}</>
{/* <>{challenge.key}</> */}
</div>
))}
CodePudding user response:
TO fix this, all I had to do was change my useState
type for the allChallenges. I changed it from <Array<Object>>
to <Array<any>>
and it worked perfectly!