当 magic_quotes_gpc 开启时,是否有必要使用 mysql_real_escape_string() ?

发布于 2024-08-27 18:31:36 字数 97 浏览 10 评论 0原文

为了防止SQL注入,当magic_quotes_gpc开启时,是否需要使用mysql_real_escape_string()

To prevent SQL injection, is it necessary to use mysql_real_escape_string(), when magic_quotes_gpc is on?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

浮光之海 2024-09-03 18:31:36

对于一些罕见的编码,例如GBk - 是的。
但您不应该因为这个原因而将其恢复。无论如何,魔术引号应该被关闭(并且将在下一个 PHP 版本中出现)。因此,mysql_real_escape_string() 是唯一剩下的转义函数。注意,它不是sql注入预防功能。很多人不理解这一点:它只是语法的一部分。它不能用来“保护”任何东西,而是用来组装语法正确的 SQL 查询。每次构建查询时都必须使用,无论数据来自何处。当然,作为副作用,它也会保护您免受 SQL 注入。
当然,mysql_real_escape_string()仅适用于带引号的字符串。所以,如果你这样做,

$num=mysql_real_escape_string($num);
$sql="SELECT INTO table SET data=$num"; /BAD!!!

它不会保护任何东西。
如果要使用不带引号的数字,则必须将其强制转换为正确的类型,如下所示:

$num=intval($num);
$sql="SELECT INTO table SET data=$num"; /GOOD
  • 请记住,mo make mysql_real_escape_string() 按预期工作,应设置正确的客户端编码,并且它可以使用 mysql_set_charset() 函数,SET NAMES 查询不会设置它。

如果你想摆脱所有这些复杂性,你可以使用 准备好的语句,不过您需要将 mysql 驱动程序切换到 mysqli 或 PDO。

请注意,任何正确的语法或准备好的语句都无法帮助您处理除文字之外的查询部分。您无法转义标识符或运算符。如果您碰巧动态使用这些部分,则必须在脚本中对它们进行硬编码,如下所示(对于 ORDER BY 子句):

$orders=array("name","price","qty");
$key=array_search($_GET['sort'],$orders));
$orderby=$orders[$key];
$query="SELECT * FROM `table` ORDER BY $orderby";

或此(WHERE 子句)

$w=array();
if (!empty($_GET['rooms'])) $w[]="rooms='".mysql_real_escape_string($_GET['rooms'])."'";
if (!empty($_GET['space'])) $w[]="space='".mysql_real_escape_string($_GET['space'])."'";
if (!empty($_GET['max_price'])) $w[]="price < '".mysql_real_escape_string($_GET['max_price'])."'";

if (count($w)) $where="WHERE ".implode(' AND ',$w); else $where='';
$query="select * from table $where";

For some rare encodings, such as GBk - yes.
But you should revert it not for this reason. Magic quotes should be turned off anyway (and will be in the next PHP version). So, mysql_real_escape_string() is the only escape function is left. Note that it is not sql injection prevention function. Many many people don't understand this point: it's just a part of syntax. It must be used not to "protect" anything, but to assemble syntactically correct SQL query. And must be used every time you build your query, no matter where data come from. Sure it will protect you from SQL injections too, as a side effect.
Of course, mysql_real_escape_string() works only within quoted strings. So, if you do

$num=mysql_real_escape_string($num);
$sql="SELECT INTO table SET data=$num"; /BAD!!!

It will protect nothing.
If you going to use numbers unquoted, it must be cast to the proper type obligatory, like this:

$num=intval($num);
$sql="SELECT INTO table SET data=$num"; /GOOD
  • Keep in mind that mo make mysql_real_escape_string() works as intended, proper client encoding should be set, and it is possible only with mysql_set_charset() function, SET NAMES query will not set that.

If you want to get rid of all these complexities, you can use prepared statements, though you will need to switch your mysql driver to mysqli or PDO.

Please note that no proper syntax nor prepared statements would not help you with query parts other than literals. You can't escape Identifiers or operators. If you happen to use these parts dynamically, they must be hardcoded in your script, like this (for the ORDER BY clause):

$orders=array("name","price","qty");
$key=array_search($_GET['sort'],$orders));
$orderby=$orders[$key];
$query="SELECT * FROM `table` ORDER BY $orderby";

or this (WHERE clause)

$w=array();
if (!empty($_GET['rooms'])) $w[]="rooms='".mysql_real_escape_string($_GET['rooms'])."'";
if (!empty($_GET['space'])) $w[]="space='".mysql_real_escape_string($_GET['space'])."'";
if (!empty($_GET['max_price'])) $w[]="price < '".mysql_real_escape_string($_GET['max_price'])."'";

if (count($w)) $where="WHERE ".implode(' AND ',$w); else $where='';
$query="select * from table $where";
烟燃烟灭 2024-09-03 18:31:36

查看文档; http://php.net/manual/en/function。 mysql-real-escape-string.php

注意:如果启用了 magic_quotes_gpc,请首先对数据应用 stripslashes()。对已经转义的数据使用此函数将转义数据两次。

您可以检查 magic_quotes_gpc 是否打开,请参阅示例; http://php.net/manual/en/function。获取-magic-quotes-gpc.php

Looking at the documentation; http://php.net/manual/en/function.mysql-real-escape-string.php

Note: If magic_quotes_gpc is enabled, first apply stripslashes() to the data. Using this function on data which has already been escaped will escape the data twice.

You can check if magic_quotes_gpc is on, see example; http://php.net/manual/en/function.get-magic-quotes-gpc.php

戈亓 2024-09-03 18:31:36

是的,通过过滤器 mysql_real_escape_string() 运行进入 sql 语句的所有值是一个很好的做法,它不仅仅是过滤器正在修复的引号。

它可以防止注入攻击,具体方法请参见php手册上的示例。

http://php.net/manual/en/function。 mysql-real-escape-string.php

yes its good practice to run all values that are going into your sql statement through the filter mysql_real_escape_string() its not just quotes that the filter is fixing.

it prevents injection attacks, see the example on the php manual for the method.

http://php.net/manual/en/function.mysql-real-escape-string.php

最后的乘客 2024-09-03 18:31:36

不,又是。如果打开magic_quotes并应用mysql_real_escape_string,那么一些转义将会加倍,这会导致类似“It\'s an example.”的结果。 “我在一些论坛上看到。为了获得最佳实践,您应该禁用magic_quotes并始终使用mysql_real_escape_string,或者更好的是使用数据库抽象库。

No and yes. If magic_quotes is turned on and mysql_real_escape_string is applied, then some escapes will be doubled, which results things like "It\'s an example." I saw on some forums. For best practices, you should disable magic_quotes and use mysql_real_escape_string all the time, or even better, use a DB abstraction library.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文