UNPKG

@ovine/core

Version:

Build flexible admin system with json.

181 lines (180 loc) 6.46 kB
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; /* eslint-disable max-classes-per-file */ import { createBrowserHistory } from 'history'; import { defaultsDeep, get, isFunction, merge, set } from 'lodash'; import { defaultEnvMode, rootRoute, storage, publicUrl } from "../constants"; import { Request } from "../utils/request"; import { setGlobal } from "../utils/store"; import { AppTheme } from "./theme"; let source = {}; const initConfig = { // TODO: 处理某些请夸下的多实例切换,而不是全局唯一实例 request: new Request(), theme: new AppTheme(), styled: { globalStyle: '', }, env: { default: { mode: defaultEnvMode, domains: { api: 'http://site-api.com', }, }, }, constants: { routePrefix: publicUrl.startsWith('/') ? publicUrl : rootRoute, toastDuration: 1200, rootLimitFlag: '*', enableBackTop: false, notFound: { route: '/404', pagePath: '', }, }, entry: [ { type: 'route', path: rootRoute, }, ], amis: { affixOffsetTop: 50, }, // 异步数据容器 asyncPage: { schema: {}, preset: {}, mock: {}, // {path: mockSource} // 页面mock来源 }, hook: {}, }; function checkAppGetter(key, value) { switch (key) { case 'theme': if (!(value instanceof AppTheme)) { throw new Error('You should register theme with AppTheme instance.'); } break; case 'requestFunc': if (!(value instanceof Request)) { throw new Error('You should register request with Request instance.'); } break; default: } } class AppProxy { constructor() { const that = this; const proxy = new Proxy(that, { get(_, key) { const value = key in that ? that[key] : get(source, key) || get(initConfig, key); return value; }, }); return proxy; } } // TODO: 允许 APP 多次重复创建 class App extends AppProxy { constructor() { super(...arguments); this.routePrefix = rootRoute; } create(appConfig) { var _a, _b, _c; return __awaiter(this, void 0, void 0, function* () { this.initState(); const prevBaseUrl = get(source, 'constants.routePrefix') || rootRoute; // 等待 beforeCreate hook执行完成 if ((_a = appConfig.hook) === null || _a === void 0 ? void 0 : _a.beforeCreate) { yield appConfig.hook.beforeCreate.bind(this, this, appConfig)(); } // 合并参数 source = merge(initConfig, appConfig); this.routePrefix = this.getBaseUrl((_b = appConfig.constants) === null || _b === void 0 ? void 0 : _b.routePrefix); set(source, 'constants.routePrefix', this.routePrefix); if (this.checkBaseUrl(prevBaseUrl, this.routePrefix)) { this.createRouterHistory(); } if (source.env) { this.setEnv(source.env); } if (source.request) { this.setRequest(source.request); } // 等待 afterCreated hook执行完成 if ((_c = source.hook) === null || _c === void 0 ? void 0 : _c.afterCreated) { yield source.hook.afterCreated.bind(this, this, source)(); } }); } createRouterHistory() { this.routerHistory = createBrowserHistory(this.routePrefix === rootRoute ? undefined : { basename: this.routePrefix.slice(0, -1), }); } initState() { // 非 热更新模式下,每次创建,将清除原有数据 if (!process.env.HOT) { source = {}; this.routePrefix = rootRoute; this.routerHistory = undefined; } } getBaseUrl(urlGen) { if (isFunction(urlGen)) { return urlGen() || rootRoute; } return typeof urlGen === 'string' ? urlGen : rootRoute; } checkBaseUrl(prevBaseUrl, routePrefix) { if (typeof routePrefix !== 'string' || routePrefix.substr(-1) !== rootRoute || routePrefix[0] !== rootRoute) { throw new Error(`routePrefix: "${routePrefix}" is not allowed. The "routePrefix" must be string startWith "/" and endWith "/". eg: "/subPath/"`); } if (this.routerHistory && routePrefix !== prevBaseUrl) { window.location.href = routePrefix; } return !this.routerHistory; } setEnv(value) { const mode = process.env.ENV || defaultEnvMode; const isMock = process.env.MOCK; const isRelease = process.env.NODE_ENV === 'production' && get(value, `${mode}.isProd`); const env = defaultsDeep({ isMock, mode, }, value[mode], { isRelease, }, value.default, initConfig.env.default); set(source, 'env', env); } setRequest(requestIns) { const initEnv = initConfig.env.default; checkAppGetter('requestFunc', requestIns); // 设置 request 环境变量 const env = source.env || initEnv; requestIns.setConfig({ isMock: env.isMock && !env.isRelease, domains: env.domains, }); const requestHandle = requestIns.request.bind(requestIns); requestHandle.getUrlByOption = requestIns.getUrlByOption.bind(requestIns); set(source, 'request', requestHandle); } } export const app = new App(); setGlobal(storage.appInstance, app);