元数据结构
通用业务开发的第一步是定义元数据结构,元数据结构是用于描述通用业务的数据结构。
新建通用业务
选中通用页面节点,在右侧菜单中点击"添加通用业务"按钮,并根据实际业务场景为其命名。
创建完成后,对应通用业务下会出现元数据、模版、页面三层结构。
其含义如下:
元数据:描述通用业务的数据结构,类似于TypeScript
的interface
定义。
interface IMeta {
form_query: {
items: KaceFormItems[];
}
table: {
items: Record<string, any>[];
}
form_dialog: {
items: KaceFormItems[];
}
api: {
query: string;
update: string;
delete: string;
add: string;
}
}
interface IMeta {
form_query: {
items: KaceFormItems[];
}
table: {
items: Record<string, any>[];
}
form_dialog: {
items: KaceFormItems[];
}
api: {
query: string;
update: string;
delete: string;
add: string;
}
}
模版:通用业务的页面模版,包含样式、变量、事件、方法、渲染组件,是一份低码的元数据结构。
{
"componentName": "kui-b-page",
"id": 100157,
"label": "页面",
"props": {
"compName": "页面",
"style": {}
},
"events": {},
"alias": "CURD",
"componentsTree": [],
"css": "",
"lifeCycles": {
"onMounted": {
"id": "methodlr4kidik",
"name": "onMounted",
"value": " function onMounted () {\nreturn;\n}",
"props": [],
"logicList": [
{
"id": "logic_onMounted_1704697007845",
"logicName": "manual",
"props": {
"code": "return;"
}
}
],
"type": "JSFunction",
"localVars": [],
"useScene": "function",
"label": ""
}
},
"state": {
"meta": {
"id": "20be4a33-9805-4699-b56c-b621cb4aead4",
"value": {
"new_property_1": {
"id": "b9fde205-7f7e-4738-8eca-be6d0b6baad7",
"type": "string",
"value": ""
},
"form_query": {
"id": "8b403056-3bd6-4afa-ac8a-2b3fe1d13f4e",
"value": {
"items": {
"id": "45598f80-e21f-4e19-bf68-19f5e801b37e",
"value": [],
"type": "array"
}
},
"type": "object"
},
"table": {
"id": "f06b81c8-084d-4d99-96d7-6df1ca59872d",
"value": {
"items": {
"id": "3969d1dd-cef6-4732-be54-54811212289d",
"value": [],
"type": "array"
}
},
"type": "object"
},
"form_dialog": {
"id": "79970973-6c4b-4702-b1bc-68291a811263",
"value": {
"items": {
"id": "f9c31646-4349-457b-9dd3-2dd7df426aca",
"value": [],
"type": "array"
}
},
"type": "object"
},
"api": {
"id": "f209ad70-f827-40d0-bf44-780ed2ab8721",
"value": {
"query": {
"id": "d57119c5-f9d6-4c7d-9e60-891c27c38be3",
"type": "string",
"value": ""
},
"update": {
"id": "8a9779db-deb1-46a8-beb6-af32e51536dd",
"type": "string",
"value": ""
},
"delete": {
"id": "2fb50f9d-9266-482b-8f8f-a1b1d52a0e73",
"type": "string",
"value": ""
},
"create": {
"id": "8b493982-a10c-4578-81f5-f39c3edb17e0",
"type": "string",
"value": ""
}
},
"type": "object"
}
},
"type": "object"
},
"formModel": {
"id": "046a1e83-5ba3-4b0b-9308-54dc9480a4bf",
"type": "object",
"value": {},
"desc": ""
}
},
"methods": {},
"computed": {},
"emit": {},
"env": "vue3",
"permissions": [],
"watch": [],
"children": [
{
"componentName": "KacePage",
"id": "node_1001571",
"label": "page",
"props": {
"formModel": {
"type": "jsExpression",
"value": "$page.state.formModel",
"$isBind$": true,
"mock": {}
},
"compName": "page",
"slot_topBtn": {
"enable": false,
"slotArgName": ""
},
"slot_otherBtns": {
"enable": false,
"slotArgName": ""
},
"slot_tableBtnsLeft": {
"enable": false,
"slotArgName": ""
},
"slot_toolbarRight": {
"enable": false,
"slotArgName": ""
},
"slot_panel-content": {
"enable": false,
"slotArgName": ""
},
"slot_default": {
"enable": false,
"slotArgName": "scope"
},
"formItems": {
"type": "jsExpression",
"value": "$page.state.meta.form_query.items",
"$isBind$": true,
"mock": ""
},
"columns": {
"type": "jsExpression",
"value": "$page.state.meta.table.items",
"$isBind$": true,
"mock": ""
},
"queryUrl": {
"type": "jsExpression",
"value": "$page.state.meta.api.query",
"$isBind$": true,
"mock": ""
},
"style": {}
},
"events": {},
"condition": {
"v-show": "",
"v-if": ""
},
"ref": ""
}
]
}
{
"componentName": "kui-b-page",
"id": 100157,
"label": "页面",
"props": {
"compName": "页面",
"style": {}
},
"events": {},
"alias": "CURD",
"componentsTree": [],
"css": "",
"lifeCycles": {
"onMounted": {
"id": "methodlr4kidik",
"name": "onMounted",
"value": " function onMounted () {\nreturn;\n}",
"props": [],
"logicList": [
{
"id": "logic_onMounted_1704697007845",
"logicName": "manual",
"props": {
"code": "return;"
}
}
],
"type": "JSFunction",
"localVars": [],
"useScene": "function",
"label": ""
}
},
"state": {
"meta": {
"id": "20be4a33-9805-4699-b56c-b621cb4aead4",
"value": {
"new_property_1": {
"id": "b9fde205-7f7e-4738-8eca-be6d0b6baad7",
"type": "string",
"value": ""
},
"form_query": {
"id": "8b403056-3bd6-4afa-ac8a-2b3fe1d13f4e",
"value": {
"items": {
"id": "45598f80-e21f-4e19-bf68-19f5e801b37e",
"value": [],
"type": "array"
}
},
"type": "object"
},
"table": {
"id": "f06b81c8-084d-4d99-96d7-6df1ca59872d",
"value": {
"items": {
"id": "3969d1dd-cef6-4732-be54-54811212289d",
"value": [],
"type": "array"
}
},
"type": "object"
},
"form_dialog": {
"id": "79970973-6c4b-4702-b1bc-68291a811263",
"value": {
"items": {
"id": "f9c31646-4349-457b-9dd3-2dd7df426aca",
"value": [],
"type": "array"
}
},
"type": "object"
},
"api": {
"id": "f209ad70-f827-40d0-bf44-780ed2ab8721",
"value": {
"query": {
"id": "d57119c5-f9d6-4c7d-9e60-891c27c38be3",
"type": "string",
"value": ""
},
"update": {
"id": "8a9779db-deb1-46a8-beb6-af32e51536dd",
"type": "string",
"value": ""
},
"delete": {
"id": "2fb50f9d-9266-482b-8f8f-a1b1d52a0e73",
"type": "string",
"value": ""
},
"create": {
"id": "8b493982-a10c-4578-81f5-f39c3edb17e0",
"type": "string",
"value": ""
}
},
"type": "object"
}
},
"type": "object"
},
"formModel": {
"id": "046a1e83-5ba3-4b0b-9308-54dc9480a4bf",
"type": "object",
"value": {},
"desc": ""
}
},
"methods": {},
"computed": {},
"emit": {},
"env": "vue3",
"permissions": [],
"watch": [],
"children": [
{
"componentName": "KacePage",
"id": "node_1001571",
"label": "page",
"props": {
"formModel": {
"type": "jsExpression",
"value": "$page.state.formModel",
"$isBind$": true,
"mock": {}
},
"compName": "page",
"slot_topBtn": {
"enable": false,
"slotArgName": ""
},
"slot_otherBtns": {
"enable": false,
"slotArgName": ""
},
"slot_tableBtnsLeft": {
"enable": false,
"slotArgName": ""
},
"slot_toolbarRight": {
"enable": false,
"slotArgName": ""
},
"slot_panel-content": {
"enable": false,
"slotArgName": ""
},
"slot_default": {
"enable": false,
"slotArgName": "scope"
},
"formItems": {
"type": "jsExpression",
"value": "$page.state.meta.form_query.items",
"$isBind$": true,
"mock": ""
},
"columns": {
"type": "jsExpression",
"value": "$page.state.meta.table.items",
"$isBind$": true,
"mock": ""
},
"queryUrl": {
"type": "jsExpression",
"value": "$page.state.meta.api.query",
"$isBind$": true,
"mock": ""
},
"style": {}
},
"events": {},
"condition": {
"v-show": "",
"v-if": ""
},
"ref": ""
}
]
}
页面:描述通用页面具体的页面数据,是一份符合元数据结构定义的JSON数据。
{
"form_query": {
"items": [
{
"__parentType__": "array<kaceFormItems>",
"label": "结算主体",
"prop": "settbody",
"type": "kui-select",
"required": false,
"props": {
"remote": true,
"clearable": true,
"options": [],
"filterable": true,
"labelKey": "settbodyname",
"valueKey": "settbody",
"remoteMethod": {
"type": "jsExpression",
"value": "val => {\n if (val !== \"\") {\n $global.$http.post('macbs/api/' + \"commSettbodyQueryPage\", {\n settbody: val,\n pageSize: 100,\n pageNum: 1\n }).then(res => {\n $page.state.meta.form_query.items.find(val2 => val2.prop === \"settbody\").props.options = res.data;\n });\n }\n }",
"url": "macbs/api/commSettbodyQueryPage"
}
}
}
]
},
"table": {
"pageSize": 20,
"type": "paging",
"items": [
{
"minWidth": 150,
"__parentType__": "array<object>",
"prop": "settbody",
"label": "结算主体"
},
{
"minWidth": 300,
"__parentType__": "array<object>",
"prop": "settbodyname",
"label": "结算主体名"
},
{
"minWidth": 250,
"__parentType__": "array<object>",
"prop": "remark",
"label": "备注"
}
]
},
"form_dialog": {
"items": [
{
"__parentType__": "array<kaceFormItems>",
"label": "结算主体",
"prop": "settbody",
"type": "kui-input",
"required": true,
"props": {
"disabled": false,
"maxlength": 32
}
},
{
"__parentType__": "array<kaceFormItems>",
"label": "结算主体名",
"prop": "settbodyname",
"type": "kui-input",
"required": true
},
{
"__parentType__": "array<kaceFormItems>",
"label": "备注",
"prop": "remark",
"type": "kui-textarea",
"required": false,
"props": {
"maxlength": 128,
"showWordLimit": true
}
}
]
},
"api": {
"query": "macbs/api/commSettbodyQueryPage",
"update": "macbs/api/commSettbodyModify",
"delete": "macbs/api/commSettbodyRemove",
"add": "macbs/api/commSettbodyAdd"
}
}
{
"form_query": {
"items": [
{
"__parentType__": "array<kaceFormItems>",
"label": "结算主体",
"prop": "settbody",
"type": "kui-select",
"required": false,
"props": {
"remote": true,
"clearable": true,
"options": [],
"filterable": true,
"labelKey": "settbodyname",
"valueKey": "settbody",
"remoteMethod": {
"type": "jsExpression",
"value": "val => {\n if (val !== \"\") {\n $global.$http.post('macbs/api/' + \"commSettbodyQueryPage\", {\n settbody: val,\n pageSize: 100,\n pageNum: 1\n }).then(res => {\n $page.state.meta.form_query.items.find(val2 => val2.prop === \"settbody\").props.options = res.data;\n });\n }\n }",
"url": "macbs/api/commSettbodyQueryPage"
}
}
}
]
},
"table": {
"pageSize": 20,
"type": "paging",
"items": [
{
"minWidth": 150,
"__parentType__": "array<object>",
"prop": "settbody",
"label": "结算主体"
},
{
"minWidth": 300,
"__parentType__": "array<object>",
"prop": "settbodyname",
"label": "结算主体名"
},
{
"minWidth": 250,
"__parentType__": "array<object>",
"prop": "remark",
"label": "备注"
}
]
},
"form_dialog": {
"items": [
{
"__parentType__": "array<kaceFormItems>",
"label": "结算主体",
"prop": "settbody",
"type": "kui-input",
"required": true,
"props": {
"disabled": false,
"maxlength": 32
}
},
{
"__parentType__": "array<kaceFormItems>",
"label": "结算主体名",
"prop": "settbodyname",
"type": "kui-input",
"required": true
},
{
"__parentType__": "array<kaceFormItems>",
"label": "备注",
"prop": "remark",
"type": "kui-textarea",
"required": false,
"props": {
"maxlength": 128,
"showWordLimit": true
}
}
]
},
"api": {
"query": "macbs/api/commSettbodyQueryPage",
"update": "macbs/api/commSettbodyModify",
"delete": "macbs/api/commSettbodyRemove",
"add": "macbs/api/commSettbodyAdd"
}
}
示例:定义元数据结构
考虑一个增删改查场景需要的数据结构,它至少需要如下配置:
- 搜索区域表单项
form_query.items
- 搜索结果区域的表格列配置
table.items
- 新增/修改弹窗中的表单项
form_dialog.items
- 新增/修改/删除/查询接口地址配置
api.create
,api.update
,api.delete
,api.query
在刚才创建的通用业务下双击元数据节点,进入元数据定义页面
在Meta根节点下不断添加下级属性,类型含义可以参考元数据结构类型说明
创建好增删改查场景需要的数据结构,然后点击右上角保存按钮,保存元数据结构信息
至此,就完成了元数据结构的设计。
示例:定义元数据示例
在定义好一份元数据结构之后,点击生成示例按钮,将根据元数据结构创建元数据示例,元数据示例通常在制作模版阶段用于查看设计效果。
在右侧元数据示例中,为搜索表单项、表格配置列添加数据
最后,点击右上角保存按钮,保存元数据示例信息。
对于不同的元数据类型,有不同的输入交互方式:
string
:使用文本输入框进行输入number
:使用数字输入框进行输入boolean
:使用Switch切换进行输入function
:使用代码编辑器进行输入object
:使用JSON编辑器进行输入array<object>
:点击"+"图标新增一项,进行输入
如下图示例:
元数据示例管理
通过点击"+"图标创建更多的元数据示例
通过展开示例列表,点击删除图标删除已有的元数据结构示例
表单设计
当字段类型为array<kocaFormItems>
或array<kaceFormItems>
时,提供了一种可视化的方式来设计表单联动信息以及表单字段信息。
设计表单字段
点击设计按钮,将弹出右侧抽屉对表单项进行字段设计,将展示表单项实时预览效果、表单配置项、组件配置项。最后点击抽屉下方的确认按钮保存操作。
设计表单联动
点击设计按钮,将弹出弹框对表单项进行联动设计。
表单联动是表单配置中核心的一环,目前根据掌握的业务场景,提供了如下四种联动配置方式:
场景1:当表单项A值不为空时,启用表单项B、C
场景2:当表单项A值为特定值时,隐藏表单项B、C
场景3:当表单项A的值变化时,执行自定义代码
alert(val)
场景4:当表单项A的值变化时,执行页面方法
handleValChange
(已在模版中定义此方法体:console.log("入参为", arguments)
)。
更多联动方式配置会在后续拓展。
元数据结构类型说明
元数据结构中,属性值支持如下的类型:
string
:字符串类型number
:数字类型boolean
:布尔值类型function
:函数类型object
:对象类型,常用array
:数组类型,不常用array<kocaFormItems>
:koca-ui 表单结构,将自动创建koca-ui组件库表单结构,常用array<kaceFormItems>
:kace-ui 表单结构,将自动创建kace-ui组件库表单结构,常用array<object>
:对象数组类型,常用array<string>
:字符数组类型,不常用array<number>
:数字数组类型,不常用array<boolean>
:布尔值数组类型,不常用