我在多个组件中使用了这个 useFetch
自定义钩子。
import {useState,useEffect} from 'react'
import {getToken} from './../services/token'
const useFetch = (url) => {
const [data,setData] = useState(null);
const [error,setError] = useState(null);
const [loading,setPending] = useState(false);
useEffect(() => {
(async()=>{
const abortCont = new AbortController();
const token = await getToken();
try {
setPending(true);
const response = await fetch(url,{
signal : abortCont.signal,
headers : {
"Content-Type" : "application/json",
"Authorization" : "Bearer "+token
}
});
const result = await response.json();
setData(result);
setPending(false);
} catch (err) {
if(err.name === 'AbortError'){
abortCont.abort();
return;
}
setError(String(err));
setPending(false);
}
})()
}, [])
return {data,error,loading}
}
export default useFetch;
我将它导入到用户组件中,如下所示。
const {data,error,loading} = useFetch('http://localhost:4040/users');
通常我会像 UseEffect
这样传递 [users.length]
的第二个参数来使用户数据具有反应性,但由于这是一个自定义钩子并在许多组件中使用,
当用户数据更改或更新时,如何使用户数据具有反应性?
答案 0 :(得分:2)
您可以将依赖数组作为可选参数传递给您的自定义钩子。
const useFetch = async (url, deps) => {
const [data,setData] = useState(null);
const [error,setError] = useState(null);
const [loading,setPending] = useState(false);
useEffect(() => {
(async()=>{
const abortCont = new AbortController();
const token = await getToken();
try {
setPending(true);
const response = await fetch(url,{
signal : abortCont.signal,
headers : {
"Content-Type" : "application/json",
"Authorization" : "Bearer "+token
}
});
const result = await response.json();
setData(result);
setPending(false);
} catch (err) {
if(err.name === 'AbortError'){
abortCont.abort();
return;
}
setError(String(err));
setPending(false);
}
})()
}, deps || [])
return {data,error,loading}
}
export default useFetch;
然后这样称呼它
const {data,error,loading} = useFetch('http://localhost:4040/users', [users.length]);
编辑
在您的情况下,您希望对渲染有更多的控制。所以我会说你必须修改你的钩子以支持你安装的组件的设置数据。
const useFetch = async (url, holded, setHolded) => {
const [data,setData] = useState(null);
const [error,setError] = useState(null);
const [loading,setPending] = useState(false);
useEffect(() => {
(async()=>{
const abortCont = new AbortController();
const token = await getToken();
try {
setPending(true);
const response = await fetch(url,{
signal : abortCont.signal,
headers : {
"Content-Type" : "application/json",
"Authorization" : "Bearer "+token
}
});
const result = await response.json();
setData(result);
if(setHolded) {
setHolded(result);
}
setPending(false);
} catch (err) {
if(err.name === 'AbortError'){
abortCont.abort();
return;
}
setError(String(err));
setPending(false);
}
})()
}, (holded && setHolded && [holded,setHolded,url]) || [url])
return {data,error,loading}
}
export default useFetch;
然后这样称呼它
const {data,error,loading} = useFetch('http://localhost:4040/users', users, setUsers);