Closed promise96319 closed 1 year ago
请使用 markEffectHookIsOnetime()
标记,readme 有说明
好的谢谢~,没注意到这个api。
再请教一个问题,markEffectHookIsOnetime 只是限定了 mount 执行一次,那如果我想保存组件或者页面的滚动距离 scrollTop,下次使用缓存的时候恢复之前的滚动距离,对 dom 元素设置 scrollTop,似乎没有类似于 activated 的钩子去做这个设置操作。
没有特定的 api 对应 activated dom 本身会保留滚动的状态,正常情况下,重新 attach 到 dom 树上后,会还原之前的滚动位置
activated 后会重新执行正常的 react 生命周期
这也是为什么有这些 api
markEffectHookIsOnetime
markClassComponentHasSideEffectRender
如果 hook 的 dependency 变化了,即便加了 markEffectHookIsOnetime
,hook 还是会重新执行。
activated 后会重新执行正常的 react 生命周期
这也是为什么有这些 api
markEffectHookIsOnetime
markClassComponentHasSideEffectRender
第三方组件内部的副作用似乎除了手动缓存,没有很好的解决方案。比如 ProComponents 的很多组件都支持绑定一个返回Promise的方法到request,业务代码无法直接对其进行干涉, 要么手动缓存请求数据,重新mount的时候 return 上次获取的数据
<ProTable<GithubIssueItem>
// ...
request={async (params, sort, filter) => {
console.log(sort, filter);
await waitTime(2000);
return request<{
data: GithubIssueItem[];
}>('https://proapi.azurewebsites.net/github/issues', {
params,
});
}}
/>
问题:目前的 KeepAlive 组件即使能拿到缓存的 fiber 渲染,也会触发子组件的 mount 生命周期。这就导致一些在 mount 生命周期里执行的事件会触发,比如请求服务端数据,设置一些其他的数据状态等。
建议:需要增加类似 Vue 的 activated/deactivated 生命周期,在有缓存的时候应该不触发 mount 而是触发 activated。