将PHP解析REQUEST_URI为数组

12

我正在将 REQUEST_URI 解析为一个数组。

现在,我有以下代码:

private function load_url_vars()
{
    if (preg_match('/^.+\?(.+)$/', $_SERVER["REQUEST_URI"], $matches))
    {
        $varpairs = preg_split("/&/", $matches[1]);
        foreach ($varpairs as $varpair)
        {
            if (preg_match('/^([A-Za-z_]+)=(.*)$/', $varpair, $varmatch))
            {
                $this->urlvars[$varmatch[1]] = urldecode($varmatch[2]);
            }
        }
    }
}

这样做是否存在安全问题?这是一种好的解析方式吗?

编辑:语言


没有安全问题,但是你已经可以在_GET超全局变量中获取所有内容了,那你的代码有什么意义呢? - Michael J.V.
在使用mod_rewrite时,最好在php中解析它,而不是在.htaccess中。 - OMGKurtNilsen
我已经阅读了所有当前的评论,你的想法是错误的。无论你是否使用mod_rewrite,即使你的URL看起来像/controller/method/id/?some_long_text=some_variable - 只要有正确格式的查询字符串可以解析成$_GET,你就可以在$_GET数组中使用它们。在尝试修复之前,请先测试一下。 - Michael J.V.
在我发布这篇文章之前,我已经进行了测试。以下是“/home/index/?test=willitwork”的var_dump($_GET)结果:array(2) { ["controller"]=> string(4) "home" ["method"]=> string(5) "index" } - OMGKurtNilsen
PHP解析的是mod_rewrite重写后的URL,而不是用户发送的URL。 - OMGKurtNilsen
显然,您的重写规则的正则表达式会将以/分隔的字符串重写为$_GET,这显然是错误的。我使用类似于您的方案,其中我有“漂亮”的URL,但我的$_GET按预期工作。 - Michael J.V.
4个回答

21

你也可以使用 PHP 内置函数来实现,这是一种高效的方式。

$urlArr=parse_url($_SERVER['REQUEST_URI']);
parse_str($urlArr['query'], $output);

print_r($output);

3
对于大多数人来说,这可能比被接受的答案更有用。$urlArr[0]中的路径是相对于根目录的,$output是一个整洁的数组,其中包含路径、完整查询以及单独的查询参数。使用.htaccess将非文件和非目录重定向到index.php或类似页面时,这个方法可以很好地发挥作用。 - Henrik Erlandsson
最简单的答案并且更好,因为如果URI中没有查询部分,接受的答案会抛出警告。 - Soul Reaver

8

没有安全问题,但你的解决方案相当繁琐。使用parse_str(以及parse_url用于拆分路径)已经可以实现这一点。或者在您的情况下只需:

list($path, $qs) = explode("?", $_SERVER["REQUEST_URI"], 2);
parse_str($qs, $this->urlvars);

谢谢。我不知道parse_str会这样做:D - OMGKurtNilsen
2
如果REQUEST_URI不包含?,则会创建一个“通知”。 - Philipp Kyeck

3
$the_array = explode('/', trim($_SERVER['REQUEST_URI'], '/'));

1

因为我正在使用 mod_rewrite。 - OMGKurtNilsen
1
如果你想要漂亮的URL,通常所有的查询字符串都会被压缩成目录级别;例如this/is/the/uri/path而不是this?is=the&uri=path。对于前者,因为你已经为了美观性而重写它,所以你可以直接使用explode('/', $uri)来处理REQUEST_URI。 - Dan Lugg
TomcatExodus:我两个都在做。我的URL是/controller/method/id,然后任何其他变量都是?var=something。 - OMGKurtNilsen
你可以使用QSA标志,在mod_rewrite中传递查询字符串。 - roberthuttinger
我来这里是因为在我的WordPress上,某些原因导致$_GET和$_REQUEST为空,而$_SERVER ['REQUEST_URI']却包含所需的变量。 - user109764

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