微前端基座样式,污染子应用样式的解决方案【硬核干货】

451
事件:微前端集成

技术栈:vue3,element-plus,京东微前端Micro-app:这个框架不同于熟知的single-spaqiankun的技术路线,而是借鉴了WebComponent的思想,通过CustomElement结合自定义的ShadowDom,将微前端封装成一个类WebComponent组件,基于ShadowDom天然的隔离属性,实现了js沙箱样式隔离元素隔离等一系列特性,大致可以理解成web端的docker容器,和平共处,互不干涉。

难点问题

基座应用使用的element-plus引入了element-plus/dist/index.css 某个子应用使用的是element-ui 2.x版本 引入了element-ui/lib/theme-chalk/index.css 两个文件中有相同的样式命名,导致基座应用的样式覆盖了子应用的样式,引起子应用的样式问题。

问题看起来很简单,但解决起来还是比较棘手的,由于微前端并没有实现基座应用、子应用的样式隔离问题,在尝试了各种hack的方式之后依然没能解决这个问题。

直到某天翻看element-plus文档的时候看到这样一句话,Element Plus 提供的默认命名空间为 el。 在特殊情况下,我们需要自定义命名空间,轻描淡写的一句话,起初并没有引起我太多的注意,这玩意能有啥用?

...刹那间... 灵光一闪... 这大概可能可以解决目前遇到的问题?说干就干(2.2.0版本以上才支持这个功能,所以低于这个版本需要先升级一下)

设置ElConfigProvider

使用 ElConfigProvider 包装根组件

<!-- App.vue -->

<template>
  <el-config-provider namespace="platform-ai">
    <router-view />
  </el-config-provider>
</template>

设置 SCSS 和 CSS 变量

创建 styles/element/index.scss

// styles/element/index.scss
// we can add this to custom namespace, default is 'el'
$namespace的值是可以随意命名的

@forward 'element-plus/theme-chalk/src/mixins/config.scss' with (
  $namespace: 'platform-ai'
);

在 vite.config.js 中导入 styles/element/index.scss

import { defineConfig } from 'vite'


export default defineConfig({
  css: {
    preprocessorOptions: {
      scss: {
        additionalData: `@use "~/styles/element/index.scss" as *;`,
      },
    },
  },
})

ps:官方文档中提示->Webpack也是如此,它需要在 preprocessorOptions 中设置, 但在vue.config.js中配置始终没能成功,大概率是sass-loader版本兼容问题,懒得折腾了

最后看下效果:

WechatIMG30.png

至此基座样式,污染子应用样式的问题就解决了