2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6 * ================================================================================
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 * ============LICENSE_END=========================================================
21 package org.openecomp.sdc.be.components.impl;
23 import com.google.gson.JsonElement;
24 import fj.data.Either;
25 import org.apache.commons.collections.CollectionUtils;
26 import org.apache.commons.collections.MapUtils;
27 import org.apache.commons.lang3.tuple.ImmutablePair;
28 import org.openecomp.sdc.be.components.impl.exceptions.BusinessLogicException;
29 import org.openecomp.sdc.be.config.BeEcompErrorManager;
30 import org.openecomp.sdc.be.dao.api.ActionStatus;
31 import org.openecomp.sdc.be.dao.janusgraph.JanusGraphOperationStatus;
32 import org.openecomp.sdc.be.datatypes.elements.ListDataDefinition;
33 import org.openecomp.sdc.be.datatypes.elements.OperationDataDefinition;
34 import org.openecomp.sdc.be.datatypes.elements.OperationInputDefinition;
35 import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
36 import org.openecomp.sdc.be.datatypes.elements.SchemaDefinition;
37 import org.openecomp.sdc.be.datatypes.enums.NodeTypeEnum;
38 import org.openecomp.sdc.be.impl.WebAppContextWrapper;
39 import org.openecomp.sdc.be.model.Component;
40 import org.openecomp.sdc.be.model.ComponentInstanceInterface;
41 import org.openecomp.sdc.be.model.ComponentParametersView;
42 import org.openecomp.sdc.be.model.DataTypeDefinition;
43 import org.openecomp.sdc.be.model.IComplexDefaultValue;
44 import org.openecomp.sdc.be.model.InterfaceDefinition;
45 import org.openecomp.sdc.be.model.PropertyDefinition;
46 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ArtifactsOperations;
47 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.InterfaceOperation;
48 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.exception.ToscaOperationException;
49 import org.openecomp.sdc.be.model.operations.api.IElementOperation;
50 import org.openecomp.sdc.be.model.operations.api.IGroupInstanceOperation;
51 import org.openecomp.sdc.be.model.operations.api.IGroupOperation;
52 import org.openecomp.sdc.be.model.operations.api.IGroupTypeOperation;
53 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
54 import org.openecomp.sdc.be.model.operations.impl.InterfaceLifecycleOperation;
55 import org.openecomp.sdc.be.model.operations.impl.UniqueIdBuilder;
56 import org.openecomp.sdc.be.model.operations.utils.ComponentValidationUtils;
57 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
58 import org.openecomp.sdc.be.model.tosca.converters.PropertyValueConverter;
59 import org.openecomp.sdc.be.model.tosca.validators.PropertyTypeValidator;
60 import org.openecomp.sdc.be.resources.data.EntryData;
61 import org.openecomp.sdc.common.api.Constants;
62 import org.openecomp.sdc.common.log.enums.EcompLoggerErrorCode;
63 import org.openecomp.sdc.common.log.wrappers.Logger;
64 import org.openecomp.sdc.exception.ResponseFormat;
65 import org.springframework.beans.factory.annotation.Autowired;
66 import org.springframework.web.context.WebApplicationContext;
68 import javax.servlet.ServletContext;
69 import java.util.ArrayList;
70 import java.util.List;
72 import java.util.Objects;
73 import java.util.Optional;
74 import java.util.function.Supplier;
77 @org.springframework.stereotype.Component("propertyBusinessLogic")
78 public class PropertyBusinessLogic extends BaseBusinessLogic {
80 private static final String CREATE_PROPERTY = "CreateProperty";
82 private static final Logger log = Logger.getLogger(PropertyBusinessLogic.class);
84 private static final String EMPTY_VALUE = null;
87 public PropertyBusinessLogic(IElementOperation elementDao,
88 IGroupOperation groupOperation,
89 IGroupInstanceOperation groupInstanceOperation,
90 IGroupTypeOperation groupTypeOperation,
91 InterfaceOperation interfaceOperation,
92 InterfaceLifecycleOperation interfaceLifecycleTypeOperation,
93 ArtifactsOperations artifactToscaOperation) {
94 super(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation,
95 interfaceOperation, interfaceLifecycleTypeOperation, artifactToscaOperation);
98 protected static IElementOperation getElementDao(Class<IElementOperation> class1, ServletContext context) {
99 WebAppContextWrapper webApplicationContextWrapper = (WebAppContextWrapper) context.getAttribute(Constants.WEB_APPLICATION_CONTEXT_WRAPPER_ATTR);
101 WebApplicationContext webApplicationContext = webApplicationContextWrapper.getWebAppContext(context);
103 return webApplicationContext.getBean(class1);
106 public Map<String, DataTypeDefinition> getAllDataTypes() {
107 return getAllDataTypes(applicationDataTypeCache);
111 * Create new property on component in graph
114 * @param propertyName
115 * @param newPropertyDefinition
117 * @return either properties or response format
120 public Either<EntryData<String, PropertyDefinition>, ResponseFormat> addPropertyToComponent(String componentId,
122 PropertyDefinition newPropertyDefinition,
124 Either<EntryData<String, PropertyDefinition>, ResponseFormat> result = null;
126 validateUserExists(userId);
128 Either<Component, StorageOperationStatus> serviceElement =
129 toscaOperationFacade.getToscaElement(componentId);
130 if (serviceElement.isRight()) {
131 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.RESOURCE_NOT_FOUND, ""));
134 Component component = serviceElement.left().value();
135 NodeTypeEnum nodeType = component.getComponentType().getNodeType();
136 StorageOperationStatus lockResult = graphLockOperation.lockComponent(componentId, nodeType );
137 if (!lockResult.equals(StorageOperationStatus.OK)) {
138 BeEcompErrorManager.getInstance().logBeFailedLockObjectError(CREATE_PROPERTY, nodeType.name().toLowerCase(), componentId);
139 log.info("Failed to lock component {}. Error - {}", componentId, lockResult);
140 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
145 if (!ComponentValidationUtils.canWorkOnComponent(component, userId)) {
146 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.RESTRICTED_OPERATION));
150 List<PropertyDefinition> properties = component.getProperties();
152 if(CollectionUtils.isEmpty(properties)) {
153 properties = new ArrayList<>();
156 if(isPropertyExistInComponent(properties, propertyName)) {
159 Either.right(componentsUtils.getResponseFormat(ActionStatus
160 .PROPERTY_ALREADY_EXIST, propertyName));
165 Map<String, DataTypeDefinition> allDataTypes = getAllDataTypes(applicationDataTypeCache);
167 // validate property default values
168 Either<Boolean, ResponseFormat> defaultValuesValidation = validatePropertyDefaultValue(newPropertyDefinition, allDataTypes);
169 if (defaultValuesValidation.isRight()) {
170 result = Either.right(defaultValuesValidation.right().value());
174 ToscaPropertyType type = getType(newPropertyDefinition.getType());
176 PropertyValueConverter converter = type.getConverter();
178 String innerType = null;
179 if (newPropertyDefinition != null) {
180 SchemaDefinition schema = newPropertyDefinition.getSchema();
181 if (schema != null) {
182 PropertyDataDefinition prop = schema.getProperty();
184 innerType = prop.getType();
187 String convertedValue = null;
188 if (newPropertyDefinition.getDefaultValue() != null) {
189 convertedValue = converter.convert(
190 newPropertyDefinition.getDefaultValue(), innerType, allDataTypes);
191 newPropertyDefinition.setDefaultValue(convertedValue);
195 Either<PropertyDefinition, StorageOperationStatus> addPropertyEither =
197 .addPropertyToComponent(propertyName, newPropertyDefinition, component);
199 if (addPropertyEither.isRight()) {
200 log.info("Failed to add new property {}. Error - {}", componentId,
201 addPropertyEither.right().value());
202 result = Either.right(componentsUtils.getResponseFormat(ActionStatus
207 result = Either.left(new EntryData<>(propertyName, newPropertyDefinition));
210 commitOrRollback(result);
212 graphLockOperation.unlockComponent(componentId, nodeType);
217 * Copies a list of properties to a component.
219 * @param component the component to add the copied properties
220 * @param propertiesToCopyList the properties to be copied
221 * @return the updated component with the copied properties.
222 * @throws ToscaOperationException when a problem happens during the copy operation
224 public Component copyPropertyToComponent(final Component component,
225 final List<PropertyDefinition> propertiesToCopyList) throws ToscaOperationException {
226 return copyPropertyToComponent(component, propertiesToCopyList, true);
230 * Copies a list of properties to a component.
232 * @param component the component to add the copied properties
233 * @param propertiesToCopyList the properties to be copied
234 * @param refreshComponent refresh the component from database after update
235 * @return the component refreshed from database if refreshComponent is {@code true}, the same component reference
237 * @throws ToscaOperationException when a problem happens during the copy operation
239 public Component copyPropertyToComponent(final Component component,
240 final List<PropertyDefinition> propertiesToCopyList,
241 final boolean refreshComponent) throws ToscaOperationException {
242 if (CollectionUtils.isEmpty(propertiesToCopyList)) {
246 for (final PropertyDefinition propertyDefinition : propertiesToCopyList) {
247 copyPropertyToComponent(component, propertyDefinition);
250 if (refreshComponent) {
251 return toscaOperationFacade.getToscaElement(component.getUniqueId()).left().value();
258 * Copies one property to a component.
260 * @param component the component to add the copied property
261 * @param propertyDefinition the property to be copied
262 * @throws ToscaOperationException when a problem happens during the copy operation
264 private void copyPropertyToComponent(final Component component,
265 final PropertyDefinition propertyDefinition) throws ToscaOperationException {
266 final PropertyDefinition copiedPropertyDefinition = new PropertyDefinition(propertyDefinition);
267 final String componentId = component.getUniqueId();
268 final String propertyName = copiedPropertyDefinition.getName();
269 copiedPropertyDefinition.setUniqueId(
270 UniqueIdBuilder.buildPropertyUniqueId(componentId, propertyName)
272 copiedPropertyDefinition.setParentUniqueId(componentId);
273 final Either<PropertyDefinition, StorageOperationStatus> operationResult = toscaOperationFacade
274 .addPropertyToComponent(propertyName, copiedPropertyDefinition, component);
275 if (operationResult.isRight()) {
276 final String error = String.format(
277 "Failed to add copied property '%s' to component '%s'. Operation status: '%s'",
278 propertyDefinition.getUniqueId(), componentId, operationResult.right().value()
280 log.error(EcompLoggerErrorCode.BUSINESS_PROCESS_ERROR, PropertyBusinessLogic.class.getName(), "catalog-be", error);
281 throw new ToscaOperationException(error, operationResult.right().value());
286 * Get property of component
291 * @return either properties or response format
294 public Either<Map.Entry<String, PropertyDefinition>, ResponseFormat> getComponentProperty(String componentId, String propertyId, String userId) {
296 validateUserExists(userId);
297 // Get the resource from DB
298 Either<Component, StorageOperationStatus> status =
299 toscaOperationFacade.getToscaElement(componentId);
300 if (status.isRight()) {
301 return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESOURCE_NOT_FOUND, ""));
303 Component component = status.left().value();
304 List<PropertyDefinition> properties = component.getProperties();
305 if(CollectionUtils.isEmpty(properties)) {
306 return Either.right(componentsUtils.getResponseFormat(ActionStatus.PROPERTY_NOT_FOUND, ""));
309 for(PropertyDefinition property : properties) {
310 if(property.getUniqueId().equals(propertyId)) {
311 return Either.left(new EntryData<>(property.getName(), property));
314 return Either.right(componentsUtils.getResponseFormat(ActionStatus.PROPERTY_NOT_FOUND, ""));
318 public Either<List<PropertyDefinition>, ResponseFormat> getPropertiesList(String componentId,
320 validateUserExists(userId);
322 // Get the resource from DB
323 ComponentParametersView filter = new ComponentParametersView(true);
324 filter.setIgnoreProperties(false);
325 Either<Component, StorageOperationStatus> status =
326 toscaOperationFacade.getToscaElement(componentId);
327 if (status.isRight()) {
328 return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESOURCE_NOT_FOUND, ""));
330 Component component = status.left().value();
331 List<PropertyDefinition> properties = component.getProperties();
333 return Either.left(properties);
338 * delete property of component from graph
343 * @return either properties or response format
346 public Either<Map.Entry<String, PropertyDefinition>, ResponseFormat> deletePropertyFromComponent(String componentId, String propertyId, String userId) {
348 Either<Map.Entry<String, PropertyDefinition>, ResponseFormat> result = null;
350 validateUserExists(userId);
352 // Get the resource from DB
353 Either<Component, StorageOperationStatus> getComponentRes = toscaOperationFacade.getToscaElement(componentId);
354 if (getComponentRes.isRight()) {
355 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.RESOURCE_NOT_FOUND, ""));
358 Component component = getComponentRes.left().value();
359 NodeTypeEnum nodeType = component.getComponentType().getNodeType();
360 StorageOperationStatus lockResult = graphLockOperation.lockComponent(componentId, nodeType);
361 if (!lockResult.equals(StorageOperationStatus.OK)) {
362 BeEcompErrorManager.getInstance().logBeFailedLockObjectError(CREATE_PROPERTY, nodeType.name().toLowerCase(),
364 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
369 // verify that resource is checked-out and the user is the last
371 if (!ComponentValidationUtils.canWorkOnComponent(component, userId)) {
372 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.RESTRICTED_OPERATION));
376 // verify property exist in resource
377 Either<Map.Entry<String, PropertyDefinition>, ResponseFormat> statusGetProperty =
378 getComponentProperty(componentId, propertyId, userId);
379 if (statusGetProperty.isRight()) {
380 result = Either.right(statusGetProperty.right().value());
384 Map.Entry<String, PropertyDefinition> propertyDefinitionEntry = statusGetProperty.left().value();
386 // verify that the property is not used by operation
387 if (isPropertyUsedByOperation(component, propertyDefinitionEntry.getValue())) {
388 return Either.right(componentsUtils.getResponseFormat(ActionStatus
389 .PROPERTY_USED_BY_OPERATION));
392 StorageOperationStatus status =
393 toscaOperationFacade.deletePropertyOfComponent(component, propertyDefinitionEntry.getKey());
394 if (status != StorageOperationStatus.OK) {
395 result = Either.right(componentsUtils.getResponseFormat(componentsUtils
396 .convertFromStorageResponse(status), component.getName()));
399 result = Either.left(propertyDefinitionEntry);
403 commitOrRollback(result);
405 graphLockOperation.unlockComponent(componentId, nodeType);
409 public boolean isPropertyUsedByOperation(Component component,
410 PropertyDefinition propertyDefinitionEntry) {
412 // Component's own interfaces
413 Map<String, InterfaceDefinition> interfaces = component.getInterfaces();
414 if(MapUtils.isNotEmpty(interfaces)){
415 for(Map.Entry<String, InterfaceDefinition> interfaceEntry : interfaces.entrySet()) {
416 if (isPropertyExistInOperationInterface(propertyDefinitionEntry, interfaceEntry.getValue())) {
422 // Component's child's component interfaces
423 if(isPropertyUsedInCIInterfaces(component.getComponentInstancesInterfaces(), propertyDefinitionEntry)){
427 // Component's parent's component interfaces
428 Either<List<Component>, StorageOperationStatus> componentList = toscaOperationFacade.getParentComponents(component.getUniqueId());
429 if(componentList.isLeft()){
430 for (Component parentComponent : componentList.left().value()) {
431 if(isPropertyUsedInCIInterfaces(parentComponent.getComponentInstancesInterfaces(), propertyDefinitionEntry)){
440 private boolean isPropertyUsedInCIInterfaces(Map<String, List<ComponentInstanceInterface>> componentInstanceInterfaces, PropertyDefinition propertyDefinitionEntry){
441 Optional<ComponentInstanceInterface> isPropertyExistInOperationInterface = Optional.empty();
442 if(MapUtils.isNotEmpty(componentInstanceInterfaces)){
443 isPropertyExistInOperationInterface = componentInstanceInterfaces.entrySet().stream()
444 .flatMap(interfaceEntry -> interfaceEntry.getValue().stream())
445 .filter(instanceInterface -> isPropertyExistInOperationInterface(propertyDefinitionEntry, instanceInterface))
448 return isPropertyExistInOperationInterface.isPresent();
451 private boolean isPropertyExistInOperationInterface(PropertyDefinition propertyDefinition,
452 InterfaceDefinition interfaceDefinition) {
453 Map<String, OperationDataDefinition> operations =
454 interfaceDefinition.getOperations();
455 for(Map.Entry<String, OperationDataDefinition> operationEntry : operations
457 Optional<OperationInputDefinition> inputWithDeletedPropertyCandidate =
458 getInputWithDeclaredProperty(propertyDefinition, operationEntry);
460 if(inputWithDeletedPropertyCandidate.isPresent()) {
467 private Optional<OperationInputDefinition> getInputWithDeclaredProperty(PropertyDefinition propertyDefinition,
468 Map.Entry<String, OperationDataDefinition> operationEntry) {
469 ListDataDefinition<OperationInputDefinition> inputs =
470 operationEntry.getValue().getInputs();
471 List<OperationInputDefinition> operationInputsList =
472 Objects.isNull(inputs) ? null : inputs.getListToscaDataDefinition();
474 if(CollectionUtils.isEmpty(operationInputsList)) {
475 return Optional.empty();
478 return operationInputsList.stream().filter(input -> input.getInputId().equals(propertyDefinition.getUniqueId())
479 || (input.getSourceProperty() != null && input.getSourceProperty().equals(propertyDefinition.getUniqueId()))).findAny();
487 * @param newPropertyDefinition
489 * @return either properties or response format
492 public Either<EntryData<String, PropertyDefinition>, ResponseFormat> updateComponentProperty(String componentId,
494 PropertyDefinition newPropertyDefinition,
497 Either<EntryData<String, PropertyDefinition>, ResponseFormat> result = null;
499 Either<Component, StorageOperationStatus> status = toscaOperationFacade.getToscaElement(
501 if (status.isRight()) {
502 return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESOURCE_NOT_FOUND, ""));
504 Component component = status.left().value();
505 NodeTypeEnum nodeType = component.getComponentType().getNodeType();
507 if (!ComponentValidationUtils.canWorkOnComponent(component, userId)) {
508 return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESTRICTED_OPERATION));
511 StorageOperationStatus lockResult = graphLockOperation.lockComponent(componentId, nodeType);
512 if (!lockResult.equals(StorageOperationStatus.OK)) {
513 BeEcompErrorManager.getInstance().logBeFailedLockObjectError(CREATE_PROPERTY, nodeType.name().toLowerCase(),
515 result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
520 Either<Map.Entry<String, PropertyDefinition>, ResponseFormat> statusGetProperty =
521 getComponentProperty(componentId, propertyId, userId);
522 if (statusGetProperty.isRight()) {
523 result = Either.right(statusGetProperty.right().value());
526 String propertyName = statusGetProperty.left().value().getKey();
528 Either<PropertyDefinition, StorageOperationStatus> either =
529 toscaOperationFacade.updatePropertyOfComponent(component, newPropertyDefinition);
530 if (either.isRight()) {
531 result = Either.right(componentsUtils.getResponseFormatByResource(componentsUtils.convertFromStorageResponse(either.right().value()), component.getName()));
535 EntryData<String, PropertyDefinition> property = new EntryData<>(propertyName, either.left().value());
536 result = Either.left(property);
540 commitOrRollback(result);
541 graphLockOperation.unlockComponent(componentId, nodeType);
547 * Finds a component by id,
549 * @param componentId the component id to find
550 * @return an Optional<Component> if the component with given id was found, otherwise Optional.empty()
551 * @throws BusinessLogicException when a problem happens during the find operation
553 public Optional<Component> findComponentById(final String componentId) throws BusinessLogicException {
554 final Either<Component, StorageOperationStatus> status = toscaOperationFacade.getToscaElement(componentId);
555 if (status.isRight()) {
556 final StorageOperationStatus operationStatus = status.right().value();
557 if (operationStatus == StorageOperationStatus.NOT_FOUND) {
558 return Optional.empty();
560 final ResponseFormat responseFormat = componentsUtils.getResponseFormat(operationStatus);
561 throw new BusinessLogicException(responseFormat);
563 return Optional.ofNullable(status.left().value());
567 * Updates a component property.
569 * @param componentId the component id that owns the property
570 * @param propertyDefinition the existing property to update
571 * @return the updated property
572 * @throws BusinessLogicException if the component was not found or if there was a problem during the update
575 public PropertyDefinition updateComponentProperty(final String componentId,
576 final PropertyDefinition propertyDefinition)
577 throws BusinessLogicException {
578 final Component component = findComponentById(componentId).orElse(null);
579 if (component == null) {
580 throw new BusinessLogicException(
581 componentsUtils.getResponseFormatByResource(ActionStatus.RESOURCE_NOT_FOUND, componentId));
583 final Either<PropertyDefinition, StorageOperationStatus> updateResultEither =
584 toscaOperationFacade.updatePropertyOfComponent(component, propertyDefinition);
585 if (updateResultEither.isRight()) {
586 final ResponseFormat responseFormat = componentsUtils.getResponseFormatByResource(
587 componentsUtils.convertFromStorageResponse(updateResultEither.right().value()), component.getName()
589 throw new BusinessLogicException(responseFormat);
592 return updateResultEither.left().value();
595 private boolean isPropertyExistInComponent(List<PropertyDefinition> properties, String propertyName) {
596 if(CollectionUtils.isEmpty(properties)) {
600 Optional<PropertyDefinition> propertyCandidate =
601 properties.stream().filter(property -> property.getName().equals(propertyName))
604 return propertyCandidate.isPresent();
607 private StorageOperationStatus validateAndUpdateProperty(IComplexDefaultValue propertyDefinition, Map<String, DataTypeDefinition> dataTypes) {
609 log.trace("Going to validate property type and value. {}", propertyDefinition);
611 String propertyType = propertyDefinition.getType();
612 String value = propertyDefinition.getDefaultValue();
614 ToscaPropertyType type = getType(propertyType);
617 DataTypeDefinition dataTypeDefinition = dataTypes.get(propertyType);
618 if (dataTypeDefinition == null) {
619 log.debug("The type {} of property cannot be found.", propertyType);
620 return StorageOperationStatus.INVALID_TYPE;
622 return validateAndUpdateComplexValue(propertyDefinition, propertyType, value, dataTypeDefinition, dataTypes);
626 Either<String, JanusGraphOperationStatus> checkInnerType = getInnerType(type, propertyDefinition::getSchema);
627 if (checkInnerType.isRight()) {
628 return StorageOperationStatus.INVALID_TYPE;
630 innerType = checkInnerType.left().value();
632 log.trace("After validating property type {}", propertyType);
634 boolean isValidProperty = isValidValue(type, value, innerType, dataTypes);
635 if (!isValidProperty) {
636 log.info("The value {} of property from type {} is invalid", value, type);
637 return StorageOperationStatus.INVALID_VALUE;
640 PropertyValueConverter converter = type.getConverter();
642 if (isEmptyValue(value)) {
643 log.debug("Default value was not sent for property {}. Set default value to {}", propertyDefinition.getName(), EMPTY_VALUE);
644 propertyDefinition.setDefaultValue(EMPTY_VALUE);
645 } else if (!isEmptyValue(value)) {
646 String convertedValue = converter.convert(value, innerType, dataTypes);
647 propertyDefinition.setDefaultValue(convertedValue);
649 return StorageOperationStatus.OK;
652 private StorageOperationStatus validateAndUpdateComplexValue(IComplexDefaultValue propertyDefinition, String propertyType,
653 String value, DataTypeDefinition dataTypeDefinition, Map<String, DataTypeDefinition> dataTypes) {
655 ImmutablePair<JsonElement, Boolean> validateResult = dataTypeValidatorConverter.validateAndUpdate(value, dataTypeDefinition, dataTypes);
657 if (validateResult.right) {
658 log.debug("The value {} of property from type {} is invalid", propertyType, propertyType);
659 return StorageOperationStatus.INVALID_VALUE;
662 JsonElement jsonElement = validateResult.left;
664 log.trace("Going to update value in property definition {} {}" , propertyDefinition.getName() , jsonElement);
666 updateValue(propertyDefinition, jsonElement);
668 return StorageOperationStatus.OK;
671 private void updateValue(IComplexDefaultValue propertyDefinition, JsonElement jsonElement) {
673 propertyDefinition.setDefaultValue(getValueFromJsonElement(jsonElement));
678 protected String getValueFromJsonElement(JsonElement jsonElement) {
679 if (jsonElement == null || jsonElement.isJsonNull()) {
682 if(jsonElement.toString().isEmpty()){
685 return jsonElement.toString();
688 private Either<String, JanusGraphOperationStatus> getInnerType(ToscaPropertyType type, Supplier<SchemaDefinition> schemeGen) {
689 String innerType = null;
690 if (type == ToscaPropertyType.LIST || type == ToscaPropertyType.MAP) {
692 SchemaDefinition def = schemeGen.get();
694 log.debug("Schema doesn't exists for property of type {}", type);
695 return Either.right(JanusGraphOperationStatus.ILLEGAL_ARGUMENT);
697 PropertyDataDefinition propDef = def.getProperty();
698 if (propDef == null) {
699 log.debug("Property in Schema Definition inside property of type {} doesn't exist", type);
700 return Either.right(JanusGraphOperationStatus.ILLEGAL_ARGUMENT);
702 innerType = propDef.getType();
704 return Either.left(innerType);
708 protected boolean isValidValue(ToscaPropertyType type, String value, String innerType, Map<String, DataTypeDefinition> dataTypes) {
709 if (isEmptyValue(value)) {
712 PropertyTypeValidator validator = type.getValidator();
713 return validator.isValid(value, innerType, dataTypes);
717 public boolean isEmptyValue(String value) {
718 return value == null;