@ttk/micro-frontend-react
Advanced tools
+322
-218
| (function (global, factory) { | ||
| typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('react'), require('qiankun'), require('react-dom')) : | ||
| typeof define === 'function' && define.amd ? define(['exports', 'react', 'qiankun', 'react-dom'], factory) : | ||
| (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.ttk_mf_react = {}, global.react, global.qiankun, global.ReactDOM)); | ||
| typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('react'), require('qiankun'), require('react-dom')) : | ||
| typeof define === 'function' && define.amd ? define(['exports', 'react', 'qiankun', 'react-dom'], factory) : | ||
| (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.ttk_mf_react = {}, global.react, global.qiankun, global.ReactDOM)); | ||
| }(this, (function (exports, React, qiankun, ReactDOM) { 'use strict'; | ||
| function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; } | ||
| function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; } | ||
| var React__default = /*#__PURE__*/_interopDefaultLegacy(React); | ||
| var ReactDOM__default = /*#__PURE__*/_interopDefaultLegacy(ReactDOM); | ||
| var React__default = /*#__PURE__*/_interopDefaultLegacy(React); | ||
| var ReactDOM__default = /*#__PURE__*/_interopDefaultLegacy(ReactDOM); | ||
| var STYLE_APP = { | ||
| width: '100%', | ||
| height: '100%', | ||
| overflow: 'hidden' | ||
| }; | ||
| var STYLE_APP_CONTAINER = { | ||
| width: '100%', | ||
| height: '100%' | ||
| }; | ||
| var STYLE_APP_SPIN = { | ||
| width: '100%', | ||
| height: '100%', | ||
| display: 'flex', | ||
| alignItems: 'center', | ||
| justifyContent: 'center' | ||
| }; | ||
| var STYLE_APP_ERROR = { | ||
| width: '100%', | ||
| height: '100%', | ||
| padding: 10, | ||
| color: 'red' | ||
| }; | ||
| var STYLE_APP_ERROR_MSG = { | ||
| display: 'block', | ||
| fontSize: 16 | ||
| }; | ||
| function mfApp(props) { | ||
| var mfAppConfig = props.mfAppConfig; | ||
| var name = mfAppConfig.name, | ||
| entry = mfAppConfig.entry, | ||
| startAppName = mfAppConfig.startAppName, | ||
| _mfAppConfig$delayLoa = mfAppConfig.delayLoading, | ||
| delayLoading = _mfAppConfig$delayLoa === void 0 ? false : _mfAppConfig$delayLoa, | ||
| params = mfAppConfig.params, | ||
| callbacks = mfAppConfig.callbacks, | ||
| onSaveState = mfAppConfig.onSaveState, | ||
| restoreState = mfAppConfig.restoreState, | ||
| _mfAppConfig$singular = mfAppConfig.singular, | ||
| singular = _mfAppConfig$singular === void 0 ? true : _mfAppConfig$singular, | ||
| RenderLoading = mfAppConfig.renderLoading, | ||
| RenderError = mfAppConfig.renderError; | ||
| function getDefaultExportFromCjs (x) { | ||
| return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x; | ||
| } | ||
| var _useState = React.useState(true), | ||
| loading = _useState[0], | ||
| setLoading = _useState[1]; | ||
| function createCommonjsModule(fn, basedir, module) { | ||
| return module = { | ||
| path: basedir, | ||
| exports: {}, | ||
| require: function (path, base) { | ||
| return commonjsRequire(path, (base === undefined || base === null) ? module.path : base); | ||
| } | ||
| }, fn(module, module.exports), module.exports; | ||
| } | ||
| var _useState2 = React.useState(false), | ||
| error = _useState2[0], | ||
| setError = _useState2[1]; | ||
| function commonjsRequire () { | ||
| throw new Error('Dynamic requires are not currently supported by @rollup/plugin-commonjs'); | ||
| } | ||
| var _useState3 = React.useState("\u5FAE\u5E94\u7528" + name + "\u52A0\u8F7D\u5931\u8D25\uFF0C\u8BF7\u91CD\u65B0\u52A0\u8F7D\uFF01"), | ||
| errorMsg = _useState3[0]; | ||
| var _extends_1 = createCommonjsModule(function (module) { | ||
| function _extends() { | ||
| module.exports = _extends = Object.assign || function (target) { | ||
| for (var i = 1; i < arguments.length; i++) { | ||
| var source = arguments[i]; | ||
| var _useState4 = React.useState(''), | ||
| errorDesc = _useState4[0], | ||
| setErrorDesc = _useState4[1]; | ||
| for (var key in source) { | ||
| if (Object.prototype.hasOwnProperty.call(source, key)) { | ||
| target[key] = source[key]; | ||
| } | ||
| } | ||
| } | ||
| var appRef = React.useRef(null); | ||
| var ref = React.useRef(null); | ||
| var errorHandler = React.useCallback(function (event) { | ||
| setLoading(false); | ||
| setError(true); | ||
| setErrorDesc(event.reason ? event.reason.stack : event.type); | ||
| }, []); | ||
| React.useEffect(function () { | ||
| if (!name || !entry) { | ||
| var description = "" + (!name ? 'MicroApp的name不能为空,微应用的名称,微应用之间必须确保唯一。' : '') + (!entry ? 'entry不能为空,微应用的入口。' : ''); | ||
| setLoading(false); | ||
| setError(true); | ||
| setErrorDesc(description); | ||
| } | ||
| return target; | ||
| }; | ||
| if (delayLoading) { | ||
| return; | ||
| } | ||
| module.exports["default"] = module.exports, module.exports.__esModule = true; | ||
| return _extends.apply(this, arguments); | ||
| } | ||
| qiankun.addGlobalUncaughtErrorHandler(errorHandler); | ||
| var configuration = { | ||
| sandbox: { | ||
| experimentalStyleIsolation: true | ||
| }, | ||
| singular: singular | ||
| }; | ||
| module.exports = _extends; | ||
| module.exports["default"] = module.exports, module.exports.__esModule = true; | ||
| }); | ||
| if (!appRef.current) { | ||
| appRef.current = qiankun.loadMicroApp({ | ||
| name: name, | ||
| entry: entry, | ||
| container: ref.current || '', | ||
| props: { | ||
| restoreState: restoreState, | ||
| onSaveState: onSaveState, | ||
| startAppName: startAppName, | ||
| params: params, | ||
| callbacks: callbacks | ||
| } | ||
| }, configuration); | ||
| appRef.current.mountPromise.then(function () { | ||
| setLoading(false); | ||
| }); | ||
| } else if (appRef.current.update) { | ||
| appRef.current.update({ | ||
| container: ref.current, | ||
| restoreState: restoreState, | ||
| onSaveState: onSaveState, | ||
| startAppName: startAppName, | ||
| params: params, | ||
| callbacks: callbacks | ||
| }); | ||
| } | ||
| var _extends = /*@__PURE__*/getDefaultExportFromCjs(_extends_1); | ||
| return function () { | ||
| var _appRef$current; | ||
| var STYLE_APP = { | ||
| width: '100%', | ||
| height: '100%', | ||
| overflow: 'hidden' | ||
| }; | ||
| var STYLE_APP_CONTAINER = { | ||
| width: '100%', | ||
| height: '100%' | ||
| }; | ||
| var STYLE_APP_SPIN = { | ||
| width: '100%', | ||
| height: '100%', | ||
| display: 'flex', | ||
| alignItems: 'center', | ||
| justifyContent: 'center' | ||
| }; | ||
| var STYLE_APP_ERROR = { | ||
| width: '100%', | ||
| height: '100%', | ||
| padding: 10, | ||
| color: 'red' | ||
| }; | ||
| var STYLE_APP_ERROR_MSG = { | ||
| display: 'block', | ||
| fontSize: 16 | ||
| }; | ||
| function MfApp(props) { | ||
| var mfAppConfig = props.mfAppConfig; | ||
| var name = mfAppConfig.name, | ||
| entry = mfAppConfig.entry, | ||
| startAppName = mfAppConfig.startAppName, | ||
| _mfAppConfig$delayLoa = mfAppConfig.delayLoad, | ||
| delayLoad = _mfAppConfig$delayLoa === void 0 ? false : _mfAppConfig$delayLoa, | ||
| params = mfAppConfig.params, | ||
| callbacks = mfAppConfig.callbacks, | ||
| onSaveState = mfAppConfig.onSaveState, | ||
| restoreState = mfAppConfig.restoreState, | ||
| singular = mfAppConfig.singular, | ||
| RenderLoading = mfAppConfig.renderLoading, | ||
| RenderError = mfAppConfig.renderError; | ||
| console.log('mount startAppName', startAppName); | ||
| var status = (_appRef$current = appRef.current) == null ? void 0 : _appRef$current.getStatus(); | ||
| var _useState = React.useState(true), | ||
| loading = _useState[0], | ||
| setLoading = _useState[1]; | ||
| if ('MOUNTED' === status) { | ||
| var _appRef$current2; | ||
| var _useState2 = React.useState(false), | ||
| error = _useState2[0], | ||
| setError = _useState2[1]; | ||
| (_appRef$current2 = appRef.current) == null ? void 0 : _appRef$current2.unmount(); | ||
| } | ||
| var _useState3 = React.useState("\u5FAE\u5E94\u7528" + name + "\u52A0\u8F7D\u5931\u8D25\uFF0C\u8BF7\u91CD\u65B0\u52A0\u8F7D\uFF01"), | ||
| errorMsg = _useState3[0]; | ||
| qiankun.removeGlobalUncaughtErrorHandler(errorHandler); | ||
| }; | ||
| }, [mfAppConfig, delayLoading]); | ||
| return /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP | ||
| }, (delayLoading || loading) && RenderLoading ? /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_SPIN | ||
| }, /*#__PURE__*/React__default['default'].createElement(RenderLoading, { | ||
| loading: loading | ||
| })) : null, error ? /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_ERROR | ||
| }, RenderError ? /*#__PURE__*/React__default['default'].createElement(RenderError, { | ||
| message: errorMsg, | ||
| description: errorDesc | ||
| }) : [/*#__PURE__*/React__default['default'].createElement("span", { | ||
| style: STYLE_APP_ERROR_MSG | ||
| }, errorMsg), /*#__PURE__*/React__default['default'].createElement("span", null, errorDesc)]) : null, /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_CONTAINER, | ||
| ref: ref | ||
| })); | ||
| } | ||
| var _useState4 = React.useState(''), | ||
| errorDesc = _useState4[0], | ||
| setErrorDesc = _useState4[1]; | ||
| /** | ||
| * single-SPA生命周期钩子,只会在微应用初始化的时候调用一次,下次微应用重新进入时会直接调用 mount 钩子,不会再重复触发 bootstrap。 | ||
| * 通常我们可以在这里做一些全局变量的初始化,比如不会在 unmount 阶段被销毁的应用级别的缓存等。 | ||
| */ | ||
| var bootstrap = function bootstrap(props) { | ||
| var packageName = props.packageName, | ||
| startAppName = props.startAppName; | ||
| console.log("[" + packageName + "] app bootstraped. startAppName:", startAppName); | ||
| }; | ||
| /** | ||
| * single-SPA生命周期钩子,应用每次进入都会调用 mount 方法,通常我们在这里触发应用的渲染方法 | ||
| */ | ||
| var appRef = React.useRef(null); | ||
| var ref = React.useRef(null); | ||
| var errorHandler = React.useCallback(function (event) { | ||
| setLoading(false); | ||
| setError(true); | ||
| setErrorDesc(event.reason ? event.reason.stack : event.type); | ||
| }, []); | ||
| React.useEffect(function () { | ||
| if (!name || !entry) { | ||
| var description = "" + (!name ? 'MicroApp的name不能为空,微应用的名称,微应用之间必须确保唯一。' : '') + (!entry ? 'entry不能为空,微应用的入口。' : ''); | ||
| setLoading(false); | ||
| setError(true); | ||
| setErrorDesc(description); | ||
| } | ||
| var mount = function mount(props) { | ||
| var packageName = props.packageName, | ||
| targetDomId = props.targetDomId, | ||
| container = props.container, | ||
| startAppName = props.startAppName, | ||
| restoreState = props.restoreState, | ||
| params = props.params, | ||
| callbacks = props.callbacks, | ||
| Root = props.render; | ||
| console.log("[" + packageName + "] app mounted. startAppName:", startAppName); | ||
| ReactDOM__default['default'].render( /*#__PURE__*/React__default['default'].createElement(Root, { | ||
| startAppName: startAppName, | ||
| initData: restoreState, | ||
| params: params, | ||
| callbacks: callbacks | ||
| }), container ? container.querySelector("#" + targetDomId) : document.getElementById(targetDomId)); | ||
| }; | ||
| /** | ||
| * single-SPA生命周期钩子,应用每次 切出/卸载 会调用的方法,通常在这里我们会卸载微应用的应用实例 | ||
| */ | ||
| if (delayLoad) { | ||
| return; | ||
| } | ||
| var unmount = function unmount(props) { | ||
| var packageName = props.packageName, | ||
| targetDomId = props.targetDomId, | ||
| container = props.container, | ||
| startAppName = props.startAppName, | ||
| onSaveState = props.onSaveState, | ||
| state = props.state; | ||
| console.log("[" + packageName + "] app unmount. startAppName:", startAppName); | ||
| qiankun.addGlobalUncaughtErrorHandler(errorHandler); | ||
| var configuration = { | ||
| sandbox: { | ||
| experimentalStyleIsolation: true | ||
| }, | ||
| singular: singular | ||
| }; | ||
| if (startAppName && state && onSaveState) { | ||
| state.get(startAppName).filter(function (value, key) { | ||
| return key.startsWith('AppLoader'); | ||
| }).take(1).forEach(function (value) { | ||
| onSaveState(value.get('data').toJS()); | ||
| }); | ||
| } | ||
| if (!appRef.current) { | ||
| appRef.current = qiankun.loadMicroApp({ | ||
| name: name, | ||
| entry: entry, | ||
| container: ref.current || '', | ||
| props: { | ||
| restoreState: restoreState, | ||
| onSaveState: onSaveState, | ||
| startAppName: startAppName, | ||
| params: params, | ||
| callbacks: callbacks | ||
| } | ||
| }, configuration); | ||
| appRef.current.mountPromise.then(function () { | ||
| setLoading(false); | ||
| }); | ||
| } else if (appRef.current.update) { | ||
| appRef.current.update({ | ||
| container: ref.current, | ||
| restoreState: restoreState, | ||
| onSaveState: onSaveState, | ||
| startAppName: startAppName, | ||
| params: params, | ||
| callbacks: callbacks | ||
| }); | ||
| } | ||
| var element = container ? container.querySelector("#" + targetDomId) : document.getElementById(targetDomId); | ||
| element && ReactDOM__default['default'].unmountComponentAtNode(element); | ||
| }; | ||
| /** | ||
| * single-SPA可选生命周期钩子,仅使用 loadMicroApp 方式加载微应用时生效 | ||
| */ | ||
| return function () { | ||
| var _appRef$current; | ||
| var update = function update(props) { | ||
| var _container$firstEleme; | ||
| console.log('unmount startAppName', startAppName); | ||
| (_appRef$current = appRef.current) == null ? void 0 : _appRef$current.safeUnmount(); | ||
| qiankun.removeGlobalUncaughtErrorHandler(errorHandler); | ||
| }; | ||
| }, [mfAppConfig, delayLoad]); | ||
| return /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP | ||
| }, (delayLoad || loading) && RenderLoading ? /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_SPIN | ||
| }, /*#__PURE__*/React__default['default'].createElement(RenderLoading, { | ||
| loading: loading | ||
| })) : null, error ? /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_ERROR | ||
| }, RenderError ? /*#__PURE__*/React__default['default'].createElement(RenderError, { | ||
| message: errorMsg, | ||
| description: errorDesc | ||
| }) : [/*#__PURE__*/React__default['default'].createElement("span", { | ||
| style: STYLE_APP_ERROR_MSG | ||
| }, errorMsg), /*#__PURE__*/React__default['default'].createElement("span", null, errorDesc)]) : null, /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_CONTAINER, | ||
| ref: ref | ||
| })); | ||
| } // 初始化 state | ||
| var packageName = props.packageName, | ||
| targetDomId = props.targetDomId, | ||
| container = props.container, | ||
| startAppName = props.startAppName, | ||
| restoreState = props.restoreState, | ||
| params = props.params, | ||
| callbacks = props.callbacks, | ||
| Update = props.render; | ||
| console.log("[" + packageName + "] app update. startAppName:", startAppName); | ||
| var element = (container == null ? void 0 : (_container$firstEleme = container.firstElementChild) == null ? void 0 : _container$firstEleme.querySelector("#" + targetDomId)) || document.getElementById(targetDomId); | ||
| ReactDOM__default['default'].render( /*#__PURE__*/React__default['default'].createElement(Update, { | ||
| startAppName: startAppName, | ||
| initData: restoreState, | ||
| params: params, | ||
| callbacks: callbacks | ||
| }), element); | ||
| }; | ||
| var actions = qiankun.initGlobalState({ | ||
| // 所有app资源加载状态 | ||
| hasAppLoading: false, | ||
| // 第一个app挂载完成状态 | ||
| firstMounted: false | ||
| }); | ||
| /** | ||
| * 单实例场景,单实例指的是同一时间只会渲染一个微应用 | ||
| var lifecycle = /*#__PURE__*/Object.freeze({ | ||
| __proto__: null, | ||
| bootstrap: bootstrap, | ||
| mount: mount, | ||
| unmount: unmount, | ||
| update: update | ||
| }); | ||
| */ | ||
| exports.lifecycle = lifecycle; | ||
| exports.mfApp = mfApp; | ||
| function SingularMfApp(props) { | ||
| // 当前app加载状态 | ||
| var _useState5 = React.useState(true), | ||
| delayLoad = _useState5[0], | ||
| setDelayLoad = _useState5[1]; | ||
| Object.defineProperty(exports, '__esModule', { value: true }); | ||
| React.useEffect(function () { | ||
| // 第二个参数为true时,调用该函数就马上执行回调,此时state === prev,可进行初始化。 | ||
| actions.onGlobalStateChange(function (state, prev) { | ||
| if (state === prev) { | ||
| // 初始化 | ||
| if (!state.firstMounted) { | ||
| // 第一个app未挂载,则监听微应用生命周期 | ||
| qiankun.runAfterFirstMounted(function () { | ||
| actions.setGlobalState({ | ||
| hasAppLoading: false, | ||
| firstMounted: true | ||
| }); | ||
| }); // 无app在加载,当前app进入加载状态 | ||
| if (!state.hasAppLoading) { | ||
| actions.setGlobalState({ | ||
| hasAppLoading: true | ||
| }); | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // app资源加载完成时,其他app能加载资源缓存,delayLoad为false | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // onChange时 | ||
| if (state.firstMounted || !state.hasAppLoading) { | ||
| setDelayLoad(false); | ||
| } | ||
| } | ||
| }, true); | ||
| return function () { | ||
| actions.offGlobalStateChange(); | ||
| }; | ||
| }); | ||
| var newProps = _extends({}, props, { | ||
| mfAppConfig: _extends({}, props.mfAppConfig, { | ||
| singular: true, | ||
| delayLoad: delayLoad | ||
| }) | ||
| }); | ||
| return MfApp(newProps); | ||
| } | ||
| /** | ||
| * single-SPA生命周期钩子,只会在微应用初始化的时候调用一次,下次微应用重新进入时会直接调用 mount 钩子,不会再重复触发 bootstrap。 | ||
| * 通常我们可以在这里做一些全局变量的初始化,比如不会在 unmount 阶段被销毁的应用级别的缓存等。 | ||
| */ | ||
| var bootstrap = function bootstrap(props) { | ||
| var packageName = props.packageName, | ||
| startAppName = props.startAppName; | ||
| console.log("[" + packageName + "] app bootstraped. startAppName:", startAppName); | ||
| }; | ||
| /** | ||
| * single-SPA生命周期钩子,应用每次进入都会调用 mount 方法,通常我们在这里触发应用的渲染方法 | ||
| */ | ||
| var mount = function mount(props) { | ||
| var packageName = props.packageName, | ||
| targetDomId = props.targetDomId, | ||
| container = props.container, | ||
| startAppName = props.startAppName, | ||
| restoreState = props.restoreState, | ||
| params = props.params, | ||
| callbacks = props.callbacks, | ||
| Root = props.render; | ||
| console.log("[" + packageName + "] app mounted. startAppName:", startAppName, props); | ||
| ReactDOM__default['default'].render( /*#__PURE__*/React__default['default'].createElement(Root, { | ||
| startAppName: startAppName, | ||
| initData: restoreState, | ||
| params: params, | ||
| callbacks: callbacks | ||
| }), container ? container.querySelector("#" + targetDomId) : document.getElementById(targetDomId)); | ||
| }; | ||
| /** | ||
| * single-SPA生命周期钩子,应用每次 切出/卸载 会调用的方法,通常在这里我们会卸载微应用的应用实例 | ||
| */ | ||
| var unmount = function unmount(props) { | ||
| var packageName = props.packageName, | ||
| targetDomId = props.targetDomId, | ||
| container = props.container, | ||
| startAppName = props.startAppName, | ||
| onSaveState = props.onSaveState, | ||
| state = props.state; | ||
| console.log("[" + packageName + "] app unmount. startAppName:", startAppName); | ||
| if (startAppName && state && onSaveState) { | ||
| var _state$get; | ||
| (_state$get = state.get(startAppName)) == null ? void 0 : _state$get.filter(function (value, key) { | ||
| return key.startsWith('AppLoader'); | ||
| }).take(1).forEach(function (value) { | ||
| onSaveState(value.get('data').toJS()); | ||
| }); | ||
| } | ||
| var element = container ? container.querySelector("#" + targetDomId) : document.getElementById(targetDomId); | ||
| element && ReactDOM__default['default'].unmountComponentAtNode(element); | ||
| }; | ||
| /** | ||
| * single-SPA可选生命周期钩子,仅使用 loadMicroApp 方式加载微应用时生效 | ||
| */ | ||
| var update = function update(props) { | ||
| var _container$firstEleme; | ||
| var packageName = props.packageName, | ||
| targetDomId = props.targetDomId, | ||
| container = props.container, | ||
| startAppName = props.startAppName, | ||
| restoreState = props.restoreState, | ||
| params = props.params, | ||
| callbacks = props.callbacks, | ||
| Update = props.render; | ||
| console.log("[" + packageName + "] app update. startAppName:", startAppName); | ||
| var element = (container == null ? void 0 : (_container$firstEleme = container.firstElementChild) == null ? void 0 : _container$firstEleme.querySelector("#" + targetDomId)) || document.getElementById(targetDomId); | ||
| ReactDOM__default['default'].render( /*#__PURE__*/React__default['default'].createElement(Update, { | ||
| startAppName: startAppName, | ||
| initData: restoreState, | ||
| params: params, | ||
| callbacks: callbacks | ||
| }), element); | ||
| }; | ||
| var lifecycle = /*#__PURE__*/Object.freeze({ | ||
| __proto__: null, | ||
| bootstrap: bootstrap, | ||
| mount: mount, | ||
| unmount: unmount, | ||
| update: update | ||
| }); | ||
| exports.MfApp = MfApp; | ||
| exports.SingularMfApp = SingularMfApp; | ||
| exports.lifecycle = lifecycle; | ||
| Object.defineProperty(exports, '__esModule', { value: true }); | ||
| }))); |
+128
-25
| import React, { useState, useRef, useCallback, useEffect } from 'react'; | ||
| import { addGlobalUncaughtErrorHandler, loadMicroApp, removeGlobalUncaughtErrorHandler } from 'qiankun'; | ||
| import { addGlobalUncaughtErrorHandler, loadMicroApp, removeGlobalUncaughtErrorHandler, initGlobalState, runAfterFirstMounted } from 'qiankun'; | ||
| import ReactDOM from 'react-dom'; | ||
| function getDefaultExportFromCjs (x) { | ||
| return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x; | ||
| } | ||
| function createCommonjsModule(fn, basedir, module) { | ||
| return module = { | ||
| path: basedir, | ||
| exports: {}, | ||
| require: function (path, base) { | ||
| return commonjsRequire(path, (base === undefined || base === null) ? module.path : base); | ||
| } | ||
| }, fn(module, module.exports), module.exports; | ||
| } | ||
| function commonjsRequire () { | ||
| throw new Error('Dynamic requires are not currently supported by @rollup/plugin-commonjs'); | ||
| } | ||
| var _extends_1 = createCommonjsModule(function (module) { | ||
| function _extends() { | ||
| module.exports = _extends = Object.assign || function (target) { | ||
| for (var i = 1; i < arguments.length; i++) { | ||
| var source = arguments[i]; | ||
| for (var key in source) { | ||
| if (Object.prototype.hasOwnProperty.call(source, key)) { | ||
| target[key] = source[key]; | ||
| } | ||
| } | ||
| } | ||
| return target; | ||
| }; | ||
| module.exports["default"] = module.exports, module.exports.__esModule = true; | ||
| return _extends.apply(this, arguments); | ||
| } | ||
| module.exports = _extends; | ||
| module.exports["default"] = module.exports, module.exports.__esModule = true; | ||
| }); | ||
| var _extends = /*@__PURE__*/getDefaultExportFromCjs(_extends_1); | ||
| var STYLE_APP = { | ||
@@ -31,3 +75,3 @@ width: '100%', | ||
| }; | ||
| function mfApp(props) { | ||
| function MfApp(props) { | ||
| var mfAppConfig = props.mfAppConfig; | ||
@@ -37,4 +81,4 @@ var name = mfAppConfig.name, | ||
| startAppName = mfAppConfig.startAppName, | ||
| _mfAppConfig$delayLoa = mfAppConfig.delayLoading, | ||
| delayLoading = _mfAppConfig$delayLoa === void 0 ? false : _mfAppConfig$delayLoa, | ||
| _mfAppConfig$delayLoa = mfAppConfig.delayLoad, | ||
| delayLoad = _mfAppConfig$delayLoa === void 0 ? false : _mfAppConfig$delayLoa, | ||
| params = mfAppConfig.params, | ||
@@ -44,6 +88,6 @@ callbacks = mfAppConfig.callbacks, | ||
| restoreState = mfAppConfig.restoreState, | ||
| _mfAppConfig$singular = mfAppConfig.singular, | ||
| singular = _mfAppConfig$singular === void 0 ? true : _mfAppConfig$singular, | ||
| singular = mfAppConfig.singular, | ||
| RenderLoading = mfAppConfig.renderLoading, | ||
| RenderError = mfAppConfig.renderError; | ||
| console.log('mount startAppName', startAppName); | ||
@@ -80,3 +124,3 @@ var _useState = useState(true), | ||
| if (delayLoading) { | ||
| if (delayLoad) { | ||
| return; | ||
@@ -123,16 +167,10 @@ } | ||
| var status = (_appRef$current = appRef.current) == null ? void 0 : _appRef$current.getStatus(); | ||
| if ('MOUNTED' === status) { | ||
| var _appRef$current2; | ||
| (_appRef$current2 = appRef.current) == null ? void 0 : _appRef$current2.unmount(); | ||
| } | ||
| console.log('unmount startAppName', startAppName); | ||
| (_appRef$current = appRef.current) == null ? void 0 : _appRef$current.safeUnmount(); | ||
| removeGlobalUncaughtErrorHandler(errorHandler); | ||
| }; | ||
| }, [mfAppConfig, delayLoading]); | ||
| }, [mfAppConfig, delayLoad]); | ||
| return /*#__PURE__*/React.createElement("div", { | ||
| style: STYLE_APP | ||
| }, (delayLoading || loading) && RenderLoading ? /*#__PURE__*/React.createElement("div", { | ||
| }, (delayLoad || loading) && RenderLoading ? /*#__PURE__*/React.createElement("div", { | ||
| style: STYLE_APP_SPIN | ||
@@ -152,2 +190,65 @@ }, /*#__PURE__*/React.createElement(RenderLoading, { | ||
| })); | ||
| } // 初始化 state | ||
| var actions = initGlobalState({ | ||
| // 所有app资源加载状态 | ||
| hasAppLoading: false, | ||
| // 第一个app挂载完成状态 | ||
| firstMounted: false | ||
| }); | ||
| /** | ||
| * 单实例场景,单实例指的是同一时间只会渲染一个微应用 | ||
| */ | ||
| function SingularMfApp(props) { | ||
| // 当前app加载状态 | ||
| var _useState5 = useState(true), | ||
| delayLoad = _useState5[0], | ||
| setDelayLoad = _useState5[1]; | ||
| useEffect(function () { | ||
| // 第二个参数为true时,调用该函数就马上执行回调,此时state === prev,可进行初始化。 | ||
| actions.onGlobalStateChange(function (state, prev) { | ||
| if (state === prev) { | ||
| // 初始化 | ||
| if (!state.firstMounted) { | ||
| // 第一个app未挂载,则监听微应用生命周期 | ||
| runAfterFirstMounted(function () { | ||
| actions.setGlobalState({ | ||
| hasAppLoading: false, | ||
| firstMounted: true | ||
| }); | ||
| }); // 无app在加载,当前app进入加载状态 | ||
| if (!state.hasAppLoading) { | ||
| actions.setGlobalState({ | ||
| hasAppLoading: true | ||
| }); | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // app资源加载完成时,其他app能加载资源缓存,delayLoad为false | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // onChange时 | ||
| if (state.firstMounted || !state.hasAppLoading) { | ||
| setDelayLoad(false); | ||
| } | ||
| } | ||
| }, true); | ||
| return function () { | ||
| actions.offGlobalStateChange(); | ||
| }; | ||
| }); | ||
| var newProps = _extends({}, props, { | ||
| mfAppConfig: _extends({}, props.mfAppConfig, { | ||
| singular: true, | ||
| delayLoad: delayLoad | ||
| }) | ||
| }); | ||
| return MfApp(newProps); | ||
| } | ||
@@ -177,3 +278,3 @@ | ||
| Root = props.render; | ||
| console.log("[" + packageName + "] app mounted. startAppName:", startAppName); | ||
| console.log("[" + packageName + "] app mounted. startAppName:", startAppName, props); | ||
| ReactDOM.render( /*#__PURE__*/React.createElement(Root, { | ||
@@ -200,3 +301,5 @@ startAppName: startAppName, | ||
| if (startAppName && state && onSaveState) { | ||
| state.get(startAppName).filter(function (value, key) { | ||
| var _state$get; | ||
| (_state$get = state.get(startAppName)) == null ? void 0 : _state$get.filter(function (value, key) { | ||
| return key.startsWith('AppLoader'); | ||
@@ -237,9 +340,9 @@ }).take(1).forEach(function (value) { | ||
| var lifecycle = /*#__PURE__*/Object.freeze({ | ||
| __proto__: null, | ||
| bootstrap: bootstrap, | ||
| mount: mount, | ||
| unmount: unmount, | ||
| update: update | ||
| __proto__: null, | ||
| bootstrap: bootstrap, | ||
| mount: mount, | ||
| unmount: unmount, | ||
| update: update | ||
| }); | ||
| export { lifecycle, mfApp }; | ||
| export { MfApp, SingularMfApp, lifecycle }; |
+128
-24
@@ -14,2 +14,46 @@ 'use strict'; | ||
| function getDefaultExportFromCjs (x) { | ||
| return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x; | ||
| } | ||
| function createCommonjsModule(fn, basedir, module) { | ||
| return module = { | ||
| path: basedir, | ||
| exports: {}, | ||
| require: function (path, base) { | ||
| return commonjsRequire(path, (base === undefined || base === null) ? module.path : base); | ||
| } | ||
| }, fn(module, module.exports), module.exports; | ||
| } | ||
| function commonjsRequire () { | ||
| throw new Error('Dynamic requires are not currently supported by @rollup/plugin-commonjs'); | ||
| } | ||
| var _extends_1 = createCommonjsModule(function (module) { | ||
| function _extends() { | ||
| module.exports = _extends = Object.assign || function (target) { | ||
| for (var i = 1; i < arguments.length; i++) { | ||
| var source = arguments[i]; | ||
| for (var key in source) { | ||
| if (Object.prototype.hasOwnProperty.call(source, key)) { | ||
| target[key] = source[key]; | ||
| } | ||
| } | ||
| } | ||
| return target; | ||
| }; | ||
| module.exports["default"] = module.exports, module.exports.__esModule = true; | ||
| return _extends.apply(this, arguments); | ||
| } | ||
| module.exports = _extends; | ||
| module.exports["default"] = module.exports, module.exports.__esModule = true; | ||
| }); | ||
| var _extends = /*@__PURE__*/getDefaultExportFromCjs(_extends_1); | ||
| var STYLE_APP = { | ||
@@ -41,3 +85,3 @@ width: '100%', | ||
| }; | ||
| function mfApp(props) { | ||
| function MfApp(props) { | ||
| var mfAppConfig = props.mfAppConfig; | ||
@@ -47,4 +91,4 @@ var name = mfAppConfig.name, | ||
| startAppName = mfAppConfig.startAppName, | ||
| _mfAppConfig$delayLoa = mfAppConfig.delayLoading, | ||
| delayLoading = _mfAppConfig$delayLoa === void 0 ? false : _mfAppConfig$delayLoa, | ||
| _mfAppConfig$delayLoa = mfAppConfig.delayLoad, | ||
| delayLoad = _mfAppConfig$delayLoa === void 0 ? false : _mfAppConfig$delayLoa, | ||
| params = mfAppConfig.params, | ||
@@ -54,6 +98,6 @@ callbacks = mfAppConfig.callbacks, | ||
| restoreState = mfAppConfig.restoreState, | ||
| _mfAppConfig$singular = mfAppConfig.singular, | ||
| singular = _mfAppConfig$singular === void 0 ? true : _mfAppConfig$singular, | ||
| singular = mfAppConfig.singular, | ||
| RenderLoading = mfAppConfig.renderLoading, | ||
| RenderError = mfAppConfig.renderError; | ||
| console.log('mount startAppName', startAppName); | ||
@@ -90,3 +134,3 @@ var _useState = React.useState(true), | ||
| if (delayLoading) { | ||
| if (delayLoad) { | ||
| return; | ||
@@ -133,16 +177,10 @@ } | ||
| var status = (_appRef$current = appRef.current) == null ? void 0 : _appRef$current.getStatus(); | ||
| if ('MOUNTED' === status) { | ||
| var _appRef$current2; | ||
| (_appRef$current2 = appRef.current) == null ? void 0 : _appRef$current2.unmount(); | ||
| } | ||
| console.log('unmount startAppName', startAppName); | ||
| (_appRef$current = appRef.current) == null ? void 0 : _appRef$current.safeUnmount(); | ||
| qiankun.removeGlobalUncaughtErrorHandler(errorHandler); | ||
| }; | ||
| }, [mfAppConfig, delayLoading]); | ||
| }, [mfAppConfig, delayLoad]); | ||
| return /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP | ||
| }, (delayLoading || loading) && RenderLoading ? /*#__PURE__*/React__default['default'].createElement("div", { | ||
| }, (delayLoad || loading) && RenderLoading ? /*#__PURE__*/React__default['default'].createElement("div", { | ||
| style: STYLE_APP_SPIN | ||
@@ -162,2 +200,65 @@ }, /*#__PURE__*/React__default['default'].createElement(RenderLoading, { | ||
| })); | ||
| } // 初始化 state | ||
| var actions = qiankun.initGlobalState({ | ||
| // 所有app资源加载状态 | ||
| hasAppLoading: false, | ||
| // 第一个app挂载完成状态 | ||
| firstMounted: false | ||
| }); | ||
| /** | ||
| * 单实例场景,单实例指的是同一时间只会渲染一个微应用 | ||
| */ | ||
| function SingularMfApp(props) { | ||
| // 当前app加载状态 | ||
| var _useState5 = React.useState(true), | ||
| delayLoad = _useState5[0], | ||
| setDelayLoad = _useState5[1]; | ||
| React.useEffect(function () { | ||
| // 第二个参数为true时,调用该函数就马上执行回调,此时state === prev,可进行初始化。 | ||
| actions.onGlobalStateChange(function (state, prev) { | ||
| if (state === prev) { | ||
| // 初始化 | ||
| if (!state.firstMounted) { | ||
| // 第一个app未挂载,则监听微应用生命周期 | ||
| qiankun.runAfterFirstMounted(function () { | ||
| actions.setGlobalState({ | ||
| hasAppLoading: false, | ||
| firstMounted: true | ||
| }); | ||
| }); // 无app在加载,当前app进入加载状态 | ||
| if (!state.hasAppLoading) { | ||
| actions.setGlobalState({ | ||
| hasAppLoading: true | ||
| }); | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // app资源加载完成时,其他app能加载资源缓存,delayLoad为false | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // onChange时 | ||
| if (state.firstMounted || !state.hasAppLoading) { | ||
| setDelayLoad(false); | ||
| } | ||
| } | ||
| }, true); | ||
| return function () { | ||
| actions.offGlobalStateChange(); | ||
| }; | ||
| }); | ||
| var newProps = _extends({}, props, { | ||
| mfAppConfig: _extends({}, props.mfAppConfig, { | ||
| singular: true, | ||
| delayLoad: delayLoad | ||
| }) | ||
| }); | ||
| return MfApp(newProps); | ||
| } | ||
@@ -187,3 +288,3 @@ | ||
| Root = props.render; | ||
| console.log("[" + packageName + "] app mounted. startAppName:", startAppName); | ||
| console.log("[" + packageName + "] app mounted. startAppName:", startAppName, props); | ||
| ReactDOM__default['default'].render( /*#__PURE__*/React__default['default'].createElement(Root, { | ||
@@ -210,3 +311,5 @@ startAppName: startAppName, | ||
| if (startAppName && state && onSaveState) { | ||
| state.get(startAppName).filter(function (value, key) { | ||
| var _state$get; | ||
| (_state$get = state.get(startAppName)) == null ? void 0 : _state$get.filter(function (value, key) { | ||
| return key.startsWith('AppLoader'); | ||
@@ -247,10 +350,11 @@ }).take(1).forEach(function (value) { | ||
| var lifecycle = /*#__PURE__*/Object.freeze({ | ||
| __proto__: null, | ||
| bootstrap: bootstrap, | ||
| mount: mount, | ||
| unmount: unmount, | ||
| update: update | ||
| __proto__: null, | ||
| bootstrap: bootstrap, | ||
| mount: mount, | ||
| unmount: unmount, | ||
| update: update | ||
| }); | ||
| exports.MfApp = MfApp; | ||
| exports.SingularMfApp = SingularMfApp; | ||
| exports.lifecycle = lifecycle; | ||
| exports.mfApp = mfApp; |
+4
-4
| { | ||
| "name": "@ttk/micro-frontend-react", | ||
| "version": "0.0.3", | ||
| "version": "0.0.4", | ||
| "description": "ttk微前端react", | ||
@@ -15,3 +15,3 @@ "main": "./lib/index.js", | ||
| "test": "echo \"Error: no test specified\" && exit 1", | ||
| "build": "rollup -c" | ||
| "build": "rollup -c && cp -R es/index.js /Users/lztccol/FxProject/gitlab/src/ttk/website/node_modules/@ttk/micro-frontend-react/es" | ||
| }, | ||
@@ -26,3 +26,3 @@ "keywords": [ | ||
| "peerDependencies": { | ||
| "qiankun": "^2.4.2", | ||
| "@ttk/micro-frontend-qiankun": "^0.0.1", | ||
| "react": "^16.13.1", | ||
@@ -60,3 +60,3 @@ "react-dom": "^16.13.1", | ||
| "postcss": "^8.2.0", | ||
| "qiankun": "^2.4.2", | ||
| "@ttk/micro-frontend-qiankun": "^0.0.1", | ||
| "react": "^16.13.1", | ||
@@ -63,0 +63,0 @@ "react-dom": "^16.13.1", |
+80
-1
@@ -0,6 +1,85 @@ | ||
| # @ttk/micro-frontend-react | ||
| 提供应用qiankun微前端的react组件及相关生命周期API给TTK工程使用的依赖库 | ||
| ## 1.安装 | ||
| ``` | ||
| npm install -s @ttk/micro-frontend-react qiankun | ||
| ``` | ||
| ## License | ||
| 或 | ||
| ``` | ||
| yarn add @ttk/micro-frontend-react qiankun | ||
| ``` | ||
| ## 2.API | ||
| ### 2.1 mfApp | ||
| 主工程加载单例子应用的组件,使用方式: | ||
| #### 2.1.1 ttk json工程 | ||
| * component/index.js引入组件, | ||
| ``` | ||
| export { mfApp as MFApp } from '@ttk/micro-frontend-react' | ||
| ``` | ||
| * app详见本工程ttk-json-demo/ttk-edf-app-micro-frontend | ||
| #### 2.1.2 组件参数 | ||
| * name: 子工程打包时output.library输出名称(一般可取package.json里的name),libraryTarget需要umd | ||
| * entry: 子应用访问url, | ||
| * startAppName:子应用指定的appName | ||
| * params: 父应用传给子应用的参数 | ||
| * callbacks: 父应用传给子应用的回调 | ||
| * restoreState:子应用unmount后,重新mount时,父应用传给子应用用于恢复的state | ||
| * onSaveState:父应用传给子应用的回调onSaveState,子应用unmount时,执行onSaveState,保存state到父应用 | ||
| * renderLoading: 子应用加载过程中显示loading组件,不传不显示 | ||
| * renderError: 子应用显示错误信息的组件,不传使用默认的 | ||
| ### 2.2 lifecycle | ||
| 提供给@ttk/react框架(v4版本),作为微前端子应用工程的生命周期 | ||
| ``` | ||
| import { lifecycle } from '@ttk/micro-frontend-react'; | ||
| import { config as appLoaderConfig, start, render } from '@ttk/app-loader' | ||
| import { targetDomId, startAppName } from './constant' | ||
| import pack from '../package.json'; | ||
| const { name: packageName } = pack; | ||
| /** | ||
| * single-SPA生命周期钩子,只会在微应用初始化的时候调用一次,下次微应用重新进入时会直接调用 mount 钩子,不会再重复触发 bootstrap。 | ||
| * 通常我们可以在这里做一些全局变量的初始化,比如不会在 unmount 阶段被销毁的应用级别的缓存等。 | ||
| */ | ||
| export async function bootstrap(props) { | ||
| lifecycle.bootstrap(Object.assign({ targetDomId, packageName, startAppName }, props)); | ||
| let { apps, init } = await import(/* webpackPreload: true */ './apps/index'); | ||
| // appLoader配置 | ||
| await appLoaderConfig(init({ apps })); | ||
| } | ||
| /** | ||
| * single-SPA生命周期钩子,应用每次进入都会调用 mount 方法,通常我们在这里触发应用的渲染方法 | ||
| */ | ||
| export async function mount(props = {}) { | ||
| lifecycle.mount(Object.assign({ targetDomId, packageName, startAppName , render: start }, props)) | ||
| } | ||
| /** | ||
| * single-SPA生命周期钩子,应用每次 切出/卸载 会调用的方法,通常在这里我们会卸载微应用的应用实例 | ||
| */ | ||
| export async function unmount(props) { | ||
| lifecycle.unmount(Object.assign({ targetDomId, packageName, startAppName , state: window.reduxStore.getState() }, props)); | ||
| } | ||
| /** | ||
| * single-SPA可选生命周期钩子,仅使用 loadMicroApp 方式加载微应用时生效 | ||
| */ | ||
| export async function update(props) { | ||
| lifecycle.update(Object.assign({ targetDomId, packageName, startAppName , render }, props)); | ||
| } | ||
| ``` | ||
| * targetDomId为加载子应用容器元素的id,例如,应用容器元素为\<div id="app">\</div>,targetDomId为app | ||
| * startAppName为子应用指定的appName | ||
| * @ttk/app-loader的start, render分别为初始mount和update更新时的组件 | ||
| * unmount生命周期中的参数state,传入全局state,用于获取startAppName的state,传给主工程进行保存 | ||
| ## 3.License | ||
| MIT License | ||
@@ -7,0 +86,0 @@ |
+57
-11
| import React, { useState, useEffect, useRef, useCallback } from 'react' | ||
| import { MicroApp, loadMicroApp, addGlobalUncaughtErrorHandler, removeGlobalUncaughtErrorHandler } from 'qiankun'; | ||
| import { MicroApp, loadMicroApp, addGlobalUncaughtErrorHandler, removeGlobalUncaughtErrorHandler, runAfterFirstMounted, initGlobalState, MicroAppStateActions } from '@ttk/micro-frontend-qiankun'; | ||
@@ -21,3 +21,3 @@ const STYLE_APP = { width: '100%', height: '100%', overflow: 'hidden' }; | ||
| startAppName: string, | ||
| delayLoading: boolean, | ||
| delayLoad: boolean, | ||
| params: any, | ||
@@ -36,5 +36,5 @@ callbacks: any, | ||
| export function mfApp(props: MfAppProps) { | ||
| export function MfApp(props: MfAppProps) { | ||
| let { mfAppConfig } = props; | ||
| let { name, entry, startAppName, delayLoading = false, params, callbacks, onSaveState, restoreState, singular = true, renderLoading: RenderLoading, renderError: RenderError } = mfAppConfig; | ||
| let { name, entry, startAppName, delayLoad = false, params, callbacks, onSaveState, restoreState, singular, renderLoading: RenderLoading, renderError: RenderError } = mfAppConfig; | ||
@@ -61,3 +61,3 @@ const [loading, setLoading] = useState(true); | ||
| } | ||
| if (delayLoading) { | ||
| if (delayLoad) { | ||
| return; | ||
@@ -87,13 +87,10 @@ } | ||
| return () => { | ||
| const status = appRef.current?.getStatus(); | ||
| if ('MOUNTED' === status) { | ||
| appRef.current?.unmount(); | ||
| } | ||
| appRef.current?.safeUnmount(); | ||
| removeGlobalUncaughtErrorHandler(errorHandler) | ||
| } | ||
| }, [mfAppConfig, delayLoading]) | ||
| }, [mfAppConfig, delayLoad]) | ||
| return ( | ||
| <div style={STYLE_APP}> | ||
| {(delayLoading || loading) && RenderLoading ? | ||
| {(delayLoad || loading) && RenderLoading ? | ||
| <div style={STYLE_APP_SPIN}> | ||
@@ -113,1 +110,50 @@ <RenderLoading loading={loading} /> | ||
| } | ||
| // 初始化 state | ||
| const actions: MicroAppStateActions = initGlobalState({ | ||
| // 所有app资源加载状态 | ||
| hasAppLoading: false, | ||
| // 第一个app挂载完成状态 | ||
| firstMounted: false, | ||
| }); | ||
| /** | ||
| * 单实例场景,单实例指的是同一时间只会渲染一个微应用 | ||
| */ | ||
| export function SingularMfApp(props: MfAppProps) { | ||
| // 当前app加载状态 | ||
| const [delayLoad, setDelayLoad] = useState(true) | ||
| useEffect(() => { | ||
| // 第二个参数为true时,调用该函数就马上执行回调,此时state === prev,可进行初始化。 | ||
| actions.onGlobalStateChange((state, prev) => { | ||
| if (state === prev) { | ||
| // 初始化 | ||
| if (!state.firstMounted) { | ||
| // 第一个app未挂载,则监听微应用生命周期 | ||
| runAfterFirstMounted(() => { | ||
| actions.setGlobalState({ hasAppLoading: false, firstMounted: true }) | ||
| }); | ||
| // 无app在加载,当前app进入加载状态 | ||
| if (!state.hasAppLoading) { | ||
| actions.setGlobalState({ hasAppLoading: true }) | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // app资源加载完成时,其他app能加载资源缓存,delayLoad为false | ||
| setDelayLoad(false); | ||
| } | ||
| } else { | ||
| // onChange时 | ||
| if (state.firstMounted || !state.hasAppLoading) { | ||
| setDelayLoad(false) | ||
| } | ||
| } | ||
| }, true); | ||
| return function () { | ||
| actions.offGlobalStateChange(); | ||
| } | ||
| }); | ||
| const newProps = { ...props, mfAppConfig: { ...props.mfAppConfig, singular: true, delayLoad } }; | ||
| return MfApp(newProps); | ||
| } |
@@ -45,3 +45,3 @@ import React, { ReactElement } from "react"; | ||
| if (startAppName && state && onSaveState) { | ||
| state.get(startAppName).filter((value: any, key: string) => key.startsWith('AppLoader')) | ||
| state.get(startAppName)?.filter((value: any, key: string) => key.startsWith('AppLoader')) | ||
| .take(1) | ||
@@ -48,0 +48,0 @@ .forEach((value: any) => { |
56521
31.58%1128
38.07%106
292.59%