My Laravel Backend receives a JSON converted Javascript Array and decodes it into the following php array:
dd($cart) EDITED Keys Changed
array:4 [▼
"personcount" => 2
"person1" => array:2 [▼
"Customer" => array:2 [▶]
"Items" => array:5 [▼
"key1" => 0
"key2" => 0
"key3" => 0
"key4" => 0
"key5" => 1
]
]
"person2" => array:2 [▼
"Customer" => array:2 [▶]
"Items" => array:5 [▶]
]
]
I created a Filter Middleware which should validate the given array and redirect back in case of failure.
Filter.php EDITED added new (not working) validation rule approach
$cart = json_decode($request->input('cart'), true);
$validation_rules = [];
$TotalItemCount = 0;
for ($i = 1; $i <= $person_count; $i++) {
foreach ($cart[$i]["Items"] as $Item => $ItemCount) {
$TotalItemCount += $ItemCount;
}
$validation_rules += [
"person$i.Customer.FirstName" => "required|string|min:2|max:255",
"person$i.Customer.LastName" => "required|string|min:2|max:255",
"person$i.Items.*" => "required|numeric",
"person$i.Items" => ['required', 'array',
Rule::in(["Key1", "Items"]),
],
];
}
$validated_input = Validator::make($cart, $validation_rules);
It seems like the validator is ignoring the $i.Items validation rules. I even changed size:5 to size:6 which had to fire an error 100% because the given Item Array always contains only 5 elements.
Furthermore I tried to Validate array keys:
"$i.Items" => "required|array:key1,key2,key3"
It also didn't fire at all. I want all keys to be required. The firstName/Lastname rules apply.
I'm happy for suggestions.
Doing a lot of research and trying hard I found the solution:
For everybody searching desperately for an example of advanced array validation in Laravel 8+:
- Step: ALWAYS use an array, not an object. For that purpose:
public function fCreateArrayFromObject($Object) {
$toArray = function ($x) use (&$toArray) {
return is_scalar($x)
? $x
: array_map($toArray, (array)$x);
};
return $toArray($Object);
}
- Step: I will use my example to show you how its easily done:
My array ($cart):
array:3 [▼
"user1" => array:2 [▼
"Items" => array:5 [▼
"blue" => 0
"grey" => 1
"brown" => 1
"look" => 0
"black" => 0
]
"User" => array:2 [▼
"LastName" => "alice"
"FirstName" => "Bobby"
]
]
"user2" => ......
]
My rules:
$person_count = 2; // Up to 5
$validation_rules = [];
for ($i = 1; $i <= $person_count; $i++) {
$validation_rules += [
"user$i" => "array:Items,Customer|size:2|distinct",
"user$i.user.FirstName" => "required|string|min:2|max:255",
"user$i.user.LastName" => "required|string|min:2|max:255",
"user$i.Items.*" => "required|numeric|min:0",
"user$i.Items" => "required|array:blue,grey,brown,look,black|size:5|distinct",
];
}
Action:
$validated_input = Validator::make((array)$cart, $validation_rules);
I am not quite sure, why the make method doesn't interpret my $cart array without the (array) as an array, but it works. Goals:
Obviously everything has to be existent as well: "required"
Tags: Laravel Array Validation, Laravel Nested Array Validation