qiankun 主项目和子项目都是 vue2,部署在同一台服务器上,nginx 配置
1、主项目配置
1.1 micro.vue 组件
<template><div id="container-sub-app"></div>
</template><script>
import { loadMicroApp } from 'qiankun';
import actions from '@/utils/actions.js';export default {name: 'microApp',mixins: [actions],data() {return {microApp: null};},mounted() {const getMicroInfo = this.getMicroInfo();this.microApp = loadMicroApp(getMicroInfo, {singular: true});},beforeDestroy() {console.log('beforeDestroy...');this.microApp.unmount();},methods: {// 手动加载微应用getMicroInfo() {const appIdentifying = this.$route.path.split('/')[1];let data = {};const href = window.location.host;for (let i = 0; i < document.subApps.length; i++) {const element = document.subApps[i];if (element.activeRule.includes(appIdentifying)) {if (typeof element.entry !== 'string') {data = {...element,entry: element.entry[href]? element.entry[href]: Object.values(element.entry)[0]};} else {data = { ...element };}data.props = {token: {userInfo: {userName: '小明',userId: '123',date: new Date().toLocaleString()}}};data.activeRule = [appIdentifying];break;}}return data;}}
};
</script>
1.2 index.html 引入配置
<!DOCTYPE html>
<html><head><meta charset="utf-8" /><meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" /><metaname="viewport"content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no"/><link rel="icon" href="<%= BASE_URL %>favicon.ico" /><script src="<%= BASE_URL %>register-apps.js"></script><title><%= webpackConfig.name %></title></head><body><noscript><strong>We're sorry but <%= webpackConfig.name %> doesn't work properly withoutJavaScript enabled. Please enable it to continue.</strong></noscript><div id="app"></div><!-- built files will be auto injected --></body>
</html>
1.3 register-apps.js 配置
document.subApps = [{name: 'besFront',//entry: '//localhost:8086/bes-front/',// 本地调试entry: '/bes-front/',// 部署到服务器container: '#container-sub-app',activeRule: '/bes-front'}
];
1.4 路由配置
import Vue from 'vue';
import Router from 'vue-router';Vue.use(Router);import Layout from '@/layout';
import MicroApp from '@/components/microApp';export const constantRoutes = [{path: '/login',component: () => import('@/views/login/index'),hidden: true},{path: '/404',component: () => import('@/views/404'),hidden: true},{path: '/dashboard',component: Layout,redirect: '/dashboard/index',children: [{path: 'index',name: 'Dashboard',component: () => import('@/views/dashboard/index'),meta: { title: 'Dashboard', icon: 'dashboard' }}]},{path: '/',component: Layout,children: [{path: 'bes-front',component: MicroApp// 重点,用于加载子项目}]}// 404 page must be placed at the end !!!// { path: '*', redirect: '/404', hidden: true }
];const createRouter = () =>new Router({mode: 'history', // require service supportbase: '',scrollBehavior: () => ({ y: 0 }),routes: constantRoutes});const router = createRouter();// Detail see: https://github.com/vuejs/vue-router/issues/1234#issuecomment-357941465
export function resetRouter() {const newRouter = createRouter();router.matcher = newRouter.matcher; // reset router
}export default router;
2、子项目配置
2.1 main.js 配置
// 动态设置 publicPath
import './public-path';
import Vue from 'vue';
import App from './App.vue';
import router from './router';
import store from './store';
import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';Vue.config.productionTip = false;
Vue.use(ElementUI);let instance = null;
function render(props = {}) {console.log('子应用 render props::', props, 'instance====', instance);// sessionStorage.setItem('userInfo', JSON.stringify(props.token.userInfo));const { container } = props;instance = new Vue({router,store,render: (h) => h(App)}).$mount(container ? container.querySelector('#app') : '#app');
}// 独立运行时
/* eslint-disable */
if (!window.__POWERED_BY_QIANKUN__) {render();
}export async function bootstrap() {console.log('子应用 bootstrap ===========================');
}let initialState = null;
export async function mount(props) {console.log('子应用 mount props ===============', props);sessionStorage.setItem('userInfo', JSON.stringify(props.token.userInfo));props.onGlobalStateChange((state, prev) => {// state: 变更后的状态; prev 变更前的状态console.log('子应用获取共享数据 state::', state, 'prev::', prev);// 接收主应用中的共享数据 并将其设置为全局变量Vue.prototype.$initialState = state;});props.setGlobalState({initialState:'子应用中修改主应用中的全局变量,实现住应用子应用间数据的双向双向通信'});render(props);
}
export async function unmount() {console.log('子应用 unmount==========');instance.$destroy();instance.$el.innerHTML = '';instance = null;
}
2.2 public-path 文件
if (window.__POWERED_BY_QIANKUN__) {/* eslint-disable @typescript-eslint/camelcase */__webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__;
}
2.3 vue.config.js 配置
'use strict';
const path = require('path');
const defaultSettings = require('./src/settings.js');
const proxyTable = require('./proxyTable');function resolve(dir) {return path.join(__dirname, dir);
}const name = defaultSettings.title || 'vue Admin Template'; // page title// If your port is set to 80,// use administrator privileges to execute the command line.
// For example, Mac: sudo npm run
// You can change the port by the following methods:
// port = 9528 npm run dev OR npm run dev --port = 9528
const port = process.env.port || process.env.npm_config_port || 9528; // dev port// All configuration item explanations can be find in https://cli.vuejs.org/config/
module.exports = {/*** You will need to set publicPath if you plan to deploy your site under a sub path,* for example GitHub Pages. If you plan to deploy your site to https://foo.github.io/bar/,* then publicPath should be set to "/bar/".* In most cases please use '/' !!!* Detail: https://cli.vuejs.org/config/#publicpath*/publicPath: '/bes-front/',outputDir: 'dist',assetsDir: 'static',lintOnSave: process.env.NODE_ENV === 'development',productionSourceMap: false,devServer: {headers:{"Access-Control-Allow-Origin": "*",},port: port,open: true,proxy: proxyTable,overlay: {warnings: false,errors: true}},configureWebpack: {// provide the app's title in webpack's name field, so that// it can be accessed in index.html to inject the correct title.name: name,output:{library: `besFront`,// 主应用libraryTarget: "umd",// 把微应用打包成 umd 库格式jsonpFunction: `webpackJsonp_besFront`,// webpack5 需要把 jsonpFunction 替换成 chunkLoadingGlobal},resolve: {alias: {'@': resolve('src')}}},chainWebpack(config) {// it can improve the speed of the first screen, it is recommended to turn on preloadconfig.plugin('preload').tap(() => [{rel: 'preload',// to ignore runtime.js// https://github.com/vuejs/vue-cli/blob/dev/packages/%40vue/cli-service/lib/config/app.js#L171fileBlacklist: [/\.map$/, /hot-update\.js$/, /runtime\..*\.js$/],include: 'initial'}]);// when there are many pages, it will cause too many meaningless requestsconfig.plugins.delete('prefetch');// set svg-sprite-loaderconfig.module.rule('svg').exclude.add(resolve('src/icons')).end();config.module.rule('icons').test(/\.svg$/).include.add(resolve('src/icons')).end().use('svg-sprite-loader').loader('svg-sprite-loader').options({symbolId: 'icon-[name]'}).end();config.when(process.env.NODE_ENV !== 'development', (config) => {config.plugin('ScriptExtHtmlWebpackPlugin').after('html').use('script-ext-html-webpack-plugin', [{// `runtime` must same as runtimeChunk name. default is `runtime`inline: /runtime\..*\.js$/}]).end();config.optimization.splitChunks({chunks: 'all',cacheGroups: {libs: {name: 'chunk-libs',test: /[\\/]node_modules[\\/]/,priority: 10,chunks: 'initial' // only package third parties that are initially dependent},elementUI: {name: 'chunk-elementUI', // split elementUI into a single packagepriority: 20, // the weight needs to be larger than libs and app or it will be packaged into libs or apptest: /[\\/]node_modules[\\/]_?element-ui(.*)/ // in order to adapt to cnpm},commons: {name: 'chunk-commons',test: resolve('src/components'), // can customize your rulesminChunks: 3, // minimum common numberpriority: 5,reuseExistingChunk: true}}});// https:// webpack.js.org/configuration/optimization/#optimizationruntimechunkconfig.optimization.runtimeChunk('single');});}
};
3、主项目和子项目部署在同一台服务器上,其中主应用路由使用history模式,子应用路由使用hash模式,nginx 的配置如下:
locatoin / {root /opt/parent;index index.html index.htm;try_files $uri $uri/ /index.html;
}location /bes-front/ {root /opt/parent;index index.html index.htm;try_files $uri $uri. /index.html;
}
注:使用的下面这种部署方式,主应用代码放在parent目录下,子应用代码放在parent目录下面,其他,子应用的目录应该代码中的名称保持一致,在本示例当中,子应用使用的是bes-front
官网参考链接: 入门教程 - qiankun
4、总结
在部署主应用和子应用时,遇到主应用转发到子应用时,静态资源无法访问的问题,重点是查看子应用publicPath这个配置,这个是静态文件的访问前缀,如果部署到服务器上,子应用的静态资源无法访问到,可以看一下服务器访问的静态资源的前缀是否和代码中配置的一致。
相关文章:

qiankun 主项目和子项目都是 vue2,部署在同一台服务器上,nginx 配置
1、主项目配置 1.1 micro.vue 组件 <template><div id"container-sub-app"></div> </template><script> import { loadMicroApp } from qiankun; import actions from /utils/actions.js;export default {name: microApp,mixins: [ac…...
深入浅出MongoDB(七)
深入浅出MongoDB(七) 文章目录 深入浅出MongoDB(七)查询优化创建索引以支持读取操作查询选择性覆盖查询 分析性能使用数据库分析器评估对数据库的操作使用db.currentOp()评估mongod操作使用explain评估查询性能 优化查询性能创建索…...

【华为】配置NAT访问互联网
1.AR1: int g0/0/0 ip ad 64.1.1.2 255.255.255.0 int g0/0/1 ip ad 110.242.68.1 255.255.255.02.AR2: (1)配置端口ip: int g0/0/1 ip ad 10.3.1.2 255.255.255.0 int g0/0/0 ip ad 64.1.1.1 255.255.255.0(2)配置默认路由: ip route-static 0.0.0.0 0.…...
Spring Boot项目使用多线程执行定时任务
我在一个Spring Boot项目中,采用定时器执行一些操作,比如10秒就发送一次数据。这些操作有2个,如下所示。我就想,虽然这两个操作各自指定了时间频率,但如果其中一个操作非常耗时,会不会影响其他操作呢&#…...

【安装JDK和Android SDK】
安装JDK和Android SDK 1 前言2 下载2.1 下载途径2.2 JDK下载和安装2.2.1 下载2.2.2 安装并配置环境变量2.2.3 验证 2.3 SDK下载和安装2.3.1 下载2.3.2 安装2.3.3 环境变量配置2.3.4 验证 1 前言 在软件开发中,Android应用开发通常使用Android Studio,但…...

汇总10个AI免费一键生成PPT的网站
一、前言 PPT幻灯片是现代办公和学习中的重要组成部分。它在工作、研究或培训中扮演着重要角色,并能够让观众更好地理解信息。随着当今人工智能技术的快速发展,现在有很多免费的AI PPT生成器可供选择,帮助用户更加便捷地制作出高效且具有较强…...

超材料光子晶体和禁带分析实例_CST电磁仿真教程
光子晶体是由周期性排列的不同折射率的介质制造的光学结构,可被视为广义超材料metamaterial的一种。本期我们演示设计一个基于光频能带(PBG,photonics band gap) 的二维光子晶体波导,能带分析方法也可适用于微波波段(EBG,electromagetic band…...

关于OceanBase数据库的poc测试连接经验(by liuhui)
poc客户给了OceanBase数据库实例如下 ob实例: ip:1xx.xx.xx 端口:2883 实例名:obm_xczjj_1_poc#cs_pool_1 用户名:root 密码:xxxxxx 问题出现:根据客户提供的OceanBase数据库配置报错。配置如下 查询数据…...
Docker部署如何修改本地mysql,redis连接信息
要修改数据库 MySQL 和缓存 Redis 的地址为 ruoyi-mysql 和 ruoyi-redis,通常需要在 Spring Boot 项目的配置文件中进行相应的修改。 ### 修改 MySQL 数据库地址为 ruoyi-mysql 1. **在 Spring Boot 项目中找到 application.properties 或 application.yml 文件**…...
PHP中的ReflectionClass常见用法
ReflectionClass是 PHP 中的一个类,它提供了有关类的信息的反射。 使用ReflectionClass可以在运行时获取关于类的各种信息,例如类的名称、方法、属性、注释等。 以下是一些常见的用法: 获取类的名称: $reflection new Reflec…...

processing像素画教程
前提:各位已经安装了processing 第一步:创建一个简单的网格 我们首先创建一个网格来定义我们作品的像素画布。网格将帮助您在适当的位置绘制每个像素。 int gridSize 20; // 每个像素的大小 int cols, rows; void setup() {size(400, 400); // 设置画…...
【秋招笔试】10.13字节跳动(已改编)秋招-三语言题解
🍭 大家好这里是 春秋招笔试突围,一起备战大厂笔试 💻 ACM金牌团队🏅️ | 多次AK大厂笔试 | 大厂实习经历 ✨ 本系列打算持续跟新 春秋招笔试题 👏 感谢大家的订阅➕ 和 喜欢💗 和 手里的小花花🌸 ✨ 笔试合集传送们 -> 🧷春秋招笔试合集 本次的三题全部上线…...

牛客网上最全的Java八股文整理,涵盖Java全栈技术点
Java 面试 “金九银十”这个字眼对于程序员应该是再熟悉不过的了,每年的金九银十都会有很多程序员找工作、跳槽等一系列的安排。说实话,面试中 7 分靠能力,3 分靠技能;在刚开始的时候介绍项目都是技能中的重中之重,它…...

Skyeye 云智能制造 v3.14.9 发布,ERP 商城 + AI
Skyeye 云智能制造,采用 Springboot winUI 的低代码平台、移动端采用 UNI-APP。包含 30 多个应用模块、50 多种电子流程,CRM、PM、ERP、MES、ADM、EHR、笔记、知识库、项目、门店、商城、财务、多班次考勤、薪资、招聘、云售后、论坛、公告、问卷、报表…...

Element-快速入门
什么是 Element 在现代前端开发中,组件化的思想日益盛行,Element组件库作为一款流行的UI组件库,特别适用于基于Vue.js的项目,它为开发者提供了丰富的组件和良好的开发体验。 想要使用Element的组件库,我们需要完成下面…...

利士策分享,从“亮剑精神”汲取财富智慧
利士策分享,从“亮剑精神”汲取财富智慧 在某一广袤区域内,一场寓意深远的活动正如火如荼地展开,它不仅象征着直面挑战的勇气,更隐含着经济社会发展的深层启示。 对于广大民众来说,这场活动背后所传达的理念与机遇&am…...
【JavaScript】关于使用JS对word文档实现预览的一些思考
文章目录 mammothdocx4js mammoth 官网地址:https://github.com/mwilliamson/mammoth.js#readme 安装mammoth: npm i mammoth -S我们可以安装mammoth来实现上传的word文件的在线预览,我们以element的上传组件为示例: <temp…...

安宝特方案 | AR技术在轨交行业的应用优势
随着轨道交通行业不断向智能化和数字化转型,传统巡检方式的局限性日益凸显。而安宝特AR眼镜以其独特的佩戴方式和轻便设计,为轨道交通巡检领域注入了创新活力,提供了全新的解决方案。 01 多样化佩戴方法,完美适应户外环境 安宝特…...

K8S配置MySQL主从自动水平扩展
前提环境 操作系统Ubuntu 22.04 K8S 1.28.2集群(1个master2个node) MySQL 5.7.44部署在K8S的主从集群 metrics-server v0.6.4 概念简介 在K8s中扩缩容分为两种 ●Node层面:对K8s物理节点扩容和缩容,根据业务规模实现物理节点自动扩…...

Excel:将一列拆分成多列
实现的效果是: 操作步骤如下: 1.选中列 → 点击菜单栏中的"数据" → 分列 2.选择"分列符号",点击下一步 3.我想要按照空格分列,就选择空格 4.点击完成,就可以实现分列的效果了...

多云管理“拦路虎”:深入解析网络互联、身份同步与成本可视化的技术复杂度
一、引言:多云环境的技术复杂性本质 企业采用多云策略已从技术选型升维至生存刚需。当业务系统分散部署在多个云平台时,基础设施的技术债呈现指数级积累。网络连接、身份认证、成本管理这三大核心挑战相互嵌套:跨云网络构建数据…...
Linux链表操作全解析
Linux C语言链表深度解析与实战技巧 一、链表基础概念与内核链表优势1.1 为什么使用链表?1.2 Linux 内核链表与用户态链表的区别 二、内核链表结构与宏解析常用宏/函数 三、内核链表的优点四、用户态链表示例五、双向循环链表在内核中的实现优势5.1 插入效率5.2 安全…...
日语学习-日语知识点小记-构建基础-JLPT-N4阶段(33):にする
日语学习-日语知识点小记-构建基础-JLPT-N4阶段(33):にする 1、前言(1)情况说明(2)工程师的信仰2、知识点(1) にする1,接续:名词+にする2,接续:疑问词+にする3,(A)は(B)にする。(2)復習:(1)复习句子(2)ために & ように(3)そう(4)にする3、…...

MFC内存泄露
1、泄露代码示例 void X::SetApplicationBtn() {CMFCRibbonApplicationButton* pBtn GetApplicationButton();// 获取 Ribbon Bar 指针// 创建自定义按钮CCustomRibbonAppButton* pCustomButton new CCustomRibbonAppButton();pCustomButton->SetImage(IDB_BITMAP_Jdp26)…...

Debian系统简介
目录 Debian系统介绍 Debian版本介绍 Debian软件源介绍 软件包管理工具dpkg dpkg核心指令详解 安装软件包 卸载软件包 查询软件包状态 验证软件包完整性 手动处理依赖关系 dpkg vs apt Debian系统介绍 Debian 和 Ubuntu 都是基于 Debian内核 的 Linux 发行版ÿ…...

理解 MCP 工作流:使用 Ollama 和 LangChain 构建本地 MCP 客户端
🌟 什么是 MCP? 模型控制协议 (MCP) 是一种创新的协议,旨在无缝连接 AI 模型与应用程序。 MCP 是一个开源协议,它标准化了我们的 LLM 应用程序连接所需工具和数据源并与之协作的方式。 可以把它想象成你的 AI 模型 和想要使用它…...

376. Wiggle Subsequence
376. Wiggle Subsequence 代码 class Solution { public:int wiggleMaxLength(vector<int>& nums) {int n nums.size();int res 1;int prediff 0;int curdiff 0;for(int i 0;i < n-1;i){curdiff nums[i1] - nums[i];if( (prediff > 0 && curdif…...

对WWDC 2025 Keynote 内容的预测
借助我们以往对苹果公司发展路径的深入研究经验,以及大语言模型的分析能力,我们系统梳理了多年来苹果 WWDC 主题演讲的规律。在 WWDC 2025 即将揭幕之际,我们让 ChatGPT 对今年的 Keynote 内容进行了一个初步预测,聊作存档。等到明…...

如何在看板中有效管理突发紧急任务
在看板中有效管理突发紧急任务需要:设立专门的紧急任务通道、重新调整任务优先级、保持适度的WIP(Work-in-Progress)弹性、优化任务处理流程、提高团队应对突发情况的敏捷性。其中,设立专门的紧急任务通道尤为重要,这能…...
VTK如何让部分单位不可见
最近遇到一个需求,需要让一个vtkDataSet中的部分单元不可见,查阅了一些资料大概有以下几种方式 1.通过颜色映射表来进行,是最正规的做法 vtkNew<vtkLookupTable> lut; //值为0不显示,主要是最后一个参数,透明度…...