有没有办法在 url 更改时更新在单个 spa 中注册的应用程序的历史位置?

Posted

技术标签:

【中文标题】有没有办法在 url 更改时更新在单个 spa 中注册的应用程序的历史位置?【英文标题】:Is there a way to update history location of app registered in single spa when url changes? 【发布时间】:2021-09-11 22:52:07 【问题描述】:

我在 single-spa 中有两个应用程序,一个在 React 中,另一个在 Vue 中。 React 应用程序使用历史库进行导航。以下是我的 React 应用文件:

history.js

import  createBrowserHistory  from 'history'

export const history = createBrowserHistory(
    basename: '/myapp,
    forceRefresh: true 
)

App.js

import React, Component from 'react';
import  Router, Switch, Route  from 'react-router-dom';
import history from ‘../history.js’; 

class App extends Component 
   constructor(props)
     super(props);
   

   render()
       return (
           <Router history=history>  
             <Switch>
               <Route exact path="/user" component=User />
               <Route exact path="/" component=Home />
             </Switch>
           <Router />
      )
  

我在以下情况下遇到问题:

    我在 React 应用的路径 https://localhost:3000/myapp/user 并切换到 Vue 应用(使用导航栏菜单)。 现在,当我切换回 React 应用程序时,URL 显示 https://localhost:3000/myapp 理想情况下应该加载我的 Home 组件。 但现在历史记录仍然有旧位置 (https://localhost:3000/myapp/user),然后加载旧的用户组件。

有没有办法在 url 更改时更新历史记录?

【问题讨论】:

【参考方案1】:

我认为这归结为让路由机制协同工作。这是一个有趣的问题,我有两个可行的想法:

思路一:刷新页面

如果完全重新加载没问题,在 Vue 和 React 之间切换时刷新浏览器可能会重置两个路由器中的状态,以便它们都读取加载时的初始状态并继续。

我会通过在任何会导致转换到 React 的事件处理程序中分配 window.location.href = '/myapp' 来做到这一点。它应该重新加载浏览器并导航到该页面。如果您的 React 应用程序正在该路径加载,这应该工作。

想法2:使用createMemoryHistory并与Vue的路由器同步

您可以将“内存路由器”传递给react-router,而不是提供“浏览器路由器”。顾名思义,内存路由器将状态保存在内存中(而不是使用History API)。

我认为您可以将 Vue 路由器的事件连接到 react-router 的内存路由器,并像这样使它们同步。我认为您可以在 Vue 的 global after hooks 中调用 history.push

类似这样的:

// ? I have not tested this, take this as inspiration
const router = new VueRouter(/* ... */);
const history = createMemoryHistory(/* ... */);

router.afterEach((fullPath) => 
  history.replace(fullPath, fromVueRouter: true);
);

history.listen(location => 
  if (location.state?.fromVueRouter) return;

  router.replace(location.pathname);
);

【讨论】:

谢谢。现在我已经以与您提到的想法 1 类似的方式解决了它。 if (window.location.pathname === '/myapp') history.replace('/') else history.replace(window .location.href.substring(window.location.href.lastIndexOf('/') + 1)) // 在后按时获取正确的 url。但我一直在寻找一种更干净的方式来做到这一点,而无需进行不必要的刷新。关于想法 2,我不应该更改 Vue 应用程序配置中的任何内容。【参考方案2】:

我没有找到如何更改历史记录,但我希望您修正一些语法错误。 Meybe 修复错误可以帮助您。

history.js

export const history = createBrowserHistory(
    basename: '/myapp, // basename: '/myapp',
    forceRefresh: true 
)

App.js

<Switch>
    <Route exact path="/user" component=User /> // <Route path="/user" component=User />
    <Route exact path="/" component=Home />
</Switch>

【讨论】:

谢谢。但这是一个错字。在 App.js 中,我希望这些组件仅针对给定的确切路径加载。

以上是关于有没有办法在 url 更改时更新在单个 spa 中注册的应用程序的历史位置?的主要内容,如果未能解决你的问题,请参考以下文章

检查 Angular SPA 视图更改的缓存清单更新

通知用户在 SPA 网站上刷新浏览器的正确方法是啥(更改 .js 文件时)

有没有办法 pushState() facebook 画布中的父窗口?

从更新中排除 pod

有没有办法在没有多个类的情况下更改单个工具提示工具提示的侧面/位置?

更改图像时清除 CATiledLayers 缓存