1

我的表单中有这个选择输入,我想通过 PHP 访问。

<div data-role='fieldcontain'>
    <label for='fruits' class='select'>Favorite Fruits</label>
    <select name='fruits[]' id='fruits' multiple='multiple' data-native-menu='false'>
        <option value=''>Favorite Fruits</option>
        <option value='1' selected='selected'>Apple</option>
        <option value='2' selected='selected'>Banana</option>
        <option value='3' selected='selected'>Cherry</option>
    </select>
</div>

通过将选择元素的名称设置为“fruits[]”,这样可以:

// |$fruits| is an array
$fruits = $_POST['fruits']

但是,我担心从表单中清除数据。将帖子数据输入数组听起来不安全。例如,如果有人通过 Firebug 将 select 元素更改为文本输入元素并将恶意代码输入到我的程序中怎么办?我从不打电话htmlspecialchars

我的安全顾虑有效吗?为什么或者为什么不?

4

3 回答 3

1

它们确实有效,如果数据来自用户输入,您需要先对其进行清理。

在这种情况下,用户可以轻松破坏您的 HTML,或者更糟糕的是,注入一些恶意 XSS 攻击。

您需要清理这些值,htmlspecialchars在这种情况下就足够了。


没关系,我知道您正在使用来自用户输入的选项填充 HTML 选择标记,但事实并非如此。PHP 将只接受 POST 数据中的字符串或数组,因此您需要确保传入的数据与您想要对其执行的操作兼容。一种可能的解决方案是将提交的值列入白名单,类似的函数array_intersect可能在这里有用,例如:

$allowed_fruits = array('Apple', 'Banana', 'Cherry');
$fruits = array_intersect($allowed_fruits, $_POST['fruits']);

这样,如果用户提交“草莓”,它将在$fruits数组中被忽略。

您可能还想确保数组不是多维的,如下所示:

if (count($_POST['fruits']) != count($_POST['fruits'], COUNT_RECURSIVE))
{
    // array is multidimensional, do not process
}

当然,这取决于您对数据的使用,但白名单方法始终是最安全的。

于 2012-04-04T06:16:13.547 回答
1

您的代码应该验证用户输入是否为预期格式(isset, is_array, ...),并在将其发送到数据库、html 输出、日志等其他任何地方之前正确转义它。从根本上说,用户输入的字符串和用户输入的字符串数组之间几乎没有区别。

使用mysql_real_escape_string(甚至更好PDO)处理数据库,htmlspecialchars处理 HTML 输出。

于 2012-04-04T06:17:30.800 回答
1

这是获取值的正确方法,但是,您担心是对的。您按照建议的方式接收值,然后使用适当的清洁方法:用于显示的 htmlspecialchars、用于插入数据库的 mysql_escape 等。您需要对数组中的每个元素执行此操作,但仅在当时你要使用它。

于 2012-04-04T06:17:33.133 回答