we are trying to convert existing JS code into TS but stuck in updating local state data. here apiData is expected to come from API due to which we dont know possibilities of fields.
DataContext.tsx
import { createContext,useContext, useState } from "react";
interface Data {
id: number;
title: string;
apiData:object;
}
type DataContextType = {
myData: Data;
updateMyData: (myData: Data) => void;
};
const DataContext = createContext<DataContextType | null>(null);
export const useDataContext =()=>{ return useContext(DataContext) as DataContextType};
export const DataContextProvider =({children}: any)=>{
const [myData, setMyData]=useState<Data>({id:1,title:'this',apiData:{}})
const updateMyData=(myData:Data)=>{
setMyData(myData);
}
return (
<DataContext.Provider value={{myData,updateMyData}}>
{children}
</DataContext.Provider>
)
}
page.tsx
"use client"
import { useEffect , useState} from 'react';
import {useDataContext} from '../context/DataContext'
export default function Sample() {
const { myData,updateMyData } = useDataContext();
const [name,setName]=useState([]);
useEffect(()=>{
if(name.length===0)
{
updateMyData({id:2,title:'that',apiData:{employee:[{data:'tom'},{data:'harry'}]}});
setName(myData["apiData"]["employee"]);
}
},[name]);
return (
<>
<h1>hellow1</h1>
{name.map((element)=>{ return <h2>{element.data}</h2>})}
</>
)
}
TS Error
even tough updateMyData setting up employee data we are not able to setName
You need to make a couple of changes to make TS play along nicely.
apiData: object
is not a well defined type. And hence you cannot use apiData["employee"]["data"], without TS screaming at you.
Replace that with:
apiData: { employee: { data: string }[] };
Even with that, you will get another error:
const [name, setName] = useState([]);
The way setName
is defined it can only accept an empty tuple. This happens because React-Typescript narrows the type (of state variable) to the most specific one by its own. You should define the type of the state variable while calling useState
.
Use the below to define the type:
const [name, setName] = useState<{ data: string }[]>([]);
useState
is defined as a generic in typescript to facilitate using values of all types.
Here is a demo. It is not functional but demos all the type errors and fixes.