php - 图像 URL 中的 unicode 字符 - 404

标签 php html unicode url-encoding

我正在尝试打开名称中包含拉丁字符的图像 (113_Atlético Madrid)。

我通过使用 PHP 函数 rawurlencode() 对其名称进行编码来保存它,因此现在它的新名称是 113_Atl%C3%A9tico%20Madrid。但是当我尝试通过此 URL 打开它时,例如 mysite.com/images/113_Atl%C3%A9tico%20Madrid.png 我收到 404 错误。

如何解决这个问题?

PHP 代码:

if(isset($_FILES['Team'])){
    $avatar = $_FILES['Team'];
    $model->avatar = "{$id}_".rawurlencode($model->name).".png";
    if(!is_file(getcwd()."/images/avatars/competitions/{$model->avatar}")){
        move_uploaded_file($avatar['tmp_name']['avatar'], getcwd()."/images/avatars/teams/{$model->avatar}");
    }
}

最佳答案

%-encoding 用于 URL。文件名不是 URL。您使用以下表格:

http://example.org/images/113_Atl%C3%A9tico%20Madrid.png

在 URL 中,网络服务器会将其解码为如下文件名:

/var/www/example-site/data/images/113_Atlético Madrid.png

在准备要放入 URL 的文件名时,应该使用 rawurlencode(),但不应使用它来准备用于光盘存储的文件名。

这里还有一个额外的问题,即在光盘上存储非 ASCII 文件名在跨平台上是不可靠的。特别是如果您在 Windows 服务器上运行,像 move_uploaded_file() 这样的 PHP 文件 API 很可能会使用您不想要的编码,并且最终可能会得到像 113_Atlí 这样的文件名©tico madrid.png.

对此不一定有简单的解决方法,但您可以使用任何形式的编码,甚至是%编码。因此,如果您坚持使用当前的 rawurlencode() 来创建文件名:

/var/www/example-site/data/images/113_Atl%C3%A9tico%20Madrid.png

这样就可以了,但是您必须使用 double-rawurlencode 来生成匹配的 URL:

http://example.org/images/113_Atl%25C3%25A9tico%2520Madrid.png

但无论如何,将用户可能提供的任意字符串作为文件名的一部分是非常危险的。您可能会受到目录遍历攻击,其中名称包含类似 /../../ 的字符串,以访问目标目录之外的文件系统。 (这些攻击通常升级为针对 PHP 应用程序的执行任意代码攻击,这些应用程序通常在较弱的权限下部署。)使用完全合成的名称会更好,如@MatthewBrown 建议的(+1)。

(请注意,这仍然不是允许用户文件上传的安全问题的结束,事实证明这是一个非常难以正确实现的功能。内容嗅探和插件仍然存在问题,可以允许图像文件被重新解释为其他类型的文件,从而导致跨站点脚本问题。为了防止出现这种情况的所有可能性,最好只从单独的主机名提供用户提供的文件,这样针对该主机的 XSS 就不会攻击您针对主站点的 XSS。)

关于php - 图像 URL 中的 unicode 字符 - 404,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38978495/

相关文章:

python - 如何在自定义模板标签中传递 url 标签?

html - 确保我的缩略图描述始终与缩略图的中间对齐?

html - 额外间距图像响应网站

java - 从字节数组中提取第一行有效的字符串

c++ - 如何在C/C++中输出unicode字符

Android 将 unicode 字符串设置为 textview

php - 如何在 php 中将循环查询转化为一个查询

javascript - 用于多个字段的单个 jQuery 图像选择器

PHP/MySQL 在表达到一定行数后停止更新

php - 允许 PHP date() 函数识别 dd-mm-yy 格式