在 PHP 中,有没有一种简单的方法来获取 URI 的目录部分?

发布于 2024-11-14 16:06:31 字数 742 浏览 0 评论 0原文

在 PHP 中,有没有一种巧妙的方法来获取 HTTP URI 的目录部分?即给定一个带有可选文件名和查询的 URI,我只想要不带文件名或查询的目录;

  Given            Returns
  /                /
  /a.txt           /
  /?x=2            /
  /a.txt?x=2       /
  /foo/            /foo/
  /foo/b.txt       /foo/
  /foo/b.txt?y=3   /foo/
  /foo/bar/        /foo/bar/
  /foo/bar/c.txt   /foo/bar/

等等。

我找不到 PHP 函数来执行此操作。我正在使用以下代码片段,但对于感觉应该是单个函数的东西来说,它是冗长且过于复杂的;

$uri_path = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$uri_dir = substr($uri_path, 0, 1 + strrpos($uri_path, '/'));

有更干净的方法吗?

编辑

dirname() 没有执行我想要的操作。

echo dirname("/foo/bar/");

输出;

/foo

In PHP, is there a neat way to get just the directory part of an HTTP URI? I.e. given a URI with an optional filename and query, I want just the directory without the filename or query;

  Given            Returns
  /                /
  /a.txt           /
  /?x=2            /
  /a.txt?x=2       /
  /foo/            /foo/
  /foo/b.txt       /foo/
  /foo/b.txt?y=3   /foo/
  /foo/bar/        /foo/bar/
  /foo/bar/c.txt   /foo/bar/

And so on.

I can't find a PHP function to do it. I'm using the following code snippet but it's long-winded and over-complicated for something that feels like it ought to be a single function;

$uri_path = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$uri_dir = substr($uri_path, 0, 1 + strrpos($uri_path, '/'));

Is there a cleaner way?

Edit

dirname() doesn't do what I want.

echo dirname("/foo/bar/");

Outputs;

/foo

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

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

发布评论

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

评论(4

锦欢 2024-11-21 16:06:31

dirname 返回目录。

明确地, $uri_dir = dirname($_SERVER['REQUEST_URI']);

另外, pathinfo 返回一个包含 PATHINFO_DIRNAME、PATHINFO_BASENAME、PATHINFO_EXTENSION 的关联数组PATHINFO_FILENAME。很有用。

dirname returns the directory.

Explicitly, $uri_dir = dirname($_SERVER['REQUEST_URI']);

As well, pathinfo returns an associative array with PATHINFO_DIRNAME, PATHINFO_BASENAME, PATHINFO_EXTENSION and PATHINFO_FILENAME. Quite useful.

凉宸 2024-11-21 16:06:31

这是一个单行代码,它将通过剥离最后一个斜杠之后的所有内容来通过测试。

$path=preg_replace('{/[^/]+$}','/', $uri);

dirname 函数无法帮助您,因为它返回其输入的父目录,即 dirname('/foo/bar/') 返回 '/foo ' (但是,请参阅 Arvin 的评论,首先偷偷地在 uri 上添加额外的位会欺骗它执行您的命令!)

要分解该正则表达式...

  • 左大括号和右大括号 {} 是只是模式的分隔符,并且会被忽略。
  • 字符串中我们必须匹配的第一件事是 /
  • 然后我们在方括号 [^/] 中包含一个“字符类”
    • 前导 ^ 表示“反转类别” - 换句话说,匹配不属于此类的任何字符
    • 下一个符号是 /
    • 所以这个字符类只匹配任何不是 / 的字符
  • ,下一个符号是 + 符号表示“匹配 1 个或多个前一个模式” - 换句话说,匹配尽可能多的非斜杠字符
  • 最后 $ 符号匹配字符串的末尾

因此,正则表达式会找到字符串中的最后一个斜杠和所有字符跟随它。

Here's a one liner that will pass your tests by stripping everything after the final slash

$path=preg_replace('{/[^/]+$}','/', $uri);

The dirname function can't help you, as it returns the parent dir of its input, i.e. dirname('/foo/bar/') returns '/foo' (however, see Arvin's comment that sneakily tacking an extra bit on the uri first would fool it into doing your bidding!)

To break down that regex...

  • the opening and closing braces {} are just delimiters for the pattern, and are ignored.
  • the first thing we must match in the string is a /
  • then we have a 'character class' in square brackets [^/]
    • the leading ^ means 'invert the class' - in other words, match any character not in this class
    • the next symbol is a /
    • so this character class simply matches any character which isn't a /
  • next, a + symbol means 'match 1 or more of the previous pattern' - in other words, match as many non-slash characters as possible
  • finally the $ symbol matches the end of a string

So, the regex finds the final slash in a string and all the characters following it.

信愁 2024-11-21 16:06:31

尝试 dirname($uri_path); - 请参阅 dirname()

另一种选择是使用 strrpos() 函数查找最后出现的 / ,这可能比 dirname 更好,因为 Windows 系统上的 dirname 将 \ 视为 /。

然后你应该检查 parse_url() 是否进行 urldecoding 。

Try dirname($uri_path); - see dirname()

The other option is to use the strrpos() function to find the last occurring / which is probably better than dirname as dirname on windows systems treats \ as /.

Then you should check if parse_url() does urldecoding or not.

獨角戲 2024-11-21 16:06:31
$dir = $_SERVER['PHP_SELF']; // $dir = '/foo/'; // also works
$dir = (substr($dir,-1)=='/') ? $dir : dirname($dir) . '/';

似乎也有效,而且有点短。

使用: 'http://' 。 $_SERVER['HTTP_HOST'] 。 $dir 表示完整的 URI

我使用 PHP_SELF 而不是 REQUEST_URI 的原因是,在其他一些示例中,如果用户在其中一个参数中放入“/”,您将得到意外的结果,而无需进行额外的清理。此外,并非所有服务器都支持所有标头变量,但这里的标头变量非常常见。

$dir = $_SERVER['PHP_SELF']; // $dir = '/foo/'; // also works
$dir = (substr($dir,-1)=='/') ? $dir : dirname($dir) . '/';

also seems to work and is bit shorter.

use: 'http://' . $_SERVER['HTTP_HOST'] . $dir for full URI

The reason I would use PHP_SELF instead of REQUEST_URI is that in some of the other examples if the user puts a "/" in one of the arguments, you will get unexpected results without additional sanitizing. Also, not all servers support all header variables, but the ones here are pretty common.

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