简体   繁体   English

React Hooks异步最佳实践

[英]React Hooks Async Best Practice

Now with use useEffect s, there is a substitute for componentDidMount into a React Component with Hooks. 现在使用useEffect s,可以将componentDidMount替换为带有Hook的React组件。

Scenario "initial unique call to a server": 场景“对服务器的初始唯一调用”:

To accomplish this, DependencyList (second argument of useEffect ) in useEffect should every time an empty array otherwise the application will send every state change a fetch call to the server. 要做到这一点,DependencyList(的第二个参数useEffect )在useEffect应该每次都空数组,否则申请将发送的每个状态更改取调用服务器。

it means, this is the best practice to getData 这意味着,这是getData的最佳实践

useEffect(() => {
  console.log("useEffect, fetchData here");
}, []);

Is it best practice, to use [] as DependencyList param to disable server requesting every state changing? 最好的做法是,使用[]作为DependencyList参数来禁用服务器请求每个状态发生变化吗?

Link to github https://github.com/facebook/react/issues/14326 链接到github https://github.com/facebook/react/issues/14326

Yes. 是。 This is the best approach. 这是最好的方法。

From the react docs : 来自反应文档

Passing in an empty array [] of inputs tells React that your effect doesn't depend on any values from the component, so that effect would run only on mount and clean up on unmount; 传入一个空数组[]输入告诉React你的效果不依赖于组件中的任何值,因此该效果只能在mount上运行并在unmount上清理; it won't run on updates. 它不会在更新时运行。

useEffect is a very powerful, and my favorite, hook. useEffect是一个非常强大的,我最喜欢的钩子。 You can monitor one or more variables for state changes by passing them into the second parameter array, or you can just listen for mounting and unmounting with the approach that you're using. 您可以通过将状态更改传递到第二个参数数组来监视一个或多个变量以进行状态更改,或者您可以使用您正在使用的方法监听安装和卸载。

It depends on whether you want the server to be called whenever some parameter changes. 这取决于您是否希望在某些参数更改时调用服务器。 If you want the same async call regardless, you can use [] as the second parameter. 如果您想要相同的异步调用,可以使用[]作为第二个参数。

However, if you are for example displaying a profile page of a user where each page has a userID state/prop, you should pass in that ID as a value into the second parameter of useEffect so that the data will be refetched for a new user ID. 但是,如果您要显示用户的配置文件页面,其中每个页面都具有userID状态/ prop,则应将该ID作为值传递到useEffect的第二个参数中,以便为新用户重新获取数据ID。 componentDidMount is insufficient here as the component might not need remounting if you go directly from user A to user B's profile. componentDidMount在这里是不够的,因为如果你直接从用户A转到用户B的配置文件,组件可能不需要重新安装。

In the traditional classes way, you would do: 在传统的课程方式中,你会这样做:

componentDidMount() {
  this.fetchData();
}

componentDidUpdate(prevProps, prevState) {
  if (prevState.id !== this.state.id) {
    this.fetchData();
  }
}

With hooks, that would be: 使用钩子,那将是:

useEffect(() => {
  this.fetchData();
}, [id]);

Try running the code below and see the result. 尝试运行下面的代码并查看结果。 Change the id to 2 for instance to see that useEffect is run again. 例如,将id更改为2,以便再次运行useEffect

 function Todo() { const [todo, setTodo] = React.useState(null); const [id, setId] = React.useState(1); React.useEffect(() => { if (id == null || id === '') { return; } fetch(`https://jsonplaceholder.typicode.com/todos/${id}`) .then(results => results.json()) .then(data => { setTodo(data); }); }, [id]); // useEffect will trigger whenever id is different. return ( <div> <input value={id} onChange={e => setId(e.target.value)}/> <br/> <pre>{JSON.stringify(todo, null, 2)}</pre> </div> ); } ReactDOM.render(<Todo />, document.querySelector('#app')); 
 <script src="https://unpkg.com/react@16.8.1/umd/react.development.js"></script> <script src="https://unpkg.com/react-dom@16.8.1/umd/react-dom.development.js"></script> <div id="app"></div> 

You should read up on useEffect so that you know what you can/cannot do with it. 你应该阅读useEffect以便你知道你可以/不能用它做什么。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM