feat(editor,core,schema): 组件高级配置支持配置数据源方法

This commit is contained in:
roymondchen 2024-02-28 14:33:57 +08:00
parent 0d471a96ed
commit 074d76456b
4 changed files with 90 additions and 20 deletions

View File

@ -18,10 +18,17 @@
import { EventEmitter } from 'events';
import { isEmpty } from 'lodash-es';
import type { DeprecatedEventConfig, EventConfig, MComponent, MContainer, MPage, MPageFragment } from '@tmagic/schema';
import { HookType } from '@tmagic/schema';
import { DataSource } from '@tmagic/data-source';
import type {
AppCore,
DeprecatedEventConfig,
EventConfig,
MComponent,
MContainer,
MPage,
MPageFragment,
} from '@tmagic/schema';
import { HookCodeType, HookType } from '@tmagic/schema';
import type App from './App';
import type Page from './Page';
@ -78,7 +85,7 @@ class Node extends EventEmitter {
});
this.instance = instance;
await this.runCodeBlock('created');
await this.runHookCode('created');
});
this.once('mounted', async (instance: any) => {
@ -90,24 +97,51 @@ class Node extends EventEmitter {
this.app.compActionHandler(eventConfig.eventConfig, eventConfig.fromCpt, eventConfig.args);
}
await this.runCodeBlock('mounted');
await this.runHookCode('mounted');
});
}
private async runCodeBlock(hook: string) {
private async runHookCode(hook: string) {
if (typeof this.data[hook] === 'function') {
// 兼容旧的数据格式
await this.data[hook](this);
return;
}
if (this.data[hook]?.hookType !== HookType.CODE || isEmpty(this.app.codeDsl)) return;
for (const item of this.data[hook].hookData) {
const { codeId, params = {} } = item;
const functionContent = this.app.codeDsl?.[codeId]?.content;
const hookData = this.data[hook] as {
/** 钩子类型 */
hookType: HookType;
hookData: {
/** 函数类型 */
codeType?: HookCodeType;
/** 函数id, 代码块为string, 数据源为[数据源id, 方法名称] */
codeId: string | [string, string];
/** 参数配置 */
params: Record<string, any>;
}[];
};
if (typeof functionContent === 'function') {
await functionContent({ app: this.app, params });
if (hookData?.hookType !== HookType.CODE) return;
for (const item of hookData.hookData) {
const { codeType = HookCodeType.CODE, codeId, params = {} } = item;
let functionContent: ((...args: any[]) => any) | string | undefined;
const functionParams: { app: AppCore; params: Record<string, any>; dataSource?: DataSource } = {
app: this.app,
params,
};
if (codeType === HookCodeType.CODE && typeof codeId === 'string' && this.app.codeDsl?.[codeId]) {
functionContent = this.app.codeDsl[codeId].content;
} else if (codeType === HookCodeType.DATA_SOURCE_METHOD && Array.isArray(codeId) && codeId.length > 1) {
const dataSource = this.app.dataSourceManager?.get(codeId[0]);
functionContent = dataSource?.methods.find((method) => method.name === codeId[1])?.content;
functionParams.dataSource = dataSource;
}
if (functionContent && typeof functionContent === 'function') {
await functionContent(functionParams);
}
}
}

View File

@ -12,7 +12,8 @@ import { isEmpty } from 'lodash-es';
import { TMagicCard } from '@tmagic/design';
import type { FieldProps } from '@tmagic/form';
import { HookType } from '@tmagic/schema';
import { FormState } from '@tmagic/form';
import { HookCodeType, HookType } from '@tmagic/schema';
import type { Services } from '@editor/type';
@ -38,13 +39,40 @@ const codeConfig = computed(() => ({
name: 'hookData',
enableToggleMode: false,
expandAll: true,
titleKey: 'codeId',
title: (mForm: FormState, { model, index }: any) => {
if (model.codeType === HookCodeType.DATA_SOURCE_METHOD) {
if (Array.isArray(model.codeId)) {
const ds = services?.dataSourceService.getDataSourceById(model.codeId[0]);
return `${ds?.title} / ${model.codeId[1]}`;
}
return Array.isArray(model.codeId) ? model.codeId.join('/') : index;
}
return model.codeId || index;
},
items: [
{
type: 'code-select-col',
name: 'codeId',
labelWidth: 0,
disabled: () => !services?.codeBlockService.getEditStatus(),
type: 'row',
items: [
{
type: 'select',
name: 'codeType',
span: 8,
options: [
{ value: HookCodeType.CODE, text: '代码块' },
{ value: HookCodeType.DATA_SOURCE_METHOD, text: '数据源方法' },
],
defaultValue: 'code',
},
{
type: (mForm: FormState, { model }: any) =>
model.codeType === HookCodeType.DATA_SOURCE_METHOD ? 'data-source-method-select' : 'code-select-col',
name: 'codeId',
span: 16,
labelWidth: 0,
disabled: () => !services?.codeBlockService.getEditStatus(),
},
],
},
],
}));

View File

@ -17,6 +17,7 @@
<CodeParams
v-if="paramsConfig.length"
name="params"
:key="model[name]"
:model="model"
:size="size"
:params-config="paramsConfig"
@ -33,7 +34,7 @@
</div>
</template>
<script lang="ts" setup name="">
<script lang="ts" setup>
import { computed, inject, ref, watch } from 'vue';
import { Edit, View } from '@element-plus/icons-vue';
import { isEmpty, map } from 'lodash-es';

View File

@ -205,6 +205,13 @@ export enum HookType {
CODE = 'code',
}
export enum HookCodeType {
/** 代码块 */
CODE = 'code',
/** 数据源方法 */
DATA_SOURCE_METHOD = 'data-source-method',
}
export interface DataSchema {
type?: 'null' | 'boolean' | 'object' | 'array' | 'number' | 'string' | 'any';
/** 键名 */