refactor: runtime

This commit is contained in:
wuyue.xht 2020-03-31 18:58:55 +08:00
parent 770a1b6c34
commit 768e71444e
10 changed files with 90 additions and 46 deletions

View File

@ -1,20 +1,20 @@
import { contribution, run } from '@ali/lowcode-runtime'; import { app } from '@ali/lowcode-runtime';
import Renderer from '@ali/lowcode-react-renderer'; import Renderer from '@ali/lowcode-react-renderer';
import FusionLoading from './plugins/loading/fusion'; import FusionLoading from './plugins/loading/fusion';
import BasicLayout from './layouts/BasicLayout'; import BasicLayout from './layouts/BasicLayout';
import Preview from './plugins/provider'; import Preview from './plugins/provider';
// 注册渲染模块 // 注册渲染模块
contribution.registerRenderer(Renderer); app.registerRenderer(Renderer);
// 注册布局组件,可注册多个 // 注册布局组件,可注册多个
contribution.registerLayout('BasicLayout', BasicLayout); app.registerLayout('BasicLayout', BasicLayout);
// 注册页面 Loading // 注册页面 Loading
contribution.registerLoading(FusionLoading); app.registerLoading(FusionLoading);
// appKey应用唯一标识 // appKey应用唯一标识
contribution.registerProvider(new Preview({ appKey: 'lowcode_demo' })); app.registerProvider(Preview);
// 启动应用 // 启动应用
run(); app.run();

View File

@ -8,7 +8,7 @@ import utils from '../config/utils';
// 定制加载应用配置的逻辑 // 定制加载应用配置的逻辑
export default class Preview extends ReactProvider { export default class Preview extends ReactProvider {
// 定制获取、处理应用配置(组件、插件、路由模式、布局等)的逻辑 // 定制获取、处理应用配置(组件、插件、路由模式、布局等)的逻辑
async getAppData(appkey: string): Promise<any> { async getAppData(): Promise<any> {
const { history, layout, containerId } = appConfig; const { history, layout, containerId } = appConfig;
const appSchemaStr: any = localStorage.getItem('lce-dev-store'); const appSchemaStr: any = localStorage.getItem('lce-dev-store');
if (!appSchemaStr) { if (!appSchemaStr) {

View File

@ -1,6 +1,6 @@
{ {
"name": "@ali/lowcode-runtime", "name": "@ali/lowcode-runtime",
"version": "0.8.5", "version": "0.8.6",
"description": "Runtime for Ali lowCode engine", "description": "Runtime for Ali lowCode engine",
"files": [ "files": [
"es", "es",

View File

@ -1,7 +1,7 @@
import { ReactType } from 'react'; import { ReactType } from 'react';
import { IProvider } from './provider/base'; import Provider from './provider';
class Contribution { export default class Container {
private renderer: ReactType | null = null; private renderer: ReactType | null = null;
private layouts: { [key: string]: ReactType } = {}; private layouts: { [key: string]: ReactType } = {};
private loading: ReactType | null = null; private loading: ReactType | null = null;
@ -25,8 +25,13 @@ class Contribution {
this.loading = component; this.loading = component;
} }
registerProvider(provider: IProvider) { registerProvider(CustomProvider: any) {
this.provider = provider; if (Provider.isPrototypeOf(CustomProvider)) {
this.provider = new CustomProvider();
} else {
const identifier = (CustomProvider && CustomProvider.name) || 'registered Provider';
throw new Error(`${identifier} is not a child class of Provider`);
}
} }
getLayout(componentName: string) { getLayout(componentName: string) {
@ -48,5 +53,3 @@ class Contribution {
return this.provider; return this.provider;
} }
} }
export default new Contribution();

View File

@ -0,0 +1,49 @@
import { ReactType } from 'react';
import Container from './container';
import run from './run';
class App {
private container: Container;
constructor() {
this.container = new Container();
}
run() {
run();
}
registerRenderer(renderer: ReactType): any {
this.container.registerRenderer(renderer);
}
registerLayout(componentName: string, Layout: ReactType): any {
this.container.registerLayout(componentName, Layout);
}
registerLoading(component: ReactType) {
this.container.registerLoading(component);
}
registerProvider(CustomProvider: any) {
this.container.registerProvider(CustomProvider);
}
getLayout(componentName: string) {
return this.container.getLayout(componentName);
}
getRenderer(): ReactType | null {
return this.container.getRenderer();
}
getLoading(): ReactType | null {
return this.container.getLoading();
}
getProvider() {
return this.container.getProvider();
}
}
export default new App();

View File

@ -38,10 +38,6 @@ interface IAppData {
constants?: IConstants; constants?: IConstants;
} }
interface IOptions {
appKey: string;
}
export interface ComponentProps { export interface ComponentProps {
[key: string]: any; [key: string]: any;
} }
@ -90,22 +86,21 @@ export interface ComponentModel {
dataSource?: DataSource; dataSource?: DataSource;
lifeCycles?: LifeCycles; lifeCycles?: LifeCycles;
methods?: Methods; methods?: Methods;
children?: ComponentModel[]; children?: ComponentModel[] | string[];
condition?: JSExpression | boolean; condition?: JSExpression | boolean;
loop?: string[]; loop?: string[];
loopArgs?: string[]; loopArgs?: string[];
} }
export interface IProvider { // export interface IProvider {
init?(): void; // init?(): void;
getAppData?(appkey: string): Promise<IAppData | undefined>; // getAppData?(appkey: string): Promise<IAppData | undefined>;
getPageData?(pageId: string): Promise<ComponentModel | undefined>; // getPageData?(pageId: string): Promise<ComponentModel | undefined>;
getLazyComponent?(pageId: string, props: any): any; // getLazyComponent?(pageId: string, props: any): any;
createApp?(): void; // createApp?(): void;
} // }
export default class Provider implements IProvider { export default class Provider {
private appKey = '';
private components: IComponents = {}; private components: IComponents = {};
private utils: IUtils = {}; private utils: IUtils = {};
private constants: IConstants = {}; private constants: IConstants = {};
@ -116,16 +111,14 @@ export default class Provider implements IProvider {
private containerId = ''; private containerId = '';
private lazyElementsMap: { [key: string]: any } = {}; private lazyElementsMap: { [key: string]: any } = {};
constructor(options: IOptions) { constructor() {
const { appKey } = options;
this.appKey = appKey;
this.init(); this.init();
} }
async(): Promise<IAppConfig> { async(): Promise<IAppConfig> {
return new Promise(async (resolve, reject) => { return new Promise(async (resolve, reject) => {
try { try {
const appData = await this.getAppData(this.appKey || ''); const appData = await this.getAppData();
if (!appData) { if (!appData) {
return; return;
} }
@ -154,11 +147,11 @@ export default class Provider implements IProvider {
console.log('init'); console.log('init');
} }
async getAppData(appkey: string): Promise<IAppData | undefined> { getAppData(): any {
throw new Error('Method called "getPageData" not implemented.'); throw new Error('Method called "getPageData" not implemented.');
} }
async getPageData(pageId: string): Promise<ComponentModel | undefined> { getPageData(pageId?: string): any {
throw new Error('Method called "getPageData" not implemented.'); throw new Error('Method called "getPageData" not implemented.');
} }

View File

@ -1,7 +1,7 @@
import { createElement, ReactElement } from 'react'; import { createElement, ReactElement } from 'react';
import { Router } from '@ali/recore'; import { Router } from '@ali/recore';
import contribution from '../../contribution'; import app from '../../index';
import Provider from '../base'; import Provider from '..';
import LazyComponent from './lazy-component'; import LazyComponent from './lazy-component';
export default class ReactProvider extends Provider { export default class ReactProvider extends Provider {
@ -52,7 +52,7 @@ export default class ReactProvider extends Provider {
return App; return App;
} }
const { componentName: layoutName, props: layoutProps } = layoutConfig; const { componentName: layoutName, props: layoutProps } = layoutConfig;
const Layout = contribution.getLayout(layoutName); const Layout = app.getLayout(layoutName);
if (Layout) { if (Layout) {
App = (props: any) => createElement(Layout, layoutProps, RouterView({ props })); App = (props: any) => createElement(Layout, layoutProps, RouterView({ props }));
} else { } else {

View File

@ -1,5 +1,5 @@
import { Component, createElement } from 'react'; import { Component, createElement } from 'react';
import contribution from '../../contribution'; import app from '../../index';
interface IProps { interface IProps {
getPageData: () => any; getPageData: () => any;
@ -29,8 +29,8 @@ export default class LazyComponent extends Component<IProps, IState> {
render() { render() {
const { getPageData, ...restProps } = this.props; const { getPageData, ...restProps } = this.props;
const { schema } = this.state; const { schema } = this.state;
const Renderer = contribution.getRenderer(); const Renderer = app.getRenderer();
const Loading = contribution.getLoading(); const Loading = app.getLoading();
if (!Renderer || !schema) { if (!Renderer || !schema) {
if (!Loading) { if (!Loading) {
return null; return null;

View File

@ -1,7 +1,7 @@
import { ReactType } from 'react'; import { ReactType } from 'react';
import { runApp } from '@ali/recore'; import { runApp } from '@ali/recore';
import { HashHistoryBuildOptions, BrowserHistoryBuildOptions, MemoryHistoryBuildOptions } from '@recore/history'; import { HashHistoryBuildOptions, BrowserHistoryBuildOptions, MemoryHistoryBuildOptions } from '@recore/history';
import contribution from './contribution'; import app from './index';
export type HistoryOptions = { export type HistoryOptions = {
mode?: HistoryMode; mode?: HistoryMode;
@ -47,7 +47,7 @@ function transformConfig(config: IAppConfig | (() => IAppConfig)): IRecoreAppCon
} }
export default function run(config?: IAppConfig | (() => IAppConfig)) { export default function run(config?: IAppConfig | (() => IAppConfig)) {
const provider = contribution.getProvider(); const provider = app.getProvider();
if (config) { if (config) {
config = transformConfig(config); config = transformConfig(config);
const App = provider.createApp(); const App = provider.createApp();

View File

@ -1,8 +1,7 @@
import { navigator, Router } from '@ali/recore'; import { navigator, Router } from '@ali/recore';
import run from './core/run'; import Provider from './core/provider';
import contribution from './core/contribution';
import Provider from './core/provider/base';
import ReactProvider from './core/provider/react'; import ReactProvider from './core/provider/react';
import app from './core';
import * as Utils from './utils'; import * as Utils from './utils';
export { run, Router, contribution, Provider, ReactProvider, navigator, Utils }; export { app, Router, Provider, ReactProvider, navigator, Utils };