PHP输入GET vars清理

时间:2017-04-13 17:16:02

标签: php validation input code-injection sanitization

对于我的应用程序,用PHP 5+编写,我有一个common.php,它包含在所有其他页面中。在其中,我有一个include sanitize.php,旨在清理URL中使用的任何输入变量。因此,定位$_GET[]值。

这只是为了让我可以整理任何变量(如果使用的话),并在以后的代码中使用它们。

我已经看到,基于预期/期望的投入进行消毒似乎没有整洁的方式。我最初看到的方法是这个sanitize.php有一个foreach循环遍历所有vars,查找所需的清理类型,然后将清理过的vars添加到一个单独的数组中以便在我的代码中使用。

我认为我不使用PHP清理过滤器来保持标准,而是使用正则表达式。我想要的类型是 alphaonly 字母数字电子邮件密码。虽然"密码"会允许一些特殊的字符,我想删除甚至逃避潜在的"危险"然后将' "之类的内容包含在mysql数据库中。我们有一个欧洲用户群,因此可能有不同的区域设置,但我希望这不会成为一个问题。

这会是一个好的"开始的解决方案,还是我试图重新发明轮子?

随机页面

/mypage.php?c=userid&p=lkasjdlakjsdlakj&z=....
(use SANITIZED_SAFE_INPUT_VARS variable only)

sanitize.php

var aryAllowedGetParamNames = array(
    "c" => "alphaonly",         //login
    "p" => "alphaemail",        //password
    "e" => "email"              //email
    //...
);

var sanitizeTypes = array (
    "alphaonly" => "[a-zA-Z]",
    "alphanumeric" => "[a-zA-Z0-9]",
    "email" => "[a-zA-Z0-9]...etc"
);

var SANITIZED_SAFE_INPUT_VARS = array();

foreach ($_GET as $key => $value) { 
    //apply regex and add value to SANITIZED_SAFE_INPUT_VARS 
}

修改

似乎有一些关于在URL中使用密码的意见。我将更详细地解释一下。我没有使用带有用户名和密码的POST登录提示,而是使用带有userid和password参数的_db_tryLogin.php的ajax异步调用。用户名始终是一个仅6-ALPHA的文本字符串,密码是输入内容的md5。我很清楚MD5上的观点并不是足够安全"。

JS当前MD5密码并将其发送到_db_tryLogin.php

-> async : _db_login.php?c=ABCDEF&p=SLKDauwfLKASFUWPOjkjafkKoAWOIFHF2733287

这将返回" 1"的异步响应。或" 0"。两者都会导致页面刷新,但如果_db_tryLogin.php页面检测到密码并且用户ID匹配一个DB记录,则会设置会话变量并且站点知道用户已登录。

我使用MD5作为异步请求,只是为了快速散列密码,因此不会以明文传输。

_db_tryLogin.php获取密码,md5(plainpass)再次添加SALT和MD5,然后将其与数据库中的usertable进行比较。

存储的数据库密码= md5(SALT.md5(plainpass))

2 个答案:

答案 0 :(得分:1)

  

你正在消毒什么?如果您[仅]尝试保护您的SQL数据库您做错了,应该查看准备好的语句

用户提交的数据从不值得信任。接受,是的,信任 - 否。

不要经历允许某些字符的冗长乏味的过程,只是禁止(即删除)您不想接受的字符,例如非字母数字或反引号字符等。它也可能为您节省很多努力使用PHP strip_tags()函数。

1)在包含文件中创建您的功能。我建议在abstract Static Class中创建它,但这有点超出了这个答案的范围。

2)在此函数/类方法中,添加您要查找的错误字符的定义,以及这些检查适用的数据。您似乎对逻辑过程有了一个很好的了解,但请注意,没有明确的 正确的 代码答案,因为每个程序员都会这样做。字符串的需求是不同的。

3)使用(2)中定义的标准,然后您可以使用正则表达式删除无效字符以返回" safe"变量集。

示例:

   // Remove backtick, single and double quotes from a variable.  
   // using PCRE Regex.
   $data = preg_relace("/[`"']/","",$data);

4)使用PHP函数strip_tags()来做到这一点并从字符串中删除HTML和PHP代码。

5)对于电子邮件验证,使用PHP $email = filter_var($data, FILTER_SANITIZE_EMAIL);函数,它将比您自己的简单正则表达式好得多。 使用PHP Filter Validations它们完全适用于您的情况。

6)从不信任输出数据,即使它通过了你可以提供的所有检查和正则表达式,某些仍然可以通过。总是非常警惕用户提交的数据。 从不信任它。

7)使用Prepared Statements进行SQL交互。

8)作为数字类型(int / float)的快捷方式,你可以使用PHP类型转换来强制给定的varibles成为某种类型,并且破坏它是否是其他任何东西:

$number = $_GET['number']; //can be anything.
$number = (int)$_GET['number']; //must be an integer or zero.

注意:

  • 密码仅为a-z,但应该是您可以选择的字符数越多越好。

  • 如果您在此处采取的措施是针对保护数据库安全性和完整性的情况,那么您做错了,应该使用准备好的语句进行MySQL交互。

  • 停止使用var来声明变量,因为这是来自PHP4 and is VERY old,使用变量前置条件$(例如$variable = true;)要好得多。

  • 你说:

      

    我们拥有欧洲用户群,因此可以使用不同的区域设置

    我强烈建议您探索PHP mb_string functions,因为本机PHP不是安全的。

答案 1 :(得分:0)

我只想启动每个变量的正则表达式,如果它与要求不匹配则应用null。要么只测试它应该具有的东西,要么测试它不应该具有的东西,以较小者为准:

$safeValue = (preg_match('/^[a-zA-Z0-9]{0,5}$/',$value) ? $value : "");

ALONG与参数输入又名

的预备语句
$query = "SELECT x FROM table WHERE id=?";
bind_param("si",$var,$var)

PHP还带有内置过滤器,例如电子邮件等。示例:filter_var($data, FILTER_SANITIZE_EMAIL)

http://php.net/manual/en/filter.filters.sanitize.php