From 0d8a8e92714e0a8f3a59674a836a470fe8914a89 Mon Sep 17 00:00:00 2001 From: Lvbo163 Date: Thu, 21 Sep 2017 11:31:52 +0800 Subject: Support set value for tree branch Set value for tree branch node. Issue-ID: SDC-355 Change-Id: I4fea941bc2f3de321079049ea4735491cf9ca474 Signed-off-by: Lvbo163 --- .../parameter-tree/parameter-tree.component.html | 84 +++---- .../parameter-tree/parameter-tree.component.ts | 248 +++++++++++++-------- .../components/parameter/parameter.component.html | 2 +- .../components/parameter/parameter.component.ts | 2 +- .../rest-task-parameters.component.ts | 8 +- .../src/app/model/value-source.enum.ts | 1 + .../app/services/swagger-tree-converter.service.ts | 176 ++++++++++----- 7 files changed, 316 insertions(+), 205 deletions(-) (limited to 'sdc-workflow-designer-ui/src/app') diff --git a/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.html b/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.html index 0a12a600..cf4f9354 100644 --- a/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.html +++ b/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.html @@ -1,54 +1,42 @@ - - - - + + + - - [Array]({{node.children.length}}) {{node.label}}: - [Array]({{node.children.length}}) - - - - - - [Object] {{node.label}}: - [Object] - : - + +
+
+ +
+
+ +
+
+
- - - + +
+
+ +
+
+ +
+
- - -
+
- - [Map] {{node.label}}: - [Map] - : - - - - - -
+ + + + + diff --git a/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.ts b/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.ts index 0de35b94..4f399158 100644 --- a/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.ts +++ b/sdc-workflow-designer-ui/src/app/components/parameter-tree/parameter-tree.component.ts @@ -10,17 +10,18 @@ * ZTE - initial API and implementation and/or initial documentation */ -import { Component, Input, OnChanges, Output, SimpleChange, SimpleChanges, ViewEncapsulation } from '@angular/core'; +import { Component, Input, OnChanges, Output, SimpleChange, SimpleChanges } from '@angular/core'; import { TreeNode } from 'primeng/primeng'; +import { PlanTreeviewItem } from '../../model/plan-treeview-item'; import { ValueSource } from '../../model/value-source.enum'; import { ValueType } from '../../model/value-type.enum'; import { Parameter } from '../../model/workflow/parameter'; -import { RestParameter } from '../../model/workflow/rest-parameter'; import { RestTask } from '../../model/workflow/rest-task'; import { SwaggerTreeConverterService } from '../../services/swagger-tree-converter.service'; import { WorkflowUtil } from '../../util/workflow-util'; -import { PlanTreeviewItem } from "../../model/plan-treeview-item"; +import { Swagger } from "../../model/swagger"; +import { WorkflowConfigService } from "../../services/workflow-config.service"; /** * parameter tree presents parameter of task node's input and output parameters. @@ -29,7 +30,6 @@ import { PlanTreeviewItem } from "../../model/plan-treeview-item"; selector: 'b4t-parameter-tree', styleUrls: ['./parameter-tree.component.css'], templateUrl: 'parameter-tree.component.html', - encapsulation: ViewEncapsulation.None }) export class ParameterTreeComponent implements OnChanges { @Input() public parameters: TreeNode[]; @@ -38,51 +38,50 @@ export class ParameterTreeComponent implements OnChanges { @Input() public valueSource: ValueSource[]; @Input() public planItems: PlanTreeviewItem[]; - constructor(private swaggerTreeConverterService: SwaggerTreeConverterService) { } + constructor(private restService: WorkflowConfigService, private swaggerTreeConverterService: SwaggerTreeConverterService) { } public ngOnChanges(changes: SimpleChanges) { - const changeParameters = changes["parameters"]; - if (changeParameters && 0 < changeParameters.currentValue.length) { - this.formatParam(changeParameters.currentValue); - } + // const changeParameters = changes['parameters']; + // if (changeParameters && 0 < changeParameters.currentValue.length) { + // this.formatParam(changeParameters.currentValue); + // } } - public getParam(node: any) { - if (undefined === node.parameter.name) { - node.parameter.name = node.label; - node.parameter.valueSource = this.defaultValueSource; - } else { - if (node.parent.parameter.value[node.label]) { - node.parameter.value = node.parent.parameter.value[node.label].value; - node.parameter.valueSource = node.parent.parameter.value[node.label].valueSource; - } else { - const tempParamValue: any = {}; - tempParamValue.value = ''; - tempParamValue.valueSource = this.defaultValueSource; - node.parent.parameter.value[node.label] = tempParamValue; - node.parameter.value = tempParamValue.value; - node.parameter.valueSource = tempParamValue.valueSource; - } - } - return node.parameter; + public getParameter(node: any): Parameter { + return new Parameter(node.label,node.value.value, node.value.valueSource, node.definition.type); } + public paramChange(param: Parameter, node: any) { + node.value.valueSource = param.valueSource; + node.value.value = param.value; + + this.objectParameterChange(node); + if (node.label !== param.name) { + delete node.parent.value.value[node.label]; node.label = param.name; - this.propertyKeyChanged(node, param.value); } if (node.parent) { - if (node.parent.parameter.value[param.name]) { - node.parent.parameter.value[param.name].value = param.value; - node.parent.parameter.value[param.name].valueSource = param.valueSource; - } else { - node.parent.parameter.value[param.name] = { - value: param.value, - valueSource: param.valueSource - }; - } + node.parent.value.value[node.label] = node.value; + } else { + console.warn('Node.parent does not exists!' + JSON.stringify(node)); } + + } + + private objectParameterChange(node: any) { + if(node.value.valueSource === ValueSource[ValueSource.Definition]) { // value will be set by node defintion + const treeNode = this.swaggerTreeConverterService.schema2TreeNode(this.getSwagger(), node.label, node.definition, node.value); + node.value = treeNode.value; + node.children = treeNode.children; + } else { // parameter value will be set by param + node.children = []; + } + } + + private getSwagger(): Swagger { + return this.restService.getSwaggerInfo(this.task.serviceName, this.task.serviceVersion); } public getKeyParameter(node: any) { @@ -109,53 +108,87 @@ export class ParameterTreeComponent implements OnChanges { } public addChildNode4DynamicObject(node: any) { - const copyItem = WorkflowUtil.deepClone(node.parameter.additionalProperties); - const key = Object.keys(node.parameter.value).length; + const copyItem = WorkflowUtil.deepClone(node.definition.additionalProperties); + const key = Object.keys(node.value.value).length; + const childrenNode = this.swaggerTreeConverterService - .schema2TreeNode(key, this.task.serviceName, this.task.serviceVersion, copyItem); + .schema2TreeNode(this.getSwagger(), key, copyItem); childrenNode.keyEditable = true; - node.parameter.value[key] = childrenNode.parameter.value; + node.value.value[key] = childrenNode.value; node.children.push(childrenNode); } public propertyKeyChanged(node: any, newKey: string) { - const value = node.parent.parameter.value[node.label]; - node.parent.parameter.value[newKey] = value; - delete node.parent.parameter.value[node.label]; + const value = node.parent.value.value[node.label]; + node.parent.value.value[newKey] = value; + delete node.parent.value.value[node.label]; node.label = newKey; } public addChildNode4ObjectArray(node: any) { - const copyItem = WorkflowUtil.deepClone(node.parameter.items); + const copyItem = WorkflowUtil.deepClone(node.definition.items); const childrenNode = this.swaggerTreeConverterService .schema2TreeNode( + this.getSwagger(), node.children.length, - this.task.serviceName, - this.task.serviceVersion, copyItem); - node.parameter.value.push(childrenNode.parameter.value); + node.value.value.push(childrenNode.value); node.children.push(childrenNode); - this.initParam(node); } public deleteTreeNode(node: any) { - // delete data - node.parent.parameter.value.splice(node.label, 1); - node.parent.children.splice(node.label, 1); + if ('array' === node.parent.type) { + // delete data + node.parent.value.value.splice(node.label, 1); + node.parent.children.splice(node.label, 1); - // update node index - node.parent.children.forEach((childNode, index) => childNode.label = index); + // update node index + node.parent.children.forEach((childNode, index) => childNode.label = index); + } else if ('map' === node.parent.type) { + delete node.parent.value.value[node.label]; + for (let index = 0; index < node.parent.children.length; index++) { + const element = node.parent.children[index]; + if (element.label === node.label) { + node.parent.children.splice(index, 1); + break; + } + } + } } public canEditValue(node: any): boolean { return node.children.length === 0; } + public editNode(node: any) { + node.editing = true; + } + + public editComplete(node: any) { + node.editing = false; + + const newValueObj = JSON.parse(node.tempValue); + for (const key in node.value.value) { + delete node.value.value[key]; + } + + for (const key in newValueObj) { + node.value.value[key] = newValueObj[key]; + } + + // delete all children nodes + + // add new nodes by new value + + } + + + public canDelete(node: any) { const parent = node.parent; if (parent && @@ -167,59 +200,70 @@ export class ParameterTreeComponent implements OnChanges { } public updateObjectValue(node: any, value: string) { - const newValueObj = JSON.parse(value); - for (const key in node.parameter.value) { - delete node.parameter.value[key]; - } + node.tempValue = value; + // const newValueObj = JSON.parse(value); + // for (const key in node.parameter.value) { + // delete node.parameter.value[key]; + // } - for (const key in newValueObj) { - node.parameter.value[key] = newValueObj[key]; - } + // for (const key in newValueObj) { + // node.parameter.value[key] = newValueObj[key]; + // } } public getObjectValue(node) { - return JSON.stringify(node.parameter.value); + return JSON.stringify(node.value.value); + } + + public getObjectValueSource(): ValueSource[] { + const result = []; + result.push(ValueSource.Definition); + this.valueSource.forEach(source => result.push(source)); + return result; } public canAdd(node: any) { return this.isArrayObject(node) || this.isDynamicObject(node); } - private formatParam(params: any[]): void { - params.forEach(param => this.initParam(param)); - } + // private formatParam(params: any[]): void { + // console.log(params); + // params.forEach(param => this.initParam(param)); + // } - private initParam(parameter: any, value?: any): void { - if (!parameter || 0 === parameter.length) { - return; - } - switch (parameter.type) { - case 'default': - parameter.parameter.name = parameter.label; - if (value && value[parameter.label]) { - parameter.parameter.value = value[parameter.label].value; - parameter.parameter.valueSource = value[parameter.label].valueSource; - } else { - parameter.parameter.valueSource = this.defaultValueSource; - } - break; - case 'object': - for (let index = 0; index < parameter.children.length; index++) { - let param = parameter.children[index]; - this.initParam(param, parameter.parameter.value); - } - break; - case 'array': - for (let index = 0; index < parameter.children.length; index++) { - let param = parameter.children[index]; - this.initParam(param, parameter.parameter.value); - } - break; - default: - console.log('init a unsupport parameter, type is:' + parameter.type); - break; - } - } + // private initParam(treeNode: any, value?: any): void { + // switch (treeNode.type) { + // case 'default': + // if (value) { + // treeNode.value.value = value[treeNode.label].value; + // treeNode.value.valueSource = value[treeNode.label].valueSource; + // } else { + // treeNode.parameter.valueSource = this.defaultValueSource; + // } + // break; + // case 'object': + // for (let index = 0; index < treeNode.children.length; index++) { + // const param = treeNode.children[index]; + // this.initParam(param, treeNode.parameter.value); + // } + // break; + // case 'array': + // for (let index = 0; index < treeNode.children.length; index++) { + // const param = treeNode.children[index]; + // this.initParam(param, treeNode.parameter.value); + // } + // break; + // case 'map': + // for (let index = 0; index < treeNode.children.length; index++) { + // const param = treeNode.children[index]; + // this.initParam(param, treeNode.parameter.value); + // } + // break; + // default: + // console.log('init a unsupport parameter, type is:' + treeNode.type); + // break; + // } + // } private isArrayObject(node: any): boolean { return node.type === 'array'; @@ -228,4 +272,16 @@ export class ParameterTreeComponent implements OnChanges { private isDynamicObject(node: any): boolean { return node.type === 'map'; } + + public getWidth(node: any) { + if(this.canAdd(node)) { + return { + 'col-md-11': true + }; + } else { + return { + 'col-md-12': true + }; + } + } } diff --git a/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.html b/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.html index e6a7ff44..3c9f1858 100644 --- a/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.html +++ b/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.html @@ -28,7 +28,7 @@ childrenField="children" #simpleSelect="ngModel" [ngClass]="valueClass" class="tree-select-class" [ngModel]="planValue" (ngModelChange)="valueChange($event)"> - diff --git a/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.ts b/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.ts index 3539c8f0..9f4c6d1e 100644 --- a/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.ts +++ b/sdc-workflow-designer-ui/src/app/components/parameter/parameter.component.ts @@ -49,7 +49,7 @@ export class ParameterComponent implements OnInit { this.showValueSource = false; } this.valueClass = { - 'col-md-9': this.showValueSource, + 'col-md-8': this.showValueSource, 'col-md-12': !this.showValueSource }; diff --git a/sdc-workflow-designer-ui/src/app/components/property/rest-task/rest-task-parameters/rest-task-parameters.component.ts b/sdc-workflow-designer-ui/src/app/components/property/rest-task/rest-task-parameters/rest-task-parameters.component.ts index 87903578..7f8bbf43 100644 --- a/sdc-workflow-designer-ui/src/app/components/property/rest-task/rest-task-parameters/rest-task-parameters.component.ts +++ b/sdc-workflow-designer-ui/src/app/components/property/rest-task/rest-task-parameters/rest-task-parameters.component.ts @@ -20,6 +20,7 @@ import { RestParameter } from "../../../../model/workflow/rest-parameter"; import { ValueSource } from "../../../../model/value-source.enum"; import { SwaggerTreeConverterService } from "../../../../services/swagger-tree-converter.service"; import { PlanTreeviewItem } from "../../../../model/plan-treeview-item"; +import { WorkflowConfigService } from "../../../../services/workflow-config.service"; /** * property component presents information of a workflow node. @@ -42,7 +43,9 @@ export class RestTaskParametersComponent implements OnInit { private index = 1; - constructor(private broadcastService: BroadcastService, private swaggerTreeConverterService: SwaggerTreeConverterService) { + constructor(private broadcastService: BroadcastService, + private workflowConfigService: WorkflowConfigService, + private swaggerTreeConverterService: SwaggerTreeConverterService) { } public ngOnInit() { @@ -59,7 +62,8 @@ export class RestTaskParametersComponent implements OnInit { this.task.parameters.forEach(param => { if (param.position === 'body') { const requestTreeNode = this.swaggerTreeConverterService - .schema2TreeNode('Request Param', this.task.serviceName, this.task.serviceVersion, param.schema); + .schema2TreeNode(this.workflowConfigService.getSwaggerInfo(this.task.serviceName, this.task.serviceVersion), 'Request Param', param.schema, param.value); + param.value = requestTreeNode.value; param.value = param.schema.value; this.bodyParameter.push(requestTreeNode); } else { diff --git a/sdc-workflow-designer-ui/src/app/model/value-source.enum.ts b/sdc-workflow-designer-ui/src/app/model/value-source.enum.ts index eeeb5289..fd08c8de 100644 --- a/sdc-workflow-designer-ui/src/app/model/value-source.enum.ts +++ b/sdc-workflow-designer-ui/src/app/model/value-source.enum.ts @@ -14,5 +14,6 @@ export enum ValueSource { String, Plan, Variable, + Definition, // Topology, // TODO implement Topology properties in R2 } diff --git a/sdc-workflow-designer-ui/src/app/services/swagger-tree-converter.service.ts b/sdc-workflow-designer-ui/src/app/services/swagger-tree-converter.service.ts index a83ae2e4..b70b0ca5 100644 --- a/sdc-workflow-designer-ui/src/app/services/swagger-tree-converter.service.ts +++ b/sdc-workflow-designer-ui/src/app/services/swagger-tree-converter.service.ts @@ -15,75 +15,126 @@ import { TreeNode } from 'primeng/primeng'; import { ValueSource } from '../model/value-source.enum'; import { WorkflowUtil } from '../util/workflow-util'; +import { Swagger } from "../model/swagger"; import { WorkflowConfigService } from "./workflow-config.service"; @Injectable() export class SwaggerTreeConverterService { - private serviceName: string; - private serviceVersion: string; - constructor(private configService: WorkflowConfigService) { + private swagger: Swagger; - } + constructor(private workflowConfigService: WorkflowConfigService) { - public schema2TreeNode(key: string | number, serviceName: string, serviceVersion: string, schema: any): any { - this.serviceName = serviceName; - this.serviceVersion = serviceVersion; + } + public schema2TreeNode(swagger: Swagger, key: string | number, schema: any, value?: any): any { + this.swagger = swagger; if (schema.$ref) { - const treeNode = this.getTreeNodeBySwaggerDefinition(key, schema); + const treeNode = this.getTreeNodeBySwaggerDefinition(key, schema, value); return treeNode; } else { - this.setInitValue4Param(schema.value, schema); - return this.parameter2TreeNode(key, schema); + value = this.getInitValue4Param(schema, value); + return this.parameter2TreeNode(key, schema, value); } } - private getTreeNodeBySwaggerDefinition(key: string | number, schema: any): TreeNode { - const swagger = this.configService.getSwaggerInfo(this.serviceName, this.serviceVersion); - if(swagger === undefined) { - console.log(`swagger definition not exist, [${this.serviceName}].[${this.serviceVersion}]`); - return null; - } - const swaggerDefinition = this.configService.getDefinition(swagger, schema.$ref); + private getTreeNodeBySwaggerDefinition(key: string | number, schema: any, value: any): TreeNode { + const swaggerDefinition = this.workflowConfigService.getDefinition(this.swagger, schema.$ref); const definitionCopy = WorkflowUtil.deepClone(swaggerDefinition); - this.setInitValue4Param(schema.value, definitionCopy); - if (schema.value !== definitionCopy.value) { - schema.value = definitionCopy.value; + value = this.getInitValue4Param(definitionCopy, value); + + return this.schema2TreeNode(this.swagger, key, definitionCopy, value); + } + + private getInitValue4Param(definition: any, value: any) { + if (definition.$ref) { + definition = this.workflowConfigService.getDefinition(this.swagger, definition.$ref); + } + if (definition.type === 'object') { + return this.getInitValue4Object(value); + } else if (definition.type === 'array') { + return this.getInitValue4Array(value); + } else { // primary type + return this.getInitValue4Primate(value); + } + } + + private getInitValue4Object(value: any) { + const newValue = { + value: {}, + valueSource: ValueSource[ValueSource.Definition] + }; + + if(!value) { + return newValue; + } else { + if(value.valueSource !== ValueSource[ValueSource.Definition]) { + return value; + } else { + if(typeof value.value !== 'object') { + value.value = {}; + } + return value; } + } + } - return this.schema2TreeNode(key, this.serviceName, this.serviceVersion, definitionCopy); + private getInitValue4Array(value: any) { + const newValue = { + value: [], + valueSource: ValueSource[ValueSource.Definition] + }; + + if(!value) { + return newValue; + } else { + if(value.valueSource !== ValueSource[ValueSource.Definition]) { + return value; + } else { + if(!(value.value instanceof Array)) { + value.value = []; + } + return value; + } + } } - private setInitValue4Param(value: any | any[], param: any) { - param.value = value; - if (value == null) { - if (param.type === 'object') { - param.value = {}; - } else if (param.type === 'array') { - param.value = []; - } else { // primary type - param.valueSource = ValueSource[ValueSource.String]; - } + private getInitValue4Primate(value: any) { + const newValue = { + value: '', + valueSource: ValueSource[ValueSource.String] + }; + + if(!value) { + return newValue; + } else { + if(typeof value.value === 'object') { + value.value = ''; } + return value; + } } - private parameter2TreeNode(name: string | number, paramDefinition: any): any { - const nodeType = this.getTreeNodeType(paramDefinition); + private parameter2TreeNode(name: string | number, definition: any, value: any): any { + const nodeType = this.getTreeNodeType(definition); const node = { label: name, type: nodeType, + required: definition.required, children: [], - parameter: paramDefinition, + definition: definition, + value: value, }; - if (paramDefinition.type === 'object') { - node.children = this.getPropertyFromObject(paramDefinition.value, paramDefinition); - } else if (paramDefinition.type === 'array') { - this.setChildrenForArray(node, paramDefinition); + if(value.valueSource === ValueSource[ValueSource.Definition]) { + if (definition.type === 'object') { + node.children = this.getPropertyFromObject(definition, value.value); + } else if (definition.type === 'array') { + this.setChildrenForArray(definition, value.value); + } } return node; @@ -104,47 +155,58 @@ export class SwaggerTreeConverterService { } } - private setChildrenForArray(node: any, param: any) { - param.value.forEach((itemValue, index) => { - const itemCopy = WorkflowUtil.deepClone(param.items); - itemCopy.value = itemValue; - node.children.push(this.schema2TreeNode(index, this.serviceName, this.serviceVersion, itemCopy)); + private setChildrenForArray(definition: any, value: any[]): any[] { + const children = []; + value.forEach((itemValue, index) => { + const itemCopy = WorkflowUtil.deepClone(definition.items); + children.push(this.schema2TreeNode(this.swagger, index, itemCopy, itemValue)); }); + + return children; } - private getPropertyFromObject(objectValue: any, param: any): TreeNode[] { - if (param.properties) { - return this.getPropertyFromSimpleObject(objectValue, param.properties); - } else if (param.additionalProperties) { - return this.getPropertyFromMapOrDictionary(objectValue, param.additionalProperties); + private getPropertyFromObject(definition: any, value: any): TreeNode[] { + if (definition.properties) { + return this.getPropertyFromSimpleObject(definition.properties, value, definition.required); + } else if (definition.additionalProperties) { + return this.getPropertyFromMapOrDictionary(definition.additionalProperties, value); } else { + console.log('getPropertyFromObject() return [], param is:' + JSON.stringify(definition)); return []; } } - private getPropertyFromSimpleObject(objectValue: any, properties: any): TreeNode[] { + private getPropertyFromSimpleObject(properties: any, objectValue: any, required: string[]): TreeNode[] { const treeNodes: TreeNode[] = []; for (const key in properties) { - const property = properties[key]; - this.setInitValue4Param(objectValue[key], property); - - if (property.value !== objectValue[key]) { - objectValue[key] = property.value; + let property = properties[key]; + // init required property + property.required = false; + if (Array.isArray(required)) { + for (let index = 0; index < required.length; index++) { + if (required[index] === key) { + property.required = true; + break; + } + } } - treeNodes.push(this.schema2TreeNode(key, this.serviceName, this.serviceVersion, property)); + objectValue[key] = this.getInitValue4Param(property, objectValue[key]); + + const treeNode = this.schema2TreeNode(this.swagger, key, property, objectValue[key]); + treeNodes.push(treeNode); } return treeNodes; } - private getPropertyFromMapOrDictionary(mapOrDictionary: any, additionalProperties: any): TreeNode[] { + private getPropertyFromMapOrDictionary(additionalProperties: any, mapOrDictionary: any): TreeNode[] { const treeNodes: TreeNode[] = []; for (const key in mapOrDictionary) { const propertyCopy = WorkflowUtil.deepClone(additionalProperties); propertyCopy.value = mapOrDictionary[key]; - const treeNode = this.schema2TreeNode(key, this.serviceName, this.serviceVersion, propertyCopy); + const treeNode = this.schema2TreeNode(this.swagger, key, propertyCopy, propertyCopy.value); treeNode.keyEditable = true; treeNodes.push(treeNode); -- cgit 1.2.3-korg