Positonic
Positonic

Reputation: 9411

Laravel - associative Array validation in a custom request

I have a customer request as follows:

<textarea name="intro[en]"></textarea>
<textarea name="intro[fr]"></textarea>
<textarea name="intro[de]"></textarea>

I am validating it with a custom request:

class UpdateProfileRequest extends Request
{
    public function authorize()
    {
        return true;
    }

    public function rules()
    {
         return [
             'intro.*'           => 'required|max:100'
         ];
    }
}

The validator is not working. I think this is because the .* only works for numbered arrays, rather than associative arrays?

I'm not sure how to go about doing this.

Is there a way to do it with a custom request like this? If so what is the syntax?

Otherwise, what should I do. I already wrote some custom code inside the controller method like this:

    $hasIntro = false;
    $hasBio = false;

    foreach($request->get('intro') as $language => $localIntro)
    {
        if(!empty($request->get('intro')[$language]))
        {
            $hasIntro = true;
        }
    }

    if(!$hasIntro or !$hasBio)
    {
        return redirect()->back()->withErrors('You must enter at least 1 Bio and 1 Intro');
    }

Which I think might be one manual way of going about this. Though I believe withErrors requires a validator, so I'm back to the same problem... Though perhaps there is a way to do this manually?

My ideal solution is to find the associative array syntax, if that indeed exists?

Upvotes: 4

Views: 3824

Answers (3)

Bugfixer
Bugfixer

Reputation: 2617

public function rules()
{
        $rules = [];

        $intro = $this->request->get('intro');

        if (!empty($intro)) {
            foreach ($intro as $index => $doc) {
                $rules[sprintf('intro.%d', $index)] = 'required|max:100';
            }
        }

        return $rules;
    }

Upvotes: 1

Pooja JaJal
Pooja JaJal

Reputation: 293

class UpdateProfileRequest extends Request
    {
        /**
         * Determine if the user is authorized to make this request.
         *
         * @return bool
         */
        public function authorize()
        {
            return true;
        }

        /**
         * Get the validation rules that apply to the request.
         *
         * @return array
         */
        public function rules()
        {
            return [
                'intro.*'               => 'required|max:100'
            ];
        }


        /**
         * @param Validator $validator
         *
         * @return mixed
         */
        protected function formatErrors(Validator $validator)
        {
            return $validator->errors()->all();
        }
    }

You have below same name so make sure it's different or remove one, change name.

<textarea name="intro[fr]"></textarea>
<textarea name="intro[fr]"></textarea>

Upvotes: 1

I'm not sure about the right way but my idea is something like this

public function rules($inputs)
{
    $rules = [];
    foreach ($inputs as $key => $val) {
        if ( strpos($key, "intro") === 0 ){
            $rules[$key] = 'required|max:100';
        }
    }
    return $rules;
}

Upvotes: 1

Related Questions