大家好!今天,我要告诉您什么是AbortController
,为什么您可能需要它以及如何改善应用程序的性能。
介绍
在一次小型聊天中,我进行了一项调查,事实证明,只有9%的网络开发人员在一个真实的项目中使用了它,而64%的网络开发人员根本不知道它是什么。
所以让我们开始!
AbortController
接口代表一个控制器对象,允许您在需要时按照或多个Web请求进行中止。
这是一个非常简单的接口,由signal
属性和abort
方法组成
const controller = new AbortController();
const signal = controller.signal;
const abort = controller.abort;
我们将signal
传递到呼叫方法:fetch(url, { signal })
使用abort()
,可以停止此通话
例子
拿来
这个简单的代码我们的应用程序:
export default function App() {
const [url, setUrl] = useState("users");
const [data, setData] = useState([]);
const [loading, setLoading] = useState(false);
useEffect(() => {
setLoading(true);
fetch(`https://jsonplaceholder.typicode.com/${url}`)
.then((res) => res.json())
.then((res) => {
setData(res);
setLoading(false);
});
}, [url]);
return (
<div className="App">
<div className="nav">
<Link to="/users" onClick={() => setUrl("users")}>
users
</Link>
<Link to="/todos" onClick={() => setUrl("todos")}>
todos
</Link>
<Link to="/posts" onClick={() => setUrl("posts")}>
posts
</Link>
</div>
<div className="page">
<Switch>
<Route path="/users" component={() => <div>Users page</div>} />
<Route path="/todos" component={() => <div>Todos page</div>} />
<Route path="/posts" component={() => <div>Posts page</div>} />
</Switch>
{loading ? (
"loading..."
) : (
<ul>
{data?.splice(0, 5).map((item) => (
<li key={item.id}>{item?.name || item?.title}</li>
))}
</ul>
)}
</div>
</div>
);
}
这样可以工作:
您可以看到所有3个请求到达目标,并依次显示在屏幕上
我们可以想象一种情况,用户在菜单中导航的速度比请求更快地在服务器上处理,这意味着我们确实需要不必要的请求
例如:用户进入“/用户”页面,请求已经开始,下一步用户来到“/post”页面,此刻我们假设他不再需要“/用户”页面,并且可以取消此请求,并且不加载服务器
这就是abortcontroller的代码的样子,我只更改了使用效果:
useEffect(() => {
const controller = new AbortController();
const signal = controller.signal;
setLoading(true);
fetch(`https://jsonplaceholder.typicode.com/${url}`, { signal })
.then((res) => res.json())
.then((res) => {
setData(res);
setLoading(false);
});
return () => {
controller.abort();
};
}, [url]);
这就是发生的事情:
不必要的请求已被取消!
这是性能的主要点!
轴
与获取相同
const controller = new AbortController();
axios.get('/user', { signal: controller.signal })
GQL
gql几乎具有相同的方式,但是您需要使用useRef
在下面的示例中,我们离开页面时取消请求:
const controllerRef = useRef(new AbortController());
const [getUser, { data }] = useLazyQuery(USER_QUERY, {
context: {
fetchOptions: {
signal: controllerRef.current.signal,
},
},
});
useEffect(() => {
return () => controllerRef.current.abort();
}, []);
结论
AportController是提高性能的一种简单有效的方法,您可以在项目中尝试,祝您好运!