如何使用preg_match过滤包含空格的网址?

时间:2014-02-04 10:54:58

标签: php regex url preg-match whitespace

我解析了包含多个链接的文本。其中一些包含空格但文件结尾。我目前的模式是:

preg_match_all('#\bhttps?://[^\s()<>]+(?:\([\w\d]+\)|([^[:punct:]\s]|/))#', $links, $match);

这的方式相同:

preg_match_all('/(http|https|ftp|ftps)\:\/\/[a-zA-Z0-9\-\.]+\.[a-zA-Z]{2,3}(\/\S*)?/', $links, $match);

我对这些模式知之甚少,并没有找到一个很好的教程来解释所有可能模式的含义并显示示例。

我如何过滤这样的网址: http://my-url.com/my doc.doc甚至是http://my-url.com/my doc with more white spaces.doc

preg_match_all函数中的\s代表空格。但是我如何检查是否有一个文件在一个或一些空格后面结束?

有可能吗?

6 个答案:

答案 0 :(得分:1)

这可能是您正在寻找的使用urlencode

的内容
$file = "my doc with more white spaces.doc";
echo " http://my-url.com/" . urlencode($file);

产生:

http://my-url.com/my+doc+with+more+white+spaces.doc

rawurlencode

产生

http://my-url.com/my%20doc%20with%20more%20white%20spaces.doc

编辑:以下内容可能有助于使用parse_url解析您的网址

DEMO

$url = 'http://my-url.com/my doc with more white spaces.doc';
$purl = parse_url($url);
$rurl = "";
if(isset($purl['scheme'])){
    $rurl .= $purl['scheme'] . "://";
}
if(isset($purl['host'], $purl['path'])){
    $rurl .= $purl['host'] . rawurlencode($purl['path']);
}
if($rurl === ""){
    $rurl = $url;#error parsing error/invalid url?
}

您可以执行的子目录

$purl['path'] = implode('/', array_map(function($value){return rawurlencode($value);}, explode('/', $purl['path'])));

答案 1 :(得分:1)

我对php不太了解,但这个正则表达式

(http|ftp)(s)?://([\w-]+\.)+[\w-]+(/[\w- ./?%&=]*)?

将匹配每个网址,即使是空格

我认为这个正则表达式会做。

答案 2 :(得分:0)

为什么不使用PHP的FILTER函数。 ?

<?php
$url = "http://my-url.com/my doc.doc";

if(!filter_var($url, FILTER_VALIDATE_URL))
{
    echo "URL is not valid";
}
else
{
    echo "URL is valid";
}

<强> OUTPUT :

URL is not valid

答案 3 :(得分:0)

我认为这应该有效:

$url = '...';
$url_new = '';
$array = explode(' ',$url);

foreach($array as $name => $val){
    if ($val!=' '){
         $url_new = $url_new.$val;
    }
}

答案 4 :(得分:0)

使用此正则表达式

preg_match_all("/^(?si)(?>\s*)(((?>https?:\/\/(?>www\.)?)?(?=[\.-a-z0-9]{2,253}(?>$|\/|\?|\s))[a-z0-9][a-z0-9-]{1,62}(?>\.[a-z0-9][a-z0-9-]{1,62})+)(?>(?>\/|\?).*)?)?(?>\s*)$/", $input_lines, $output_array);

Demo

答案 5 :(得分:0)

做完this really helpful tutorial之后我终于知道了正则表达式的语法是如何工作的。完成后我在this site

上进行了一些实验

在弄清楚我的解析文档中的所有超链接都在引号之间之后很容易,所以我只需要将正则表达式更改为:

preg_match_all('#\bhttps?://[^()<>"]+#', $links, $match);

以便"之后它正在寻找以http开头的下一场比赛。

但这还不是完整的解决方案。用户类是正确的 - 没有rawurlencode文件名它将无法工作。

所以下一步就是:

function endsWith($haystack, $needle)
{
    return $needle === "" || substr($haystack, -strlen($needle)) === $needle;
}

if(endsWith($textlink, ".doc") || endsWith($textlink, ".docx") || endsWith($textlink, ".pdf") || endsWith($textlink, ".jpg") || endsWith($textlink, ".jpeg") || endsWith($textlink, ".png")){
        $file = substr( $textlink, strrpos( $textlink, '/' )+1 );
        $rest_url=substr($textlink, 0, strrpos($textlink, '/' )+1 );
        $textlink=$rest_url.rawurlencode($file);            
    }

从URL过滤文件名并对其进行rawurlen编码,以便输出链接正确。