From 9991ef5542b0f103c68daa5e6066594cb6ace8f8 Mon Sep 17 00:00:00 2001 From: Tihomir Surdilovic Date: Sat, 4 Sep 2021 18:15:45 -0400 Subject: [PATCH] Update error handling and retries Signed-off-by: Tihomir Surdilovic --- .../api/deserializers/ErrorsDeserializer.java | 107 ++++++++++++++++++ .../api/mapper/WorkflowModule.java | 1 + .../api/serializers/WorkflowSerializer.java | 16 +++ .../api/workflow/Errors.java | 52 +++++++++ .../main/resources/schema/actions/action.json | 20 ++++ .../main/resources/schema/error/error.json | 20 ++-- .../main/resources/schema/error/errordef.json | 23 ++++ api/src/main/resources/schema/workflow.json | 10 ++ .../api/test/MarkupToWorkflowTest.java | 36 ++++++ .../resources/examples/jobmonitoring.json | 2 +- .../test/resources/examples/jobmonitoring.yml | 2 +- .../resources/examples/provisionorder.json | 6 +- .../resources/examples/provisionorder.yml | 6 +- api/src/test/resources/features/errors.json | 38 +++++++ api/src/test/resources/features/errors.yml | 26 +++++ .../test/resources/features/retriesprops.json | 4 +- .../test/resources/features/retriesprops.yml | 4 +- .../resources/features/vetappointment.json | 4 +- .../resources/features/vetappointment.yml | 4 +- .../resources/examples/jobmonitoring.json | 2 +- .../test/resources/examples/jobmonitoring.yml | 2 +- .../resources/examples/provisionorder.json | 6 +- .../resources/examples/provisionorder.yml | 6 +- .../validation/WorkflowValidatorImpl.java | 28 ----- 24 files changed, 358 insertions(+), 67 deletions(-) create mode 100644 api/src/main/java/io/serverlessworkflow/api/deserializers/ErrorsDeserializer.java create mode 100644 api/src/main/java/io/serverlessworkflow/api/workflow/Errors.java create mode 100644 api/src/main/resources/schema/error/errordef.json create mode 100644 api/src/test/resources/features/errors.json create mode 100644 api/src/test/resources/features/errors.yml diff --git a/api/src/main/java/io/serverlessworkflow/api/deserializers/ErrorsDeserializer.java b/api/src/main/java/io/serverlessworkflow/api/deserializers/ErrorsDeserializer.java new file mode 100644 index 00000000..32db6447 --- /dev/null +++ b/api/src/main/java/io/serverlessworkflow/api/deserializers/ErrorsDeserializer.java @@ -0,0 +1,107 @@ +/* + * Copyright 2020-Present The Serverless Workflow Specification Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package io.serverlessworkflow.api.deserializers; + +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.databind.DeserializationContext; +import com.fasterxml.jackson.databind.JsonNode; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.deser.std.StdDeserializer; +import com.fasterxml.jackson.dataformat.yaml.YAMLFactory; +import io.serverlessworkflow.api.error.ErrorDefinition; +import io.serverlessworkflow.api.interfaces.WorkflowPropertySource; +import io.serverlessworkflow.api.utils.Utils; +import io.serverlessworkflow.api.workflow.Errors; +import org.json.JSONObject; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +public class ErrorsDeserializer extends StdDeserializer { + + private static final long serialVersionUID = 510l; + private static Logger logger = LoggerFactory.getLogger(ErrorsDeserializer.class); + + @SuppressWarnings("unused") + private WorkflowPropertySource context; + + public ErrorsDeserializer() { + this(Errors.class); + } + + public ErrorsDeserializer(Class vc) { + super(vc); + } + + public ErrorsDeserializer(WorkflowPropertySource context) { + this(Errors.class); + this.context = context; + } + + @Override + public Errors deserialize(JsonParser jp, + DeserializationContext ctxt) throws IOException { + + ObjectMapper mapper = (ObjectMapper) jp.getCodec(); + JsonNode node = jp.getCodec().readTree(jp); + + Errors errors = new Errors(); + List errorDefinitions = new ArrayList<>(); + + if (node.isArray()) { + for (final JsonNode nodeEle : node) { + errorDefinitions.add(mapper.treeToValue(nodeEle, ErrorDefinition.class)); + } + } else { + String errorsFileDef = node.asText(); + String errorsFileSrc = Utils.getResourceFileAsString(errorsFileDef); + JsonNode errorsRefNode; + ObjectMapper jsonWriter = new ObjectMapper(); + if (errorsFileSrc != null && errorsFileSrc.trim().length() > 0) { + // if its a yaml def convert to json first + if (!errorsFileSrc.trim().startsWith("{")) { + // convert yaml to json to validate + ObjectMapper yamlReader = new ObjectMapper(new YAMLFactory()); + Object obj = yamlReader.readValue(errorsFileSrc, Object.class); + + errorsRefNode = jsonWriter.readTree(new JSONObject(jsonWriter.writeValueAsString(obj)).toString()); + } else { + errorsRefNode = jsonWriter.readTree(new JSONObject(errorsFileSrc).toString()); + } + + JsonNode refErrors = errorsRefNode.get("errors"); + if (refErrors != null) { + for (final JsonNode nodeEle : refErrors) { + errorDefinitions.add(mapper.treeToValue(nodeEle, ErrorDefinition.class)); + } + } else { + logger.error("Unable to find error definitions in reference file: {}", errorsFileSrc); + } + + } else { + logger.error("Unable to load errors defs reference file: {}", errorsFileSrc); + } + + } + errors.setErrorDefs(errorDefinitions); + return errors; + + } +} + diff --git a/api/src/main/java/io/serverlessworkflow/api/mapper/WorkflowModule.java b/api/src/main/java/io/serverlessworkflow/api/mapper/WorkflowModule.java index 890fd824..d5d0e1bd 100644 --- a/api/src/main/java/io/serverlessworkflow/api/mapper/WorkflowModule.java +++ b/api/src/main/java/io/serverlessworkflow/api/mapper/WorkflowModule.java @@ -112,6 +112,7 @@ private void addDefaultDeserializers() { addDeserializer(DataInputSchema.class, new DataInputSchemaDeserializer(workflowPropertySource)); addDeserializer(AuthDefinition.class, new AuthDefinitionDeserializer(workflowPropertySource)); addDeserializer(StateExecTimeout.class, new StateExecTimeoutDeserializer(workflowPropertySource)); + addDeserializer(Errors.class, new ErrorsDeserializer(workflowPropertySource)); } public ExtensionSerializer getExtensionSerializer() { diff --git a/api/src/main/java/io/serverlessworkflow/api/serializers/WorkflowSerializer.java b/api/src/main/java/io/serverlessworkflow/api/serializers/WorkflowSerializer.java index dc729731..5c889838 100644 --- a/api/src/main/java/io/serverlessworkflow/api/serializers/WorkflowSerializer.java +++ b/api/src/main/java/io/serverlessworkflow/api/serializers/WorkflowSerializer.java @@ -20,6 +20,7 @@ import com.fasterxml.jackson.databind.SerializerProvider; import com.fasterxml.jackson.databind.ser.std.StdSerializer; import io.serverlessworkflow.api.Workflow; +import io.serverlessworkflow.api.error.ErrorDefinition; import io.serverlessworkflow.api.events.EventDefinition; import io.serverlessworkflow.api.functions.FunctionDefinition; import io.serverlessworkflow.api.interfaces.Extension; @@ -102,6 +103,10 @@ public void serialize(Workflow workflow, gen.writeBooleanField("keepActive", workflow.isKeepActive()); } + if (workflow.isAutoRetries()) { + gen.writeBooleanField("autoRetries", workflow.isAutoRetries()); + } + if (workflow.getMetadata() != null && !workflow.getMetadata().isEmpty()) { gen.writeObjectField("metadata", workflow.getMetadata()); @@ -140,6 +145,17 @@ public void serialize(Workflow workflow, gen.writeEndArray(); } + if (workflow.getErrors() != null && !workflow.getErrors().getErrorDefs().isEmpty()) { + gen.writeArrayFieldStart("errors"); + for (ErrorDefinition error : workflow.getErrors().getErrorDefs()) { + gen.writeObject(error); + } + gen.writeEndArray(); + } else { + gen.writeArrayFieldStart("errors"); + gen.writeEndArray(); + } + if (workflow.getSecrets() != null && !workflow.getSecrets().getSecretDefs().isEmpty()) { gen.writeArrayFieldStart("secrets"); for (String secretDef : workflow.getSecrets().getSecretDefs()) { diff --git a/api/src/main/java/io/serverlessworkflow/api/workflow/Errors.java b/api/src/main/java/io/serverlessworkflow/api/workflow/Errors.java new file mode 100644 index 00000000..44c7c685 --- /dev/null +++ b/api/src/main/java/io/serverlessworkflow/api/workflow/Errors.java @@ -0,0 +1,52 @@ +/* + * Copyright 2020-Present The Serverless Workflow Specification Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package io.serverlessworkflow.api.workflow; + +import io.serverlessworkflow.api.error.ErrorDefinition; + +import java.util.List; + +public class Errors { + private String refValue; + private List errorDefs; + + public Errors() { + } + + public Errors(List errorDefs) { + this.errorDefs = errorDefs; + } + + public Errors(String refValue) { + this.refValue = refValue; + } + + public String getRefValue() { + return refValue; + } + + public void setRefValue(String refValue) { + this.refValue = refValue; + } + + public List getErrorDefs() { + return errorDefs; + } + + public void setErrorDefs(List errorDefs) { + this.errorDefs = errorDefs; + } +} diff --git a/api/src/main/resources/schema/actions/action.json b/api/src/main/resources/schema/actions/action.json index b2accd1d..8dc80780 100644 --- a/api/src/main/resources/schema/actions/action.json +++ b/api/src/main/resources/schema/actions/action.json @@ -22,6 +22,26 @@ "sleep": { "$ref": "../sleep/sleep.json" }, + "retryRef": { + "type": "string", + "description": "References a defined workflow retry definition. If not defined the default retry policy is assumed" + }, + "nonRetryableErrors": { + "type": "array", + "description": "List of unique references to defined workflow errors for which the action should not be retried. Used only when `autoRetries` is set to `true`", + "minItems": 1, + "items": { + "type": "string" + } + }, + "retryableErrors": { + "type": "array", + "description": "List of unique references to defined workflow errors for which the action should be retried. Used only when `autoRetries` is set to `false`", + "minItems": 1, + "items": { + "type": "string" + } + }, "actionDataFilter": { "$ref": "../filters/actiondatafilter.json" } diff --git a/api/src/main/resources/schema/error/error.json b/api/src/main/resources/schema/error/error.json index c3996430..c51860de 100644 --- a/api/src/main/resources/schema/error/error.json +++ b/api/src/main/resources/schema/error/error.json @@ -2,20 +2,18 @@ "type": "object", "javaType": "io.serverlessworkflow.api.error.Error", "properties": { - "error": { + "errorRef": { "type": "string", - "description": "Domain-specific error name, or '*' to indicate all possible errors", + "description": "Reference to a unique workflow error definition. Used of errorRefs is not used", "minLength": 1 }, - "code": { - "type": "string", - "description": "Error code. Can be used in addition to the name to help runtimes resolve to technical errors/exceptions. Should not be defined if error is set to '*'", - "minLength": 1 - }, - "retryRef": { - "type": "string", - "description": "References a unique name of a retry definition.", - "minLength": 1 + "errorRefs": { + "type": "array", + "description": "References one or more workflow error definitions. Used if errorRef is not used", + "minItems": 1, + "items": { + "type": "string" + } }, "transition": { "$ref": "../transitions/transition.json", diff --git a/api/src/main/resources/schema/error/errordef.json b/api/src/main/resources/schema/error/errordef.json new file mode 100644 index 00000000..613d3cbf --- /dev/null +++ b/api/src/main/resources/schema/error/errordef.json @@ -0,0 +1,23 @@ +{ + "type": "object", + "javaType": "io.serverlessworkflow.api.error.ErrorDefinition", + "properties": { + "name": { + "type": "string", + "description": "Domain-specific error name", + "minLength": 1 + }, + "code": { + "type": "string", + "description": "Error code. Can be used in addition to the name to help runtimes resolve to technical errors/exceptions. Should not be defined if error is set to '*'", + "minLength": 1 + }, + "description": { + "type": "string", + "description": "Error description" + } + }, + "required": [ + "name" + ] +} \ No newline at end of file diff --git a/api/src/main/resources/schema/workflow.json b/api/src/main/resources/schema/workflow.json index 15b3fbb1..19164ca5 100644 --- a/api/src/main/resources/schema/workflow.json +++ b/api/src/main/resources/schema/workflow.json @@ -50,6 +50,11 @@ "default": false, "description": "If 'true', workflow instances is not terminated when there are no active execution paths. Instance can be terminated via 'terminate end definition' or reaching defined 'execTimeout'" }, + "autoRetries": { + "type": "boolean", + "default": false, + "description": "If set to true, actions should automatically be retried on unchecked errors. Default is false" + }, "metadata": { "$ref": "metadata/metadata.json" }, @@ -63,6 +68,11 @@ "existingJavaType": "io.serverlessworkflow.api.workflow.Functions", "description": "Workflow function definitions" }, + "errors": { + "type": "object", + "existingJavaType": "io.serverlessworkflow.api.workflow.Errors", + "description": "Workflow error definitions" + }, "retries": { "type": "object", "existingJavaType": "io.serverlessworkflow.api.workflow.Retries", diff --git a/api/src/test/java/io/serverlessworkflow/api/test/MarkupToWorkflowTest.java b/api/src/test/java/io/serverlessworkflow/api/test/MarkupToWorkflowTest.java index 066053ff..abb4ed7e 100644 --- a/api/src/test/java/io/serverlessworkflow/api/test/MarkupToWorkflowTest.java +++ b/api/src/test/java/io/serverlessworkflow/api/test/MarkupToWorkflowTest.java @@ -700,4 +700,40 @@ public void testActionsSleep(String workflowLocation) { assertEquals("${ .customer }", functionRef2.getArguments().get("applicant").asText()); } + + @ParameterizedTest + @ValueSource(strings = {"/features/errors.json", "/features/errors.yml"}) + public void testErrorsParams(String workflowLocation) { + Workflow workflow = Workflow.fromSource(WorkflowTestUtils.readWorkflowFile(workflowLocation)); + + assertNotNull(workflow); + assertNotNull(workflow.getId()); + assertNotNull(workflow.getName()); + assertNotNull(workflow.getStates()); + assertTrue(workflow.isAutoRetries()); + + assertNotNull(workflow.getStates()); + assertEquals(1, workflow.getStates().size()); + + assertNotNull(workflow.getErrors()); + assertEquals(2, workflow.getErrors().getErrorDefs().size()); + + assertTrue(workflow.getStates().get(0) instanceof OperationState); + + OperationState operationState = (OperationState) workflow.getStates().get(0); + assertNotNull(operationState.getActions()); + assertEquals(1, operationState.getActions().size()); + List actions = operationState.getActions(); + assertNotNull(actions.get(0).getFunctionRef()); + assertEquals("addPet", actions.get(0).getFunctionRef().getRefName()); + assertNotNull(actions.get(0).getRetryRef()); + assertEquals("testRetry", actions.get(0).getRetryRef()); + assertNotNull(actions.get(0).getNonRetryableErrors()); + assertEquals(2, actions.get(0).getNonRetryableErrors().size()); + + assertNotNull(operationState.getOnErrors()); + assertEquals(1, operationState.getOnErrors().size()); + assertNotNull(operationState.getOnErrors().get(0).getErrorRefs()); + assertEquals(2, operationState.getOnErrors().get(0).getErrorRefs().size()); + } } diff --git a/api/src/test/resources/examples/jobmonitoring.json b/api/src/test/resources/examples/jobmonitoring.json index 6951bce0..186eb2dc 100644 --- a/api/src/test/resources/examples/jobmonitoring.json +++ b/api/src/test/resources/examples/jobmonitoring.json @@ -43,7 +43,7 @@ ], "onErrors": [ { - "error": "*", + "errorRef": "AllErrors", "transition": "SubmitError" } ], diff --git a/api/src/test/resources/examples/jobmonitoring.yml b/api/src/test/resources/examples/jobmonitoring.yml index 4e0fcfc0..76dc4a7a 100644 --- a/api/src/test/resources/examples/jobmonitoring.yml +++ b/api/src/test/resources/examples/jobmonitoring.yml @@ -25,7 +25,7 @@ states: actionDataFilter: results: "${ .jobuid }" onErrors: - - error: "*" + - errorRef: "AllErrors" transition: SubmitError stateDataFilter: output: "${ .jobuid }" diff --git a/api/src/test/resources/examples/provisionorder.json b/api/src/test/resources/examples/provisionorder.json index b3839507..f6a8e446 100644 --- a/api/src/test/resources/examples/provisionorder.json +++ b/api/src/test/resources/examples/provisionorder.json @@ -32,15 +32,15 @@ "transition": "ApplyOrder", "onErrors": [ { - "error": "Missing order id", + "errorRef": "Missing order id", "transition": "MissingId" }, { - "error": "Missing order item", + "errorRef": "Missing order item", "transition": "MissingItem" }, { - "error": "Missing order quantity", + "errorRef": "Missing order quantity", "transition": "MissingQuantity" } ] diff --git a/api/src/test/resources/examples/provisionorder.yml b/api/src/test/resources/examples/provisionorder.yml index 431cab2c..37e5147d 100644 --- a/api/src/test/resources/examples/provisionorder.yml +++ b/api/src/test/resources/examples/provisionorder.yml @@ -20,11 +20,11 @@ states: output: "${ .exceptions }" transition: ApplyOrder onErrors: - - error: Missing order id + - errorRef: Missing order id transition: MissingId - - error: Missing order item + - errorRef: Missing order item transition: MissingItem - - error: Missing order quantity + - errorRef: Missing order quantity transition: MissingQuantity - name: MissingId type: operation diff --git a/api/src/test/resources/features/errors.json b/api/src/test/resources/features/errors.json new file mode 100644 index 00000000..27b969ba --- /dev/null +++ b/api/src/test/resources/features/errors.json @@ -0,0 +1,38 @@ +{ + "id": "functionrefparams", + "version": "1.0", + "specVersion": "0.7", + "name": "Function Ref Params Test", + "start": "AddPluto", + "autoRetries": true, + "errors": [ + { + "name": "ErrorA", + "code": "400" + }, + { + "name": "ErrorB", + "code": "500" + } + ], + "states": [ + { + "name": "AddPluto", + "type": "operation", + "actions": [ + { + "functionRef": "addPet", + "retryRef": "testRetry", + "nonRetryableErrors": ["A", "B"] + } + ], + "onErrors": [ + { + "errorRefs": ["A", "B"], + "end": true + } + ], + "end": true + } + ] +} \ No newline at end of file diff --git a/api/src/test/resources/features/errors.yml b/api/src/test/resources/features/errors.yml new file mode 100644 index 00000000..603d062f --- /dev/null +++ b/api/src/test/resources/features/errors.yml @@ -0,0 +1,26 @@ +id: functionrefparams +version: '1.0' +specVersion: '0.7' +name: Function Ref Params Test +start: AddPluto +autoRetries: true +errors: + - name: ErrorA + code: '400' + - name: ErrorB + code: '500' +states: + - name: AddPluto + type: operation + actions: + - functionRef: addPet + retryRef: testRetry + nonRetryableErrors: + - A + - B + onErrors: + - errorRefs: + - A + - B + end: true + end: true diff --git a/api/src/test/resources/features/retriesprops.json b/api/src/test/resources/features/retriesprops.json index bfcd8f19..1a6a191e 100644 --- a/api/src/test/resources/features/retriesprops.json +++ b/api/src/test/resources/features/retriesprops.json @@ -23,9 +23,7 @@ ], "onErrors": [ { - "error": "TimeoutError", - "code": "500", - "retryRef": "Test Retries", + "errorRef": "TimeoutError", "end": true } ], diff --git a/api/src/test/resources/features/retriesprops.yml b/api/src/test/resources/features/retriesprops.yml index bba18a47..a91614cd 100644 --- a/api/src/test/resources/features/retriesprops.yml +++ b/api/src/test/resources/features/retriesprops.yml @@ -16,8 +16,6 @@ states: type: operation actions: [] onErrors: - - error: TimeoutError - code: '500' - retryRef: Test Retries + - errorRef: TimeoutError end: true end: true diff --git a/api/src/test/resources/features/vetappointment.json b/api/src/test/resources/features/vetappointment.json index 17315d96..b8d39aa2 100644 --- a/api/src/test/resources/features/vetappointment.json +++ b/api/src/test/resources/features/vetappointment.json @@ -29,9 +29,7 @@ }, "onErrors": [ { - "error": "TimeoutError", - "code": "500", - "retryRef": "TimeoutRetryStrategy", + "errorRef": "TimeoutError", "end": true } ], diff --git a/api/src/test/resources/features/vetappointment.yml b/api/src/test/resources/features/vetappointment.yml index 2a1705ea..d56a13be 100644 --- a/api/src/test/resources/features/vetappointment.yml +++ b/api/src/test/resources/features/vetappointment.yml @@ -20,8 +20,6 @@ states: timeouts: actionExecTimeout: PT15M onErrors: - - error: TimeoutError - code: '500' - retryRef: TimeoutRetryStrategy + - errorRef: TimeoutError end: true end: true diff --git a/diagram/src/test/resources/examples/jobmonitoring.json b/diagram/src/test/resources/examples/jobmonitoring.json index 6951bce0..186eb2dc 100644 --- a/diagram/src/test/resources/examples/jobmonitoring.json +++ b/diagram/src/test/resources/examples/jobmonitoring.json @@ -43,7 +43,7 @@ ], "onErrors": [ { - "error": "*", + "errorRef": "AllErrors", "transition": "SubmitError" } ], diff --git a/diagram/src/test/resources/examples/jobmonitoring.yml b/diagram/src/test/resources/examples/jobmonitoring.yml index 4e0fcfc0..76dc4a7a 100644 --- a/diagram/src/test/resources/examples/jobmonitoring.yml +++ b/diagram/src/test/resources/examples/jobmonitoring.yml @@ -25,7 +25,7 @@ states: actionDataFilter: results: "${ .jobuid }" onErrors: - - error: "*" + - errorRef: "AllErrors" transition: SubmitError stateDataFilter: output: "${ .jobuid }" diff --git a/diagram/src/test/resources/examples/provisionorder.json b/diagram/src/test/resources/examples/provisionorder.json index b3839507..f6a8e446 100644 --- a/diagram/src/test/resources/examples/provisionorder.json +++ b/diagram/src/test/resources/examples/provisionorder.json @@ -32,15 +32,15 @@ "transition": "ApplyOrder", "onErrors": [ { - "error": "Missing order id", + "errorRef": "Missing order id", "transition": "MissingId" }, { - "error": "Missing order item", + "errorRef": "Missing order item", "transition": "MissingItem" }, { - "error": "Missing order quantity", + "errorRef": "Missing order quantity", "transition": "MissingQuantity" } ] diff --git a/diagram/src/test/resources/examples/provisionorder.yml b/diagram/src/test/resources/examples/provisionorder.yml index 431cab2c..37e5147d 100644 --- a/diagram/src/test/resources/examples/provisionorder.yml +++ b/diagram/src/test/resources/examples/provisionorder.yml @@ -20,11 +20,11 @@ states: output: "${ .exceptions }" transition: ApplyOrder onErrors: - - error: Missing order id + - errorRef: Missing order id transition: MissingId - - error: Missing order item + - errorRef: Missing order item transition: MissingItem - - error: Missing order quantity + - errorRef: Missing order quantity transition: MissingQuantity - name: MissingId type: operation diff --git a/validation/src/main/java/io/serverlessworkflow/validation/WorkflowValidatorImpl.java b/validation/src/main/java/io/serverlessworkflow/validation/WorkflowValidatorImpl.java index 29cb3ed3..84e0de4a 100644 --- a/validation/src/main/java/io/serverlessworkflow/validation/WorkflowValidatorImpl.java +++ b/validation/src/main/java/io/serverlessworkflow/validation/WorkflowValidatorImpl.java @@ -169,34 +169,6 @@ public List validate() { validation.addEndState(); } - if (workflow.getRetries() != null) { - List retryDefs = workflow.getRetries().getRetryDefs(); - if (s.getOnErrors() == null || s.getOnErrors().isEmpty()) { - addValidationError("No onErrors found for state" + s.getName() + " but retries is defined", - ValidationError.WORKFLOW_VALIDATION); - } else { - for (Error e : s.getOnErrors()) { - if (e.getRetryRef() == null || e.getRetryRef().isEmpty()) { - addValidationError("No retryRef found for onErrors" + e.getError(), - ValidationError.WORKFLOW_VALIDATION); - } else { - boolean validRetryDefinition = false; - for (RetryDefinition rd : retryDefs) { - if (rd.getName().equals(e.getRetryRef())) { - validRetryDefinition = true; - break; - } - } - if (!validRetryDefinition) { - addValidationError(e.getRetryRef() + " is not a valid retryRef", - ValidationError.WORKFLOW_VALIDATION); - } - } - } - } - } - - if (s instanceof OperationState) { OperationState operationState = (OperationState) s; pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy