diff --git a/api/app/Http/Requests/AnswerFormRequest.php b/api/app/Http/Requests/AnswerFormRequest.php index 6431bbef..cb19bb70 100644 --- a/api/app/Http/Requests/AnswerFormRequest.php +++ b/api/app/Http/Requests/AnswerFormRequest.php @@ -87,7 +87,10 @@ class AnswerFormRequest extends FormRequest $data[$field['id']] = isset($tmpop['name']) ? $tmpop['name'] : $data[$field['id']]; } } - if (FormLogicPropertyResolver::isRequired($property, $data)) { + if ( + FormLogicPropertyResolver::isRequired($property, $data) && + !FormLogicPropertyResolver::isHidden($property, $data) + ) { $rules[] = 'required'; if ($property['type'] == 'checkbox') { diff --git a/api/tests/Feature/Forms/FormLogicTest.php b/api/tests/Feature/Forms/FormLogicTest.php index e87560b7..77a5e629 100644 --- a/api/tests/Feature/Forms/FormLogicTest.php +++ b/api/tests/Feature/Forms/FormLogicTest.php @@ -543,3 +543,67 @@ it('handles invalid regex patterns gracefully', function () { 'message' => $validationMessage, ]); }); + +it('skips validation for fields hidden by logic conditions', function () { + $user = $this->actingAsUser(); + $workspace = $this->createUserWorkspace($user); + $form = $this->createForm($user, $workspace, [ + 'properties' => [ + [ + 'id' => 'title', + 'name' => 'Name', + 'type' => 'title', + 'hidden' => false, + 'required' => true, + 'logic' => [ + 'conditions' => [ + 'operatorIdentifier' => 'and', + 'children' => [ + [ + 'identifier' => 'email', + 'value' => [ + 'operator' => 'is_empty', + 'property_meta' => [ + 'id' => 'email_field', + 'type' => 'email', + ], + 'value' => true, + ], + ], + ], + ], + 'actions' => ['hide-block'], + ], + ], + [ + 'id' => 'email_field', + 'name' => 'Email', + 'type' => 'email', + 'hidden' => false, + 'required' => false, + ], + ], + ]); + + // Test when field should be hidden (email is empty) + $formData = ['email_field' => '']; // Empty email + $this->postJson(route('forms.answer', $form->slug), $formData) + ->assertSuccessful() + ->assertJson([ + 'type' => 'success', + 'message' => 'Form submission saved.', + ]); + + // Test when field should be visible (email is not empty) + $formData = ['email_field' => 'test@example.com']; + $this->postJson(route('forms.answer', $form->slug), $formData) + ->assertStatus(422) + ->assertJson([ + 'message' => 'The Name field is required.', + 'errors' => [ + 'title' => [ + 'The Name field is required.', + ], + ], + ]); +}); diff --git a/client/components/open/forms/components/form-logic-components/FormBlockLogicEditor.vue b/client/components/open/forms/components/form-logic-components/FormBlockLogicEditor.vue index 62898159..1ab33123 100644 --- a/client/components/open/forms/components/form-logic-components/FormBlockLogicEditor.vue +++ b/client/components/open/forms/components/form-logic-components/FormBlockLogicEditor.vue @@ -45,6 +45,9 @@
2. Actions
+

+ Action(s) triggered when above conditions are true. +

+

+ Note that hidden fields can never be required. +

+