微前端 micro-app 在vue 中的路由跳转问题

微前端 micro-app 在vue 中的路由跳转问题

 1. 子项目中的配置

 

vue.config.js 配置

const isProd = process.env.NODE_ENV === "production";
const isDev = process.env.NODE_ENV === "development";
const isWorking = process.env.NODE_ENV === "working";

const vueConfig = {
  outputDir: isWorking ? "dist/rslice/" : 'dist/',
  publicPath: isWorking ? '/rslice/' : "/", //这个必须,引入静态资源需要从根路径引入,否则会找不到静态资源
};

module.exports = vueConfig;

 

 

.env.working 中

# 环境配置
NODE_ENV = 'working'
# 页面标题
VUE_APP_TITLE = 'TITLE'

 

 

package.json 中

  "scripts": {
    "serve": "vue-cli-service serve",
    "build": "vue-cli-service build",
    "build:work": "vue-cli-service build --mode working",
    "lint": "vue-cli-service lint"
  },

 

 

 src / utils /  internal-router.js 

注:这里写的比较全,可以解决这个问题:由于 windows 与 linux 环境不同,加载路由情况有差异,各别跳转方式会失败,导致空白页。

export function internalReplace(router, path) {
  if (!router) {
    console.error('[internalReplace] router 实例不存在')
    return
  }

  console.log('router.base:', router.options.base)

  const base = router.options.base || '/'
  let purePath = path

  // 如果 path 已经带了 base,去掉前缀,保证 match 不会失败
  if (purePath.startsWith(base)) {
    purePath = purePath.slice(base.length - 1) // 保留前导 /
  }

  // 匹配目标 route
  let target = null
  try {
    target = router.match(purePath, router.history.current)
  } catch (e) {
    console.error('[internalReplace] router.match 出错:', e)
  }

  if (!target || !target.matched || target.matched.length === 0) {
    console.error('[internalReplace] 找不到路由:', purePath, 'base:', base)
    return
  }

  // 替换当前 route,不触发 pushState
  router.history.current = target

  // 强制刷新视图
  if (typeof router.history.updateRoute === 'function') {
    router.history.updateRoute(target)
     console.log("vue-router3 的回调")
  } else if (router.history.cb) {
    router.history.cb(target)
    console.log("vue-router3 的回调")
  } else if (router.app && router.app._route) {
    router.app._route = target
    console.log("最终兜底:手动替换 _route")
  
  }

  console.log('[internalReplace] 成功替换路由为:', target.fullPath)
}

 

 

 main.js 中,路由跳转使用 internalReplace 

import { internalReplace } from '@/utils/internal-router'
new Vue({
  router,
  render: (h) => h(App),
}).$mount("#app");

// 与基座进行数据交互
function handleMicroData() {
  // debugger;
  // 是否是微前端环境
  if (window.__MICRO_APP_ENVIRONMENT__) {
    // 主动获取基座下发的数据

    var microAppData = window.microApp.getData();
    console.log("app-rslice getData:", microAppData);

    if (microAppData && microAppData.axiosTokenValue) {
      // store.commit("SETTOKENKEY", microAppData.axiosTokenValue);
      // audit_token = microAppData.axiosTokenValue;
      window.RSLICE_TOKEN = microAppData.axiosTokenValue;
    }

    if (microAppData && microAppData.currentUser) {
      // store.commit("SETCURRENTUSER", microAppData.currentUser);
      window.RSLICE_CURRENTUSER = microAppData.currentUser;
    }
    debugger;
    // router.push(microAppData.route);
    internalReplace(router, microAppData.route);

    // 监听基座下发的数据变化
    window.microApp.addDataListener((data) => {
      console.log("app-rslice addDataListener:", data);

      // 当基座下发path时进行跳转
      if (data.path && data.path !== router.currentRoute.path) {
        // router.push(data.path);
        internalReplace(router, data.path);
      }
    });

    // 向基座发送数据
    setTimeout(() => {
      window.microApp.dispatch({ myname: "app-rslice" });
    }, 3000);
  }
}

 

 

 

 

 

 

 

 

 

 

 

 

 

 

end .

posted @ 2025-09-24 11:23  无心々菜  阅读(44)  评论(0)    收藏  举报