微前端架构-qiankun在vue3的应用

这篇具有很好参考价值的文章主要介绍了微前端架构-qiankun在vue3的应用。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

本文章介绍了qiankun在vue3的应用,其中子应用有vue2、vue3、react、angular

介绍

qiankun 是一个基于 single-spa 的微前端实现库,旨在帮助大家能更简单、无痛的构建一个生产可用微前端架构系统。
其他几款([single-spa]、[micro-app]、[百度emp]])

使用 iframe 整合系统时,假设我们有系统 A, 当我们想把系统 B 引入 A 系统时,只需要 B 系统提供一个 url 给 A 系统引用即可,这里我们把 A 系统叫做父应用,把 B 系统叫做子应用。同样的,微前端也延续了这个概念,微前端在使用起来基本和使用 iframe 一样平滑。

结构

主应用(父),微应用(子)

微前端架构-qiankun在vue3的应用

案例

一、主应用

  • 主应用不限技术栈,只需要提供一个容器 DOM,然后注册微应用并 start 即可。
创建主应用项目 -vue3

npm install @vue/cli -g
 
vue create qiankun-tast

  1. 在主应用中安装qiankun框架
$ yarn add qiankun # 或者 npm i qiankun -S
  1. 在 主应用 中注册微应用

main.js:

import { createApp } from 'vue'
import App from './App.vue'
import router from './router/index'
import ElementPlus from 'element-plus'
import 'element-plus/dist/index.css'
import 'zone.js';

import { registerMicroApps } from 'qiankun';

registerMicroApps([
  // {
  //     name: "vue2App",
  //     props: { age: 10 }, //给子应用传数据
  //     entry: "//localhost:3001", //默认会加载这个html,解析里面的js,动态执行(子应用必须支持跨域)里面,是用fetch去请求的数据
  //     container: "#out-main", //挂载到主应用的哪个元素下
  //     activeRule: "/vue2", //当我劫持到路由地址为/vue2时,我就把http://localhost:3000这个应用挂载到#app-main的元素下
  // },
  {
    name: "vueChildOne",
    entry: "//localhost:3001",
    container: "#child-vue3-one-content",
    activeRule: "/child-one",
  },
  {
    name: "vueChildTwo",
    entry: "//localhost:3002",
    container: "#child-vue3-two-content",
    activeRule: "/child-two",
  },
  {
    name: "vue2Child",
    entry: "//localhost:3003",
    container: "#child-vue2-one-content",
    activeRule: "/child-vue2-one",
  },
  {
    name: "reactApp1",
    entry: "//localhost:4001",
    container: "#child-react-one-content",
    activeRule: "/child-react-one",
  },
  {
    name: "angularApp1",
    entry: "//localhost:4200",
    container: "#child-angular-one-content",
    activeRule: "/child-angular-one",
  },
]);

// setDefaultMountApp('/child-one')

// 启动 qiankun
// start();

createApp(App).use(ElementPlus).use(router).mount('#app-base')

App.vue

<template>
  <div class="common-layout">
    <el-container>
      <el-aside width="200px">
        <el-menu>
          <el-menu-item index="1">
            <el-icon><icon-menu /></el-icon>
            <span @click="goHome">首页</span>
          </el-menu-item>
          <el-menu-item index="2">
            <el-icon><icon-menu /></el-icon>
            <span @click="$router.push('/child-one')">child-vue3-one</span>
          </el-menu-item>
          <el-menu-item index="3">
            <el-icon><document /></el-icon>
            <span @click="$router.push('/child-two')">child-vue3-one</span>
          </el-menu-item>
          <el-menu-item index="4">
            <el-icon><document /></el-icon>
            <span @click="$router.push('/child-vue2-one')">child-vue2-one</span>
          </el-menu-item>
          <el-menu-item index="5">
            <el-icon><document /></el-icon>
            <span @click="$router.push('/child-react-one')">child-react-one</span>
          </el-menu-item>
          <el-menu-item index="6">
            <el-icon><document /></el-icon>
            <span @click="$router.push('/child-angular-one')">child-angular-one</span>
          </el-menu-item>
        </el-menu>
      </el-aside>
      <el-main> <router-view></router-view></el-main>
    </el-container>
  </div>
</template>

<script>
export default {
  name: "App",
  components: {},
  methods: {
    // 跳转页面方法

    goHome() {
      this.$router.push("/");
    },
  },
};
</script>

<style>
.bens {
  width: 100%;
  display: flex;
  justify-content: center;
  position: absolute;
  top: 15px;
  left: 0;
  z-index: 9999999;
}
#app-base {
  font-family: Avenir, Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-align: center;
  color: #2c3e50;
  margin-top: 60px;
}
</style>

index.html:

// 将id:app 改为 app-base  自定义就行,只要与main.js对应起来,切不与微应用重复
<div id="app-base"></div>

router.js

import { createRouter, createWebHistory } from "vue-router";

// 2. 配置路由
const routes = [
  {
    path: "/",
    name: "home",
    component: () => import("@/views/home/index.vue"),
  },
  {
    path: "/child-one",
    component: () => import("@/views/childOne/index.vue"),
  },
  {
    path: "/child-two",
    component: () => import("@/views/childTwo/index.vue"),
  },
  {
    path: "/child-vue2-one",
    component: () => import("@/views/childVue2One/index.vue"),
  },
  {
    path: "/child-react-one",
    component: () => import("@/views/childReactOne/index.vue"),
  },
  {
    path: "/child-angular-one",
    component: () => import("@/views/childAgOne/index.vue"),
  },
];
// 1.返回一个 router 实列,为函数,里面有配置项(对象) history
const router = createRouter({
    mode: 'history',
    history: createWebHistory(),
    routes,
});

// 3导出路由   然后去 main.ts 注册 router.ts
export default router

vue3子应用

  1. 创建项目
// 选择vue3这个版本
vue create child-one
  1. 在 src 目录新增 public-path.js

  2. 解决静态文件跨域

// src/public-path.js
if(window.__POWERED_BY_QIANKUN__) {
  __webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__;
}
  1. 修改路由文件,建议使用history 模式的路由,并设置路由 base,值和它的 activeRule 是一样的。
import { createRouter, createWebHashHistory, createWebHistory } from "vue-router";

// 2. 配置路由
const routes = [
    {
        path: '/',
        component: () => import('@/views/home/index.vue'),
    },
    {
        path: '/about',
        component: () => import('@/views/about/index.vue'),
    },

];
// 1.返回一个 router 实列,为函数,里面有配置项(对象) history
const router = createRouter({
    mode: 'history',
    base: window.__POWERED_BY_QIANKUN__ ? "/child-one" : "/",
    history: createWebHashHistory('/child-one'),
    routes,
});

// 3导出路由   然后去 main.ts 注册 router.ts
export default router
  1. 入口文件 main.js 修改,为了避免根 id #app 与其他的 DOM 冲突,需要限制查找范围。并导出三个生命周期函数。
import { createApp } from 'vue'
import App from './App.vue'
import router from './router/index'
import './public-path'

// createApp(App).mount('#app')

let instance = null;
function render(props = {}) {
  if (instance) return;
  const { container } = props;
  console.log(container);
  instance = createApp(App)
    .use(router)
    .mount(container ? container.querySelector("#app-child-one") : "#app-child-one");
}

// 独立运行时
if (!window.__POWERED_BY_QIANKUN__) {
  render();
}

export async function bootstrap() {
  console.log("[vue] vue app bootstraped");
}
export async function mount(props) {
  console.log("[vue] props from main framework", props);
  render(props);
}
export async function unmount() {
  //可选链操作符
  instance.$destroy?.();
  instance = null;
}
  1. 主应用容器子应用
    qiankun-test/src/views/childOne/index.vue
<template>
  <h2>我是子应用 vue3-one</h2>
  <div id="child-vue3-one-content"></div>
</template>

<script>
import { start } from "qiankun";
export default {
  name: "childOne",
  components: {},
  mounted() {
    if (!window.qiankunStarted) {
      window.qiankunStarted = true;
      start();
    }
  },
};
</script>

<style>
</style>

运行效果如下:

微前端架构-qiankun在vue3的应用

vue2子应用-child-vue2

微前端架构-qiankun在vue3的应用

childVue2One/index.vue

<template>
  <h2>我是微应用vue2项目</h2>
  <div id="child-vue2-one-content"></div>
</template>

<script>
import { start } from "qiankun";
export default {
  name: "vueChild",
  components: {},
  mounted() {
    this.$nextTick(() => {
      if (!window.qiankunStarted) {
        window.qiankunStarted = true;
        start();
      }
    });
  },
};
</script>

<style>
</style>

  1. 微应用配置child-vue2

src下创建public-path.js


if (window.__POWERED_BY_QIANKUN__) {
    __webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__
}


main.js

// src/main.js
import Vue from 'vue'
import App from './App'
import router from './router'
import "./public-path";
 
Vue.config.productionTip = false
 
// 定义一个Vue实例
let instance = null
// 渲染方法
function render(props = {}) {
  const { container } = props
  instance = new Vue({
    router,
    render: (h) => h(App)
  }).$mount(container ? container.querySelector('#app'): '#app')
}
// 独立运行时
if(!window.__POWERED_BY_QIANKUN__) {
  render()
}
//暴露主应用生命周期钩子
/**
 * bootstrap : 在微应用初始化的时候调用一次,之后的生命周期里不再调用
 */
export async function bootstrap() {
  console.log('vue2-app bootstraped');
}
/**
 * mount : 在应用每次进入时调用
 */
export async function mount(props) {
  console.log('vue2-app mount', props);
  render(props);
}
/**
 * unmount :应用每次 切出/卸载 均会调用
 */
export async function unmount() {
  console.log("vue2-app unmount")
  instance.$destroy();
  instance.$el.innerHTML = '';
  instance = null;
}

vue.config.js

module.exports = {
    lintOnSave: false,
    devServer: {
        port: "3003",
        headers: {
            "Access-Control-Allow-Origin": "*", //所有人都可以访问我的服务器
        },
    },
    configureWebpack: {
        output: {
            // library: `${name}-[name]`,
            library: `vueChildOne`,
            libraryTarget: "umd", // 把微应用打包成 umd 库格式
            // jsonpFunction: `webpackJsonp_${name}`,
        },
    },
};

router.js

import { createRouter, createWebHashHistory, createWebHistory } from "vue-router";

// 2. 配置路由
const routes = [
    {
        path: '/',
        component: () => import('@/views/home/index.vue'),
    },
    {
        path: '/about',
        component: () => import('@/views/about/index.vue'),
    },

];
// 1.返回一个 router 实列,为函数,里面有配置项(对象) history
const router = createRouter({
    mode: 'history',
    base: window.__POWERED_BY_QIANKUN__ ? "/child-one" : "/",
    history: createWebHashHistory('/child-one'),
    routes,
});

// 3导出路由   然后去 main.ts 注册 router.ts
export default router

vue2错误问题

路由版本不对

微前端架构-qiankun在vue3的应用

下载指定版本在3*的就行

react子应用

微前端架构-qiankun在vue3的应用

问题
  1. 当修改入口文件index.tsx之后,主要是添加了qiankun的生命周期之后,报错

– You need to export lifecycle functions in reactApp1 entry

明明我已经写了生命周期但是没有生效。
问题出在:官方问题使用的js语法,我使用的是ts语法。
解决:用react-app-rewired方案复写webpack就可以了。作用:通过react-app-rewired插件,react-app-rewired的作用就是在不eject的情况下,覆盖create-react-app的配置.

angular子应用

angular由于在国内用的不多所以我是按照官方教程完成的,当然中间出了很多狗血的错误

官方:以 Angular-cli 9 生成的 angular 9 项目为例,其他版本的 angular 后续会逐渐补充。
这句话就是一个坑,首先我自己原有的angular版本是12,用 ng 命令安装的项目就是最新的了。这个导致我安装官方操作一直没有成功,不断报错。------我放弃了,做个乖孩子,用angular9

由于不能降低电脑全局版本,于是我在本项目中安装了一个angular-cli9

npm install  @angular/cli@9.0.1
ng new child-angular1

版本搞成了9那就好办了

  1. 根据要求配置好主应用的main.js与App.vue文件
  2. 在主应用views创建anguale的容器.vue文件
  3. 配置主应用路由
  4. 然后就是根据qiankun的文档配置文件了

注意:在qiankun的文档中第二步,child-angular-one这个是和主应用配置路由一致
设置 history 模式路由的 base,src/app/app-routing.module.ts 文件:

import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { APP_BASE_HREF } from '@angular/common';

const routes: Routes = [];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule],
  // @ts-ignore
  // child-angular-one 必须和主路由向对应
  providers: [{ provide: APP_BASE_HREF, useValue: window.__POWERED_BY_QIANKUN__ ? '/child-angular-one' : '/' }]
})
export class AppRoutingModule { }


gitee地址:qiankun-vue3文章来源地址https://www.toymoban.com/news/detail-404124.html

到了这里,关于微前端架构-qiankun在vue3的应用的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包赞助服务器费用

相关文章

  • 微前端qiankun架构 (基于vue2实现)使用教程

    微前端qiankun架构 (基于vue2实现)使用教程

    node -- 16+ @vue/cli -- 5+ 创建文件夹qiankun-test。 使用vue脚手架创建主应用main和子应用dev   安装 qiankun: 使用qiankun: 在 utils 内创建 微应用文件夹 microApp,在该文件夹内创建微应用出口文件 index.js,路由文件 microAppRouter,配置函数文件 microAppSetting。 路由文件 microAppRouter 配置函数文件

    2023年04月19日
    浏览(7)
  • qiankun:react18主应用 + 微应用 react18 + vue3

    qiankun:react18主应用 + 微应用 react18 + vue3

    一:主应用 搭建react项目 安装Antd 在 index.js中引入 安装react-router : 在 index.js中引入 安装 qiankun : 在主应用中注册微应用,在 index.js中引入 注:子应用嵌入到主应用的地方,id要跟index.js下registerMicroApps里面的container设置一致 修改App.js文件,将如下代码放入App.js 修改App.css样

    2024年02月16日
    浏览(15)
  • 使用vite-plugin-qiankun插件, 将应用快速接入乾坤(vue3 vite)

    qiankun官网 vite-plugin-qiankun插件github地址:vite-plugin-qiankun 1、安装乾坤 2、在主应用中注册微应用(main.ts) 3、挂载 在App.vue挂载微应用节点 1、安装插件 qiankun目前是不支持vite的,需要借助插件完成 2、修改vite.config.ts 3、修改main.ts

    2024年02月13日
    浏览(11)
  • 【几乎最全/全网最长的 2 万 字】前端工程化完整流程:从头搭到尾(vue3 + vite + qiankun + docker + tailwindcss + iview......)

    【几乎最全/全网最长的 2 万 字】前端工程化完整流程:从头搭到尾(vue3 + vite + qiankun + docker + tailwindcss + iview......)

    使用 Vite + Vue3 + Typescript + axios + echarts + pinia + view-ui-plus + vue-router + less + sass + scss + css + tailwindcss + animate.css + vite-svg-loader + postcss + stylelint + eslint + prettier + autoprefixer + commitizen + commitlint + vite-plugin-compression + vite-plugin-qiankun + Docker + nginx.conf…等等插件,带你从 0 开始一步一步搭

    2024年02月12日
    浏览(8)
  • Vue3.2 + TypeScript + Pinia + Vite4 + Element-Plus + 微前端(qiankun) 后台管理系统模板(已开源---显示项目页面截图)

    Vue3.2 + TypeScript + Pinia + Vite4 + Element-Plus + 微前端(qiankun) 后台管理系统模板(已开源---显示项目页面截图)

    Wocwin-Admin,是基于 Vue3.2、TypeScript、Vite、Pinia、Element-Plus、Qiankun(微前端) 开源的一套后台管理模板;同时集成了微前端 qiankun也可以当做一个子应用。项目中组件页面使用了Element-plus 二次封装 t-ui-plus 组件,目前已新增fastmock接口。 Link:https://wocwin.github.io/wocwin-admin/ 账号:

    2024年02月08日
    浏览(14)
  • 【qiankun】前端微服务架构踩坑记录

    【qiankun】前端微服务架构踩坑记录

    目录 前言 1.Cannot GET /cooperation/board 场景: 分析 解决 2.Invalid options in vue.config.js:\\\"css.requireModuleExtension\\\" is not allowed 原因 解决 3.less版本升级导致除法写法未转换 原因 解决 4.主子应用样式隔离 场景 解决 5.在webpack5中配置output报错 报错如下  原因  解决 6.微应用部署后报错 场景

    2024年02月15日
    浏览(7)
  • 前端vue3+typescript架构

    前端vue3+typescript架构

    1、vue creat 项目名称 选择自定义  选择需要的依赖  选择vue3  一路enter,选择eslist+prettier  继续enter,等待安装 按步骤操作,项目启动成功  2、vscode安装5款插件  2、代码保存自动格式化,保证每个开发人员代码一致,根目录新建三个文件.editorconfig和.prettierrc和.prettierignore

    2024年02月11日
    浏览(10)
  • vue项目集成乾坤(qiankun)微前端

    npm i qiankun -S qiankun文档官方地址:https://qiankun.umijs.org/zh/guide 新建一个.vue文件 配置路由地址

    2024年02月05日
    浏览(8)
  • 前端新手Vue3+Vite+Ts+Pinia+Sass项目指北系列文章 —— 第一章 技术栈简介 (开篇)

    前端新手Vue3+Vite+Ts+Pinia+Sass项目指北系列文章 —— 第一章 技术栈简介 (开篇)

    旨在帮助初学者掌握使用现代前端技术栈构建应用的基础知识和技能。在这个系列中,我们将深入探讨如何结合Vue.js、Vite、TypeScript、Pinia和Sass这些强大的工具和框架来开发现代化的前端应用。 通过这个系列,我们将从零开始构建一个完整的前端项目,覆盖项目初始化、组件

    2024年02月05日
    浏览(9)
  • 前端测试指南:Vue3 测试工具介绍与使用

    1.1 前端测试的重要性 在现代前端开发中,测试已经成为了必不可少的一环。测试可以保证代码的质量、可维护性和可靠性,防止代码的潜在错误和漏洞。同时,测试可以让开发者更加自信地提交代码和合并代码,以及更快地解决问题。因此,测试已经成为了前端开发中不可

    2024年02月10日
    浏览(19)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包