将超全局$ _POST直接写入数据库是否明智?

时间:2012-05-20 12:33:49

标签: php forms security post

我希望有一个提交代码,可以使用不同的形式,如:

<?php 
 $type = $_GET['type'];
 if(isset($_SESSION['id']))
  handle_form();
 else 
  include 'form_'.$type.'.php'; // different fields based upon type
?>

所以我想知道循环通过超全局$ _POST将所有键和值写入数据库是否明智。类似的东西:

<?php 
 function handle_form() {
 $query = "";
 foreach($_POST as $key => $value) {
  $query .= mysql_real_escape_string($key)."='".mysql_real_escape_string($value)."' AND ";
 }
 mysql_query("UPDATE ".$_POST['type']." SET ".substr($query,0,-4)."WHERE `id` = $_SESSION['id']");
 }
?>

或者这是处理表单的一种非常不安全的方法,是否更好地对相应的'form_type.php'中的所有字段进行硬编码?

3 个答案:

答案 0 :(得分:4)

这是一个非常糟糕的主意,因为任何与列不对应的额外POST字段都会破坏查询。您自己的代码使用$_POST['type']来确定您要更新的表格,除非您事先取消设置,否则该表格也会中断。

此外,您没有对实际发送到数据库的数据进行任何验证。将您自己的名称/权限更改为Admin?当然。将另一个用户的电子邮件更改为您自己的?前进。让您的帐户余额+ 100,000美元?没问题。将产品标记为“价格1美元”?烨。

拥有某种Active Record会更聪明。如果您正在编写更大的应用程序,请查看Yii或Cake PHP等框架,它们内置了此类功能。


除此之外:请停止使用古老的mysql_ *函数编写新代码。它们已不再维护,社区已经开始deprecation process。相反,您应该了解准备好的语句并使用PDOMySQLi。如果您想学习,here is a quite good PDO-related tutorial

答案 1 :(得分:2)

来自不受信任的外部来源的所有内容都无法安全插入数据库或其他任何地方,因为您冒着Code Injection的风险。如果是数据库,则存在SQL Injection的风险。你必须清理输入。这适用于任何Superglobals以及您无法控制的任何其他数据,例如Web服务。

使用mysql_real_escape_string转义数据是您需要做的最小值it does not protect you from all possible injection attacks。它纯粹是语法上的,无法检测到语法错误的数据值的篡改。

除此之外,你不应再使用ext / mysql了。 It is outdated and will be deprecated。使用ext/mysqliPDO并使用prepared statements

答案 2 :(得分:0)

这是一场潜在的噩梦。 永远不要相信您的用户。

每个$ _POST参数都应该检查为:

  • 是公认的参数白名单的一部分吗?
  • 是否有正确的数据类型或值范围?

然后,请使用准备好的语句而不是普通的mysql_query()调用。