Reactjs 如何在React自定义钩子中只提取一次数据?
我有一个定制的钩子,它获取许多组件使用的本地JSON文件 hooks.jsReactjs 如何在React自定义钩子中只提取一次数据?,reactjs,react-hooks,fetch-api,use-effect,Reactjs,React Hooks,Fetch Api,Use Effect,我有一个定制的钩子,它获取许多组件使用的本地JSON文件 hooks.js export function useContent(lang) { const [content, setContent] = useState(null); useEffect(() => { const abortController = new AbortController(); const signal = abortController.signal;
export function useContent(lang) {
const [content, setContent] = useState(null);
useEffect(() => {
const abortController = new AbortController();
const signal = abortController.signal;
fetch(`/locale/${lang}.json`, { signal: signal })
.then((res) => {
return res.json();
})
.then((json) => {
setContent(json);
})
.catch((error) => {
console.log(error);
});
return () => {
abortController.abort();
};
}, [lang]);
return { content };
}
import { useContent } from '../../hooks.js';
function MyComponent(props) {
const { content } = useContent('en');
}
import { useContent } from '../../hooks.js';
function MyOtherComponent(props) {
const { content } = useContent('en');
}
/components/MyComponent/MyComponent.js
export function useContent(lang) {
const [content, setContent] = useState(null);
useEffect(() => {
const abortController = new AbortController();
const signal = abortController.signal;
fetch(`/locale/${lang}.json`, { signal: signal })
.then((res) => {
return res.json();
})
.then((json) => {
setContent(json);
})
.catch((error) => {
console.log(error);
});
return () => {
abortController.abort();
};
}, [lang]);
return { content };
}
import { useContent } from '../../hooks.js';
function MyComponent(props) {
const { content } = useContent('en');
}
import { useContent } from '../../hooks.js';
function MyOtherComponent(props) {
const { content } = useContent('en');
}
/components/MyOtherComponent/MyOtherComponent.js
export function useContent(lang) {
const [content, setContent] = useState(null);
useEffect(() => {
const abortController = new AbortController();
const signal = abortController.signal;
fetch(`/locale/${lang}.json`, { signal: signal })
.then((res) => {
return res.json();
})
.then((json) => {
setContent(json);
})
.catch((error) => {
console.log(error);
});
return () => {
abortController.abort();
};
}, [lang]);
return { content };
}
import { useContent } from '../../hooks.js';
function MyComponent(props) {
const { content } = useContent('en');
}
import { useContent } from '../../hooks.js';
function MyOtherComponent(props) {
const { content } = useContent('en');
}
我的组件的行为相同,因为我将相同的
en
字符串发送到我的useContent()
hook。useffect()
应仅在lang
参数更改时运行,因此鉴于两个组件使用相同的en
字符串,因此useffect()
应仅运行一次,但它不会运行—它会运行多次。为什么呢?如何更新钩子,使其仅在lang
参数更改时获取?钩子在不同组件(以及相同组件类型的不同实例)中独立运行。因此,每次在新组件中调用useContent
,效果(获取数据)都会运行一次。(如React所承诺的,重复呈现相同组件将不会重新获取数据。)相关:
跨多个组件共享状态的一般方法是使用钩子(useContext
)。更多关于上下文。您可能需要以下内容:
const ContentContext = React.createContext(null)
function App(props) {
const { content } = useContent(props.lang /* 'en' */);
return (
<ContentContext.Provider value={content}>
<MyComponent>
<MyOtherComponent>
);
}
function MyComponent(props) {
const content = useContext(ContentContext);
}
function MyOtherComponent(props) {
const content = useContext(ContentContext);
}
const ContentContext=React.createContext(null)
功能应用程序(道具){
const{content}=useContent(props.lang/*'en'*/);
返回(
);
}
功能MyComponent(道具){
const content=useContext(ContentContext);
}
功能部件(道具){
const content=useContext(ContentContext);
}
这样,如果您想更新内容/语言/任何内容,您可以在应用程序级别(或您决定的任何更高级别)进行更新。鉴于这似乎是一种共享状态,为什么不使用上下文?