Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/256.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 如何转义fopen的url_Php_Fopen - Fatal编程技术网

Php 如何转义fopen的url

Php 如何转义fopen的url,php,fopen,Php,Fopen,fopen似乎无法打开带有空格的文件。 例如: $url = 'http://gatewaypeople.com/images/articles/cntrbutnssttmnts12_main 616x200.jpg'; fopen($url, 'r'); 返回false(注意url中的空格),但浏览器可以访问该文件。 我还尝试通过urlencode和rawurlencode逃出url,但没有成功。如何正确地逃离空间 rawurlencode是一种方法,但不能逃避完整的URL。仅转义文件名。

fopen似乎无法打开带有空格的文件。 例如:

$url = 'http://gatewaypeople.com/images/articles/cntrbutnssttmnts12_main 616x200.jpg';
fopen($url, 'r'); 
返回false(注意url中的空格),但浏览器可以访问该文件。
我还尝试通过
urlencode
rawurlencode
逃出url,但没有成功。如何正确地逃离空间

rawurlencode
是一种方法,但不能逃避完整的URL。仅转义文件名。因此,您将在
http://gatewaypeople.com/images/articles/cntrbutnssttmnts12_main%20616x200.jpg

您可以使用以下代码:

$url = 'http://gatewaypeople.com/images/articles/cntrbutnssttmnts12_main 616x200.jpg';
fopen(urlencode($url), 'r');
$arr = parse_url ( 'http://gatewaypeople.com/images/articles/cntrbutnssttmnts12_main 616x200.jpg' );
$parts = explode ( '/', $arr['path'] );
$fname = $parts[count($parts)-1];
unset($parts[count($parts)-1]);
$url = $arr['scheme'] . '://' . $arr['host'] . join('/', $parts) . '/' . urlencode ( $fname );
var_dump( $url );
备选答案和简短答案(感谢@Dziamid)

输出:

string(76) "http://gatewaypeople.com/images/articles/cntrbutnssttmnts12_main+616x200.jpg"
这里提出的所有解决方案都是错误的,因为它们没有转义查询字符串部分和基本目录部分。此外,它们不考虑用户、传递和片段url部分

要正确转义有效URL,必须分别转义路径部分和查询部分。 因此,解决方案是提取url部分,转义每个部分并重建url

下面是一个简单的代码片段:

function safeUrlEncode( $url ) {
    $urlParts = parse_url($url);
    $urlParts['path'] = safeUrlEncodePath( $urlParts['path'] );
    $urlParts['query'] = safeUrlEncodeQuery( $urlParts['query'] );
    return http_build_url($urlParts);
}

function safeUrlEncodePath( $path ) {
    if( strlen( $path ) == 0 || strpos($path, "/") === false ){
        return "";
    }
    $pathParts = explode( "/" , $path );
    return implode( "/", $pathParts );
}

function safeUrlEncodeQuery( $query ) {
    $queryParts = array();
    parse_str($query, $queryParts);
    $queryParts = urlEncodeArrayElementsRecursively( $queryParts );
    return http_build_query( $queryParts );
}

function urlEncodeArrayElementsRecursively( $array ){
    if( ! is_array( $array ) ) {
        return urlencode( $array );
    } else {
        foreach( $array as $arrayKey => $arrayValue ){
                $array[ $arrayKey ] = urlEncodeArrayElementsRecursively( $arrayValue );
        }
    }
    return $array;
}
用法简单地说就是:

$encodedUrl = safeUrlEncode( $originalUrl );
旁注 在我的代码片段中,我正在使用PECL扩展下提供的代码片段。如果您的服务器上没有PECL扩展,您可以简单地包括纯PHP实现:


干杯:)

我想我应该用“/”来分割路径,对各个部分进行编码并将它们内爆回来?基本上,是的。但是您可以使用它进行解析。而且不需要对主机、协议等进行编码。只有
路径
查询
片段
(如果适用)URL中首先不能有空格。请查看我的答案,我想这会有所帮助
$encodedUrl = safeUrlEncode( $originalUrl );