skip to Main Content

I created a "checklist" field with the following definition:

$this->crud->addField(
                [   // Checklist
                    'label'     => '<b>IDIOMAS</b>',
                    'type'      => 'checklist',
                    'name'      => 'idiomas',
                    'entity'    => 'idiomas',
                    'attribute' => 'titulo',
                    'model'     => "AppModelsIdioma",
                    'pivot'     => false,
                    'number_of_columns' => 3,
                    'wrapper' => [
                        'class' => 'form-group col-md-6',
                    ],
                    'tab' => 'HABILIDADES',
                ]
            );

I tried to validate with the following rules:

'idiomas' => 'required|array|min:1',
//'idiomas.*' => 'required|integer|exists:idiomas,id',

With the intention of forcing at least some element to be required. I did a lot of tests, the first one was just to use the "required" option, but nothing worked.

Reviewing the form that prints in html, I see that at the end there is a hidden field as follows:

<input type="hidden" value="[]" name="idiomas">

So for validation we receive "[]" which is NOT an array and cannot be validated that way. Shouldn’t it be an array that you send? Because now it is a string of 2 characters that skips the validation of "required".
For the moment what I did was to set the rule:

'idiomas' => 'required|min:3'

And change the validation message with:

'idiomas.min' => 'Debe seleccionar al menos un elemento'

But I was left with the doubt: Is there a better way?

Is the way Backpack Laravel returns the value to validate correct?

Should it be an array?

2

Answers


  1. If you want to validate at least 1 element, can use something like this:

    return [
            'idiomas' => [
                'required',
                'string',
                'json',
                function ($attribute, $value, $fail) {
                    $elementsArray = json_decode($value, true);
    
                    if (empty($elementsArray)) {
                        $fail('The '.$attribute.' must contain at least one element.');
                    }
                },
            ],
        ];
    

    Cheers.

    Login or Signup to reply.
  2. I’m not familiar with Backpack, but if the hidden element’s value at initialization is [] I’m willing to bet it posts its data as a JSON string. To validate it, you’d need to decode the JSON first and then add it back into the request object. Here’s my suggestion:

    <?php
    
    namespace AppHttpRequests;
    
    use IlluminateFoundationHttpFormRequest;
    
    class MyRequest extends FormRequest
    {
        protected function prepareForValidation(): void
        {
            // could also use $this->replace() if desired
            $this->merge([
                "idiomas_data" => json_decode($this->idiomas),
            ]);
        }
    
        public function rules(): array
        {
            return [
                "idiomas_data" => ["required", "array", "min:1"],
                "idiomas_data.*" => ["integer", "exists:idiomas"],
            ];
        }
    }
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search