# 基础配置

# mode

type: 'modules', default: 'modules',

一般设置为 'modules'。否则 子应用入口文件输出集成开发 将不会生效。

# features

  • type:array
  • default:['magic-modules', '$module', 'argvToRuntime', 'hackJsonpFunction', 'hackChunkName']

特性开关

magic-modules: 用于特殊资源解析,具体参考:[资源映射](#资源映射)

$module: 用于解析 '$module' 开头的资源,类似于 webpack alias, 但值是动态的,通过从当前文件向上查找第一个 modules 目录来确认当前的 $module 的值,参考 [当前模块根目录](#当前模块根目录)。

argvToRuntime: 用于将编译命令行参数解析为 runtime 参数,具体参考:[读取编译参数](#读取编译参数)

hackJsonpFunction: 自动处理 jsonpFunction 的值,避免子应用间的冲突,推荐;仅当 { mode: 'modules' } 时生效。

hackChunkName: 对于异步加载的资源输出名,增加 contenthash(v5)/chunkhash(v4) 处理,如果项目自己设置了 publicPath 则不需要;仅当 { mode: 'modules' } 时生效。

TIP

如果只使用了部分特性,或者不使用任何特性时,通过自定义 features 可以在一定程度上提高编译速度。

# 子应用入口文件输出

TIP

仅当 { mode: 'modules' } 时生效。

插件会在编译结束,自动生成一份资源元数据文件。该文件即为接入宿主应用所使用的入口文件。

# moduleEntryFile

  • type:string
  • defaultindex.js

资源元数据文件输出路径,

# outputJSON

  • type:boolean
  • defaultfalse

资源元数据以 json 格式输出。此时默认输出文件为:index.json

# assetsModifier (beta)

  • type:function
  • default(assetsJson) => assetsJson

TIP

仅当 { mode: 'modules' } 时生效。

插件在输出资源列表文件前,通过该参数进行输出值处理。一般用于附加非 webpack 处理的资源文件。

# 集成开发

通常宿主应用、子应用会各自独立启动运行,在开发调试时,我们可以将宿主应用、子应用集成到一个服务中来完成所见即所得的集成调试体验。仅在开发时用。

TIP

仅当 { mode: 'modules' } 时生效。

# devConfig.currentServer

  • type:string Required. 当前服务的地址。(对于宿主应用,通常不需要)

# devConfig.platformServer

  • type:string Required. 宿主应用的服务地址。

# devConfig.platformLocalPort

  • type:string|number Required. 集成调试服务端口。

# devConfig.modulesConfig

  • type:object Required. 集成调试时,用于配置子应用的基本信息,url 默认使用 currentServer 和 moduleEntryFile。
    devConfig: {
        modulesConfig: {
            childAppReact: {
                type: 'app',
                name: 'childAppReact',
            },
            childAppVue2: {
                type: 'app',
                name: 'Vue2 的子应用',
                url: 'http://localhost:3001/index.js',
            },
        },
    },

# devConfig.onAllServerReady

  • type:function Optional. 当所有服务都准备就绪后触发。

# devConfig.platformProxyTable

  • type: object Optional. 集成调试时,对于宿主应用中的接口请求请进行代理,用于覆盖默认的接口调用。比较少用。

# 资源映射

TIP

仅当 features 选项中启用了 'magic-modules' 时生效(默认启用)

用于导入由宿主应用所提供资源, 资源格式为: [scope?]:[namespace].[resource]

  • scope: Optional, 默认:'default'。表示资源范围,与 JModule.export 中的 scope 含义一致。
  • namespace: 资源命名空间
  • resource: 具体的资源名

eg:

import Vue from 'myScope:$node_modules.vue';

// 资源地址:'myScope:$node_modules.vue'
// scope: 'myScope'
// namespace: '$node_modules'
// resource: 'vue'

# supportedNamespaces

  • type:array
  • default:['$platform', '$node_modules']

指定外部资源的命名空间,非命名空间下的资源不做特殊处理。

比如,默认情况下:

import router from 'myScope:$platform.router'

将会被解析为

const router = JModule.import('$platform.router', {
    scope: 'myScope',
})

import 'invalidNamespace.router' 将不会被特殊处理。

# externalAlias

  • type:object
  • default:{}

编译过程中,对导入的资源进行替换,类似webpack externals。需要同时兼容多个微前端框架或独立访问时很有用,可以保持同一份源码编译出不同的产物。

TIP

当映射的目标地址为 $module.meta 或者 supportedNamespaces 指定资源匹配时生效。

# 读取编译参数

TIP

仅当 features 选项中启用了 'argvToRuntime' 时生效(默认启用)

用于在运行时读取编译所用的参数。运行时的参数名会被转换为大写加‘_’的形式。

eg: npm run build -- --mode-a=production 可以通过 process.argv.MODE_A 读取。

# 当前模块根目录

TIP

  • 仅当 features 选项中启用了 '$module' 时生效(默认启用)
  • 尽在下述项目结构中有效

对于

src/
└── modules
    ├── moduleA
    │   ├── index.js
        ├── sth.js
    └── moduleB

项目结构时,通常需要找到 moduleA 或 moduleB 当作模块根目录, 通过 $module 可以方便找到当前模块根目录。

// src/modules/moduleA/index.js
import sth from '$module/sth.js'

// 将自动指向 src/modules/moduleA/sth.js 文件

# 完整的配置参考

根据具体配置项的功能,按需要使用即可。配置项细节请参考前文的说明。

// .jmodule.conf.js
const opn = require('opn');
const chalk = require('chalk');
const platformServer = process.env.platformServer || 'http://localhost:8080';
const currentServer = process.env.currentServer || 'http://localhost:3000';
const platformLocalPort = process.env.platformLocalPort || 8093;

module.exports = {
    mode: 'modules',
    features: ['magic-modules', '$module', 'argvToRuntime'],
    moduleEntryFile: 'index.js',
    outputJSON: false,
    supportedNamespaces: ['$platform', '$node_modules'],
    externalAlias: {
        'vue': '$node_modules.vue', // eg: 对于路由模式的子应用,通常使用宿主应用提供的 Vue,可以在这里进行资源重定向,指向宿主应用提供的 Vue,既能减少打包的代码也可以避免编写特异性的业务代码。
    },
    devConfig: platform.env === 'development' ? {
        modulesConfig: { // 子应用配置
            childAppReact: {
                type: 'app',
                name: 'childAppReact',
                url: undefined, // 默认用根据 currentServer 自动生成
            },
            childAppVue2: {
                type: 'app',
                name: 'Vue2 的子应用',
                url: 'http://localhost:3001/index.js',
            },
        },
        currentServer, // 当前应用的服务地址 
        platformServer, // 宿主应用服务地址
        platformProxyTable: {
            '/api': {
                target: currentServer,
                changeOrigin: true,
            },
        }, // 将宿主应用中的接口调用代理到其它服务
        platformLocalPort, // 本地集成调试端口
        onAllServerReady: () => { // 当 currentServer\platformServer\platformLocalPort 均启动完毕时触发
            const targetService = `http://localhost:${platformLocalPort}/`;
            console.log(chalk.green('\n\t已启动集成服务: '), chalk.cyanBright(targetService), '\n');
            opn(`http://localhost:${platformLocalPort}`);
        },
    } : {},
}

TIP

devConfig 中的所有配置项,仅用于开发模式下调试,且会自动注入加载子应用脚本的功能。为适应更灵活的业务场景,生产环境的宿主应用加载子应用的实现请参考:宿主应用开发者.