I'm fairly new to react, right now I have a function that is fetching some data in my useEffect
hook, using a loading state to manage component rendering and then loading my state component with that data, everything is working fine.
But now I have to implement another function to fetch some other data.
How can this be implemented in the best way possible? Do I need to create another useEffect
for another fetch function?
Here is my code:
export default function Home() {
const [ageOptions, setAgeOptions] = useState([])
const [age, setAge] = useState('')
const [loading, setLoading] = useState(false)
// get age option from API
useEffect(() => {
setLoading(true)
const fetchAgeOptions = () => {
// transform the data to load properly in my react-select component
function transform(data) {
const options = data.map(function (row) {
return { value: row.id, label: row.description, startAge: row.startAge, endAge: row.endAge }
})
setAgeOptions(options)
setLoading(false)
}
api.get('someurl.com').then(response =>
Object.values(response.data.rows)).then(data => transform(data))
}
fetchAgeOptions()
}, [])
return loading ? <div>Loading...</div> :
<>
<label>Age level</label>
<Select
value={age}
options={ageOptions}
placeholder="All"
onChange={val => {
setAge(val)
}}
/>
</>
}
Your current useEffect will only run on mount (because you added the empty brackets at the end of the use effect []). If you are planning on only calling this function one time (on mount) then you can put it in the same useEffect. If you want to call a function every time the state of something updates then all you have to do is make a separate useEffect with the state as a dependency.
useEffect(() => {
}, ['variable-here-on-update-will-call-whatever-is-in-the-useEffect'])
Here is an example on mine:
//will run on componentDidMount
useEffect(() => {
setError(false);
}, []);
//will run if error is updated in parent component
useEffect(() => {
if (error && error.body) {
setError(true);
}
}, [error]);
I would also recommend taking out your 'fetchAgeOptions' function from the useEffect (and add it above) as you are calling to it anyways. This way it is not a private function to the useEffect and it will look cleaner.
您可能想要创建一个名为 useFetch 的自定义钩子,其中包含 useEffect 和 useState,它应该返回状态(初始、加载、错误和成功)和结果,然后仅当第一个效果具有正确的状态时才调用第二个效果。
Just like you can use the State Hook more than once, you can also use several effects. This lets us separate unrelated logic into different effects:
function FriendStatusWithCounter(props) {
const [count, setCount] = useState(0);
useEffect(() => {
document.title = `You clicked ${count} times`;
});
const [isOnline, setIsOnline] = useState(null);
useEffect(() => {
function handleStatusChange(status) {
setIsOnline(status.isOnline);
}
ChatAPI.subscribeToFriendStatus(props.friend.id, handleStatusChange);
return () => {
ChatAPI.unsubscribeFromFriendStatus(props.friend.id, handleStatusChange);
};
});
// ...
}
Hooks let us split the code based on what it is doing rather than a lifecycle method name. React will apply every effect used by the component, in the order they were specified.
React Docs - Effect Hook https://reactjs.org/docs/hooks-effect.html
Use a promise all
useEffect(() => {
setLoading(true)
const fetchAgeOptions = () => {
// transform the data to load properly in my react-select component
function transform(data) {
const options = data.map(function (row) {
return { value: row.id, label: row.description, startAge: row.startAge, endAge: row.endAge }
})
setAgeOptions(options)
setLoading(false)
}
api.get('someurl.com').then(response =>
Object.values(response.data.rows)).then(data => transform(data))
}
const fetchAgeOptions = () => {
// transform the data to load properly in my react-select component
function transform(data) {
const options = data.map(function (row) {
return { value: row.id, label: row.description, startAge: row.startAge, endAge: row.endAge }
})
setAgeOptions(options)
setLoading(false)
}
api.get('someurl.com').then(response =>
Object.values(response.data.rows)).then(data => transform(data))
}
const fetchAgeOptions = () => {
// transform the data to load properly in my react-select component
function transform(data) {
const options = data.map(function (row) {
return { value: row.id, label: row.description, startAge: row.startAge, endAge: row.endAge }
})
setAgeOptions(options)
setLoading(false)
}
api.get('someurl.com').then(response =>
Object.values(response.data.rows)).then(data => transform(data))
}
Promise.all([fetchMethod1,fetchMethod2,fetchMethod3]).then(data=>{
// DATA IS AN ARRAY AND THEY ARE IN ORDER AS PLACED IN
})
}, [])
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.