Php 除去我想要的以外的所有数组元素?
我有一个控制器,它从HTML表单中获取post参数,然后将它们发送到模型中,模型将把数组插入Cassandra数据库 它是SQLInjection的证明,因为它是NoSQL,但我担心的是,用户可以只模拟100k post参数,或者只添加一些我不需要的参数,然后将其插入数据库。如何确保数组中只保留所需的值 例如:Php 除去我想要的以外的所有数组元素?,php,arrays,Php,Arrays,我有一个控制器,它从HTML表单中获取post参数,然后将它们发送到模型中,模型将把数组插入Cassandra数据库 它是SQLInjection的证明,因为它是NoSQL,但我担心的是,用户可以只模拟100k post参数,或者只添加一些我不需要的参数,然后将其插入数据库。如何确保数组中只保留所需的值 例如: $post = ['parent_id', 'type', 'title', 'body', 'tags']; // Good $post = ['parent_id', 'type',
$post = ['parent_id', 'type', 'title', 'body', 'tags']; // Good
$post = ['parent_id', 'type', 'title', 'body', 'tags', 'one', 'two', 'three'] // Bad
如何确保我的数组将取消设置所有不在良好示例中的元素?您正在查找:
当然,这个特定的示例没有多大意义,因为它可以处理数组值,但也有一个基于键的示例可以执行相同的操作。使用数组交集,它将帮助您。这将输出与允许的$post_相同的结果。它只允许$post_input中也存在于$post_allow中的值
$post_allowed = ['parent_id', 'type', 'title', 'body', 'tags'];
$post_input = ['parent_id', 'type', 'title', 'body', 'tags', 'one', 'two', 'three'];
$post = array_intersect($post_input, $post_allowed);
通过将您所期望的条目列入白名单
<?php
$post = array(
'parent_id' => 1,
'type' => 'foo',
'title' => 'bar',
'body' => 'foo bar',
'tags' => 'foo, bar',
'one' => 'foo',
'two' => 'bar',
'three' => 'qux'
);
$allowlist = array(
'parent_id',
'type',
'title',
'body',
'tags'
);
$filtered = array_intersect_key( $post, array_flip( $allowlist ) );
var_dump( $filtered );
这称为白名单,您的示例有误导性,因为$\u POST
是一个关联数组
$post = [
'parent_id' => 'val',
'type' => 'val',
'title' => 'val',
'body' => 'val',
'tags' => 'val',
'one' => 'val',
'two' => 'val',
'three'=>'val',
];
$whitelist = ['parent_id', 'type', 'title', 'body', 'tags'];
$sanitized_post = array_whitelist_assoc($post, $whitelist);
这是我为关联数组创建的白名单函数
if(!function_exists('array_whitelist_assoc')){
/**
* Returns an associative array containing all the entries of array1 which have keys that are present in all the arguments when using their values as keys.
*
* @param array $array The array with master keys to check.
* @param array $array2 An array to compare keys against its values.
* @return array $array2,... A variable list of arrays to compare.
*
*/
function array_whitelist_assoc(Array $array1, Array $array2) {
if(func_num_args() > 2){
$args = func_get_args();
array_shift($args);
$array2 = call_user_func_array('array_merge', $args);
}
return array_intersect_key($array1, array_flip($array2));
}
}
如果您处理的是关联数组,并且出于任何原因不想使用array\u intersect\u key()
,您也可以采用一种更简单的方法,使用旧数组的值手动构建新数组
$post = array(
'parent_id' => 1,
'type' => "post",
'title' => "Post title",
'body' => "Post body",
'tags' => "Post tags",
'malicious' => "Robert'); DROP TABLE students;--"
);
$good = array(
'parent_id' => $post['parent_id'],
'type' => $post['type'],
'title' => $post['title'],
'body' => $post['body'],
'tags' => $post['tags']
);
值得记住的是,虽然array\u intersect
和array\u intersect\u key
都很好,但它们很可能是杀伤力过大。在我的情况下,我只需要剩下1个元素,因此最简单的选择就是根据所需的键/值重建我想要的数组。我想知道在什么时候数组不值得,你只需要使用$new=array('whatI'=>'want')代码>。我相信这是值得的,但在较小的情况下,这可能是过度杀伤力
或者,在回答最初的问题时,简单地使用unset
可能是一个更便宜的选择-unset($post['one']、$post['two']、$post['three'])
。不过,这也与效率太低和数组相交函数更好有关。多维数组呢?我为这个解决方案研究了几个小时,没有找到一个最优的解决方案。所以,我自己写的
function allow_keys($arr, $keys)
{
$saved = [];
foreach ($keys as $key => $value) {
if (is_int($key) || is_int($value)) {
$keysKey = $value;
} else {
$keysKey = $key;
}
if (isset($arr[$keysKey])) {
$saved[$keysKey] = $arr[$keysKey];
if (is_array($value)) {
$saved[$keysKey] = allow_keys($saved[$keysKey], $keys[$keysKey]);
}
}
}
return $saved;
}
用法:示例
$array = [
'key1' => 'kw',
'loaa'=> ['looo'],
'k' => [
'prope' => [
'prop' => ['proo', 'prot', 'loolooo', 'de'],
'prop2' => ['hun' => 'lu'],
],
'prop1' => [
],
],
];
电话:例如
allow_keys($array, ['key1', 'k' => ['prope' => ['prop' => [0, 1], 'prop2']]])
输出:
Array ( [key1] => kw [k] => Array ( [prope] => Array ( [prop] => Array ( [0] => proo [1] => prot ) [prop2] => Array ( [hun] => lu ) ) ) )
因此,您只能从多维数组中获取所需的密钥。它不仅限于“多维”,还可以通过传递一个数组来使用它,如
['key1', 'loaa']
您得到的输出:
Array ( [key1] => kw [loaa] => Array ( [0] => looo ) )
干杯 @Qmal:$good
将好的名称作为值,而$post
将它们作为键。最简单的修复方法是传入array\u flip($good)
而不是$good
,这样两个输入都有好的名称作为键。答案和注释中的代码板链接已恢复为默认的“hello world”脚本:-(与其他完整答案相比,仅此链接的答案更适合作为评论,因为它的信息量明显较少。
Array ( [key1] => kw [loaa] => Array ( [0] => looo ) )