mirror of
https://github.com/kestra-io/kestra.git
synced 2025-12-19 18:05:41 -05:00
feat(core): improve exception handling and validation with Inputs/Outputs
- Added InputOutputValidationException to represent Inputs/Outputs validation issues and added handler to it in ErrorsController - Added support for throwing multiple constraint violations for the same input - Added support for throwing multiple constraints at MultiselectInput - Refactored exception handling at FlowInputOutput - Added merge() function to combine constraint violation messages and added test for it at InputsTest - Fixed the failed tests
This commit is contained in:
committed by
Florian Hussonnois
parent
22f0b3ffdf
commit
f409657e8a
@@ -36,6 +36,10 @@ public class ErrorController {
|
||||
public HttpResponse<JsonError> error(HttpRequest<?> request, JsonParseException e) {
|
||||
return jsonError(request, e, HttpStatus.UNPROCESSABLE_ENTITY, "Invalid json");
|
||||
}
|
||||
@Error(global = true)
|
||||
public HttpResponse<JsonError> error(HttpRequest<?> request, InputOutputValidationException e) {
|
||||
return jsonError(request, e, HttpStatus.UNPROCESSABLE_ENTITY, "Invalid entity");
|
||||
}
|
||||
|
||||
@Error(global = true)
|
||||
public HttpResponse<JsonError> error(HttpRequest<?> request, ConversionErrorException e) {
|
||||
|
||||
@@ -2670,7 +2670,12 @@ public class ExecutionController {
|
||||
) {
|
||||
}
|
||||
|
||||
public static ApiValidateExecutionInputsResponse of(String id, String namespace, List<Check> checks, List<InputAndValue> inputs) {
|
||||
public static ApiValidateExecutionInputsResponse of(
|
||||
String id,
|
||||
String namespace,
|
||||
List<Check> checks,
|
||||
List<InputAndValue> inputs
|
||||
) {
|
||||
return new ApiValidateExecutionInputsResponse(
|
||||
id,
|
||||
namespace,
|
||||
@@ -2679,14 +2684,21 @@ public class ExecutionController {
|
||||
it.value(),
|
||||
it.enabled(),
|
||||
it.isDefault(),
|
||||
Optional.ofNullable(it.exception()).map(exception ->
|
||||
exception.getConstraintViolations()
|
||||
.stream()
|
||||
.map(cv -> new ApiInputError(cv.getMessage()))
|
||||
// Map the Set<InputOutputValidationException> to ApiInputError
|
||||
Optional.ofNullable(it.exceptions())
|
||||
.map(exSet -> exSet.stream()
|
||||
.map(e -> new ApiInputError(e.getMessage()))
|
||||
.toList()
|
||||
).orElse(List.of())
|
||||
)
|
||||
.orElse(List.of())
|
||||
)).toList(),
|
||||
checks.stream().map(check -> new ApiCheckFailure(check.getMessage(), check.getStyle(), check.getBehavior())).toList()
|
||||
checks.stream()
|
||||
.map(check -> new ApiCheckFailure(
|
||||
check.getMessage(),
|
||||
check.getStyle(),
|
||||
check.getBehavior()
|
||||
))
|
||||
.toList()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -242,7 +242,7 @@ class ExecutionControllerRunnerTest {
|
||||
String response = e.getResponse().getBody(String.class).orElseThrow();
|
||||
|
||||
assertThat(response).contains("Invalid entity");
|
||||
assertThat(response).contains("Invalid input for `validatedString`");
|
||||
assertThat(response).contains("Invalid value for input `validatedString`");
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -1071,7 +1071,7 @@ class ExecutionControllerRunnerTest {
|
||||
.contentType(MediaType.MULTIPART_FORM_DATA_TYPE)
|
||||
));
|
||||
assertThat(exception.getStatus().getCode()).isEqualTo(422);
|
||||
assertThat(exception.getMessage()).isEqualTo("Invalid entity: asked: Invalid input for `asked`, missing required input, but received `null`");
|
||||
assertThat(exception.getMessage()).isEqualTo("Invalid entity: Missing required input:asked");
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
Reference in New Issue
Block a user