何时以及为什么应该使用$_REQUEST而不是$_GET / $_POST / $_COOKIE?

22
标题中的问题是什么?
$_GET[foo]$_POST[foo]$_COOKIE[foo]这三个变量都存在时,会发生什么?哪一个变量将被包含在$_REQUEST中?

2
变量将根据php.ini中的gpc_order进行覆盖,您应该使用引号访问变量,例如:$_GET ['foo']。 - Alix Axel
6个回答

53

我会说从不。

如果我想通过各种方法设置某些东西,我会为每种方法编写代码以提醒自己采用了这种方式,否则你可能没有意识到已经被覆盖的内容。

难道它不应该像这样工作:

$_GET = 非破坏性操作(排序、记录操作、查询等)

$_POST = 破坏性操作(删除、更新等)

$_COOKIE = 不重要的设置(样式表首选项等)

$_SESSION = 重要的设置(用户名、是否已登录?访问级别等)


GET和POST方法的用途不同,你提到的很有道理。然而,现在很少有Web应用程序使用这种方式了... - Internet Friend
我一直认为的想法是,如果你使用get来删除东西,那么机器人可以爬取这些链接,从而删除数据库中的所有内容...听起来像是一个恐怖故事,所以我一直坚持上面的模式。 - Rich Bradshaw
我们在工作中遇到了一些困难。我们的产品是一个 CMS 系统,遵循上述规则。我们想为我们的客户提供 Google Mini 设备 www.google.com/enterprise/mini/,但是让它爬取 CMS 外部网络是不可能的,因为那样会引起混乱 :/ - Internet Friend
这真是令人沮丧...在开始之前考虑这种事情是很好的!您可以尝试在所有获取链接上使用rel="nofollow",然后逐渐删除您知道安全的链接 - 当然这仍然有点可怕,不确定Google对nofollow的要求有多严格。 - Rich Bradshaw
它确实尊重nofollow,并且当然可以通过许多其他方式来保护它。但是,如果一开始做出更好的设计决策,仍然可以避免很多不必要的工作。 - Internet Friend
1
@RichBradshaw 这在2013年帮了我。噢,是的! - Yousuf Memon

7
有时您可能希望以几种不同的方式调用相同的脚本。例如,表单提交和 AJAX 调用。然而,在大多数情况下,最好明确指定使用哪种方式。
此外,请参见http://docs.php.net/manual/en/ini.core.php#ini.request-order了解变量的不同来源如何覆盖彼此(如果存在名称冲突)。

5

$_REQUEST只是一个快捷方式,用于避免测试数据是否可以来自POST、GET和cookie。

有一些陷阱:

  • 数据从GET、POST和最后是COOKIE获取。最后一个会覆盖第一个,所以要小心。
  • REST架构要求你分离POST和GET语义,在这种情况下,你不能依赖$_REQUEST

尽管如此,如果你知道你在做什么,那么这只是另一个方便的PHP技巧。

如果我想快速更新可能来自多个来源的变量,我会使用它,例如:

  • 在你的控制器中,决定服务哪个页面,而无需检查请求是来自表单操作还是超链接。

  • 检查会话是否仍处于活动状态,而不考虑会话ID的传递方式。


4
回答“当所有3个存在时会发生什么”这个问题,答案是“这取决于情况”。
PHP根据PHP.INI中的request_order指令(或者如果request_order不存在则使用variables_order)自动填充$_REQUEST。默认值通常为“GPC”,这意味着首先加载GET,然后加载POST(如果有冲突则覆盖GET),然后加载cookies(如果有冲突则覆盖get/post)。但是,您可以在PHP.INI文件中更改此指令。例如,将其更改为“CPG”会使cookie首先加载,然后是post,最后是get。
至于何时使用它?我赞同“永远不要使用”。你已经不信任用户了,为什么要给用户更多工具?作为开发人员,您应该知道数据来自哪里。这一切都是为了减少攻击面积。

2

当您不确定值是由哪个位置填充的,或者当您同时使用它们并且想要通过POST和GET方法循环遍历所有值时。


1

当我不希望人们轻易访问所传递的内容时,我使用POST方法;而当我不介意他们在URL中看到值时,我使用GET方法。通常我不会过多地使用cookies,因为我认为SESSION对于持久化值来说已经足够了(尽管拥有一个适当的注册表是利用它的最佳方式)。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接