Search code examples
laravellaravel-8

How to get current value in Laravel form request for array field


The following is from the request

[
    'coupons'                 => 'nullable|array|min:1',
    'coupons.*.code'          => [
                'required', 'string', new CheckCouponValidityForOrder(
                    $this->input('coupons.*.code'), // how to current value at this index?
                    $this->input('coupons.*.product_ids')
                ),
            ],
]

How do I get the code for the current index?


Solution

  • Here is an idea that has not fully tested

    Will be slightly different if you are doing this inside a FormRequest

        $data = $request->all() ?? [
            // sample data
            'coupons' => [
                [
                    'code' => 'coupon1',
                    'product_ids' => [1, 2, 3]
                ],
                [
                    'code' => 'coupon2',
                    'product_ids' => [4, 5, 6]
                ]
            ]
        ];
    
        $rules = [
            'coupons'                 => 'nullable|array|min:1',
            'coupons.*.code'          => [
                'required', 'string', new CheckCouponValidityForOrder($data),
            ],
        ];
    
        $v = Validator::make($data, $rules);
    
    <?php
    
    namespace App\Rules;
    
    use Illuminate\Contracts\Validation\Rule;
    use Illuminate\Support\Facades\Request;
    
    class CheckCouponValidityForOrder implements Rule
    {
        private $data;
    
        /**
         * Create a new rule instance.
         *
         * @return void
         */
        public function __construct(array $data = [])
        {
            $this->data = $data ?: Request::all();
        }
    
        /**
         * Determine if the validation rule passes.
         *
         * @param  string  $attribute
         * @param  mixed  $value
         * @return bool
         */
        public function passes($attribute, $value)
        {
            //  "coupons.0.code" -> "0"
            preg_match('/\d+/', $attribute, $matches);
            $index = $matches[0] ?? null;
    
            // Ensure index exists
            if ($index === null) {
                return false;
            }
    
            $productIds = $this->data['coupons'][$index]['product_ids'] ?? [];
            $code = $this->data['coupons'][$index]['code'] ?? $value;
    
            // Debugging Output
            dd($value, $attribute, $index, $productIds, $code);
        }
    
        /**
         * Get the validation error message.
         *
         * @return string
         */
        public function message()
        {
            return 'The validation error message.';
        }
    }