I've just started programmatically sanitizing $_POST inputs as part of a new PHP project and I've come across this issue - the posted values include multi-select values, which are posted as further arrays inside the POST array.
Array
(
[return_url] => dataset
[dataset_name] => Retail
[dataset_collection] => Array
(
[0] => 183
[1] => 184
)
[dataset_purpose] => Array
(
[0] => 186
[1] => 188
[2] => 190
[3] => 191
)
[dataset_security] => Array
(
[0] => 192
[1] => 194
)
[dataset_location] => internal
[dataset_processor_name] => XXX
[dataset_processor_role] => XXX
[dataset_processor_email] => XXX@YYY
[dataset_processor_tel] => XXX
)
I've built a filter array to push the POST values through via filter_input_array and very quickly realized this wasn't processing the data correctly...
$filters = array (
"return_url" => FILTER_SANITIZE_STRING,
"dataset_name" => FILTER_SANITIZE_STRING,
"dataset_collection" => FILTER_REQUIRE_ARRAY,
"dataset_purpose" => FILTER_REQUIRE_ARRAY,
"dataset_security" => FILTER_REQUIRE_ARRAY,
"dataset_location" => FILTER_SANITIZE_STRING,
"dataset_processor_name" => FILTER_SANITIZE_STRING,
"dataset_processor_role" => FILTER_SANITIZE_STRING,
"dataset_processor_email" => FILTER_VALIDATE_EMAIL,
"dataset_processor_tel" => FILTER_SANITIZE_STRING
);
$posted_data = filter_input_array(INPUT_POST, $filters);
Array
(
[return_url] => dataset
[dataset_name] => Customers - Retail
[dataset_collection] =>
[dataset_purpose] =>
[dataset_security] =>
[dataset_location] => internal
[dataset_processor_name] => XXX
[dataset_processor_role] => XXX
[dataset_processor_email] => XXX@YYY
[dataset_processor_tel] => XXX
)
I've found this suggestion of using a recursive array walk to step through every stage of the array, but that doesn't take into account the differing filter types.
I know, in theory, pushing every value through FILTER_SANITIZE_STRING will work, but does anyone know of a way to dynamically creating the $filter array, for example, based on the number of values in POST, or is the best method to simply run the filter_input_array initially on the POST array then manually array walk the dataset arrays in manually..?
Ok, I found the result (in plain sight) here in the PHP manual...
I needed to insert sub-arrays against the appropriate values in the the filter, as follows...
$filters = array (
"return_url" => FILTER_SANITIZE_STRING,
"dataset_name" => FILTER_SANITIZE_STRING,
"dataset_collection" => array('filter' => FILTER_VALIDATE_INT,
'flags' => FILTER_REQUIRE_ARRAY
),
"dataset_purpose" => array('filter' => FILTER_VALIDATE_INT,
'flags' => FILTER_REQUIRE_ARRAY
),
"dataset_security" => array('filter' => FILTER_VALIDATE_INT,
'flags' => FILTER_REQUIRE_ARRAY
),
"dataset_location" => FILTER_SANITIZE_STRING,
"dataset_processor_name" => FILTER_SANITIZE_STRING,
"dataset_processor_role" => FILTER_SANITIZE_STRING,
"dataset_processor_email" => FILTER_VALIDATE_EMAIL,
"dataset_processor_tel" => FILTER_SANITIZE_STRING
);
This returned the correct array...
Array
(
[return_url] => dataset
[dataset_name] => Customers - Retail
[dataset_collection] => Array
(
[0] => 183
[1] => 184
)
[dataset_purpose] => Array
(
[0] => 186
[1] => 188
[2] => 190
[3] => 191
)
[dataset_security] => Array
(
[0] => 192
[1] => 194
)
[dataset_location] => internal
[dataset_processor_name] => XXX
[dataset_processor_role] => XXX
[dataset_processor_email] => XXX@YYY
[dataset_processor_tel] => XXX
)