ZBLOG

import api from '@/store/api'; export default { name: 'App', data() { return { isReload: false, }; }, computed: { assetTag() { return th...

在你的 Vue.js 组件中,你已经实现了对页面刷新的检测和关闭窗口时的处理,但可能会遇到一些问题,例如在刷新页面时也执行了注销操作。这是因为你在 beforeunload 事件中进行了一些逻辑判断,而这些逻辑可能未能正确区分刷新与关闭窗口的行为。

让我们来优化一下这部分代码,以便能够更清晰地识别用户是否是在刷新页面,而不是直接关闭浏览器:

优化建议

  1. 利用 Performance API 检测页面类型:使用 performance.getEntriesByType('navigation') 来检测导航类型,进而决定如何处理 beforeunload 事件。
  2. 增强状态管理:确保每次加载后都设置好状态,并且当状态表明是刷新时,避免不必要的注销操作。

改进后的代码

以下是改进过的代码示例:

  1. <template>
  2. <div id="app">
  3. <router-view />
  4. </div>
  5. </template>
  6. <script>
  7. import api from '@/store/api';
  8. export default {
  9. name: 'App',
  10. data() {
  11. return {
  12. isReload: false,
  13. };
  14. },
  15. computed: {
  16. assetTag() {
  17. return this.$store.getters['global/assetTag'];
  18. },
  19. },
  20. watch: {
  21. assetTag(tag) {
  22. if (tag) {
  23. document.title = `${tag} - ${this.$route.meta.title}`;
  24. }
  25. },
  26. $route(to) {
  27. document.title = to.meta.title || 'Page is missing title';
  28. if (this.assetTag) {
  29. document.title = `${this.assetTag} - ${to.meta.title}`;
  30. }
  31. },
  32. },
  33. created() {
  34. document.title = this.$route.meta.title || 'Page is missing title';
  35. let icoFlag = localStorage.getItem('CustomWebLogo');
  36. var link =
  37. document.querySelector("link[rel*='icon']") ||
  38. document.createElement('link');
  39. link.type = 'image/x-icon';
  40. link.rel = 'shortcut icon';
  41. link.href = `${icoFlag}.ico`;
  42. document.head.appendChild(link);
  43. this.$store.dispatch('authentication/twoFactorLogin').then(() => {
  44. this.$router.push('/');
  45. });
  46. // 检测页面是否为重新加载
  47. this.detectPageReload();
  48. },
  49. mounted() {
  50. window.addEventListener('beforeunload', this.handleBeforeUnload);
  51. },
  52. beforeDestroy() {
  53. window.removeEventListener('beforeunload', this.handleBeforeUnload);
  54. },
  55. methods: {
  56. detectPageReload() {
  57. const navEntries = performance.getEntriesByType('navigation');
  58. const isReload =
  59. navEntries.length > 0 && navEntries[0].type === 'reload';
  60. // 如果是刷新,则设置标记
  61. if (isReload) {
  62. sessionStorage.setItem('isPageReload', 'true');
  63. // 短暂延迟后清除标记,防止关闭误判
  64. setTimeout(() => sessionStorage.removeItem('isPageReload'), 50);
  65. }
  66. },
  67. handleBeforeUnload(event) {
  68. const isReload = sessionStorage.getItem('isPageReload');
  69. // 强制触发浏览器默认弹窗
  70. event.preventDefault();
  71. event.returnValue = '';
  72. if (!isReload) {
  73. // 执行关闭窗口时的退出操作
  74. this.logoutUser();
  75. } else {
  76. // 清除标记,表示该次 unload 是由于刷新引起的,不做任何操作
  77. sessionStorage.removeItem('isPageReload');
  78. }
  79. },
  80. logoutUser() {
  81. api.post('/logout', { data: [] });
  82. sessionStorage.removeItem('TOKEN');
  83. localStorage.removeItem('storedUsername');
  84. },
  85. },
  86. };
  87. </script>
  88. <style lang="scss">
  89. @import '@/assets/styles/_obmc-custom';
  90. </style>

修改要点:

  1. 状态管理:确保在 detectPageReload() 中准确设置和清除刷新标记。
  2. 事件处理:在 handleBeforeUnload() 中,如果检测到是重载(即页面刷新的情况),则只需清除标记并返回,不执行注销操作。
  3. 不必要的监听器:移除了对 load 的监听,因为你的需求主要集中在监听页面卸载。

这样一来,当用户尝试离开页面时,通过设定好的机制,你可以更准确地判断他们是在进行何种操作,从而作出相应的响应。


内容由零声教学AI助手提供,问题来源于学员提问

本站部分文章来源于网络,版权归原作者所有,如有侵权请联系站长删除。
转载请注明出处:https://golang.0voice.com/?id=22893

分享:
扫描分享到社交APP
上一篇
下一篇
发表列表
游客 游客
此处应有掌声~
评论列表

还没有评论,快来说点什么吧~

联系我们

在线咨询: 点击这里给我发消息

微信号:3007537140

上班时间: 10:30-22:30

关注我们
x

注册

已经有帐号?