0

メッセージ内の URL を HTML リンクに変換する次のコードがあります。

$message = preg_replace("#(http|https|ftp|ftps)://([.]?[&;%=a-zA-Z0-9_/?-])*#",
    "<a href=\"away?to=\\0\" target=\"_blank\">\\0</a>", $message);

$message = preg_replace("#(^| |\n)(www([.]?[&;%=a-zA-Z0-9_/?-])*)#",
    "\\1<a href=\"away?to=http://\\2\" target=\"_blank\">\\2</a>", $message);

次の場合を除いて、ほとんどすべてのリンクで非常にうまく機能します。

1) http://example.com/mediathek#/video/1976914/zoom:-World-Wide

ここでの問題は、リンク内の#とです。これは、完全なリンクが変換されるわけではないためです。:

2) If someone just writes "www" in a message

例:<a href="http://www">www</a>

質問は、上記のコードでこれら 2 つのケースを修正する方法があるかどうかです。

4

3 に答える 3

2

ハッシュ( ) を正規表現に含めたいので#、区切り文字を正規表現に含まれていない文字に変更する必要があります!。したがって、正規表現は次のようになります。

$message = preg_replace("!(http|https|ftp|ftps)://([.]?[&;%#:=a-zA-Z0-9_/?-])*!",
"<a href=\"away?to=\\0\" target=\"_blank\">\\0</a>", $message);

これは役に立ちますか?

ただし、仕様 ( RCF 1738% ) にさらに準拠したい場合は、URL で許可されていないものを除外することをお勧めします。含めなかった許可された文字もいくつかあります。

  • $
  • _
  • . (ドット)
  • +
  • !
  • *
  • '
  • (
  • )

これらの文字を含める場合は、正規表現を で区切る必要があります%

于 2013-10-30T21:49:45.287 に答える
1

私の意見では、この問題に取り組むことは無駄です。別の方法としては、正規表現(http、ftp、mail... または www などのプロトコルで開始) を介して URL の可能性があるものを見つけ、FILTER_VALIDATE_URL でテストすることもできます。PHP のマニュアルにあるように、このフィルターは防水の方法ではないことに注意してください。

"Note that the function will only find ASCII URLs to be valid; internationalized domain names (containing non-ASCII characters) will fail."

コードの例 (テストされていません):

$message = preg_replace_callback(
    '~(?(DEFINE)
          (?<prot> (?>ht|f) tps?+ :// )         # you can add protocols here
      )
      (?>
          <a\b (?> [^<]++ | < (?!/a>) )++ </a>  # avoid links inside "a" tags
        |
          <[^>]++>                              # and tags attributes.
      ) (*SKIP)(?!)                             # makes fail the subpattern.
      |                                         # OR
      \b(?>(\g<prot>)|www\.)(\S++)              # something that begins with
                                                # "http://" or "www."
     ~xi',
    function ($match) {
        if (filter_var($match[2], FILTER_VALIDATE_URL)) {
            $url = (empty($match[1])) ? 'http://' : '';
            $url .= $match[0];
            return '<a href="away?to=' . $url . '"target="_blank">'
                 . $url . '</a>';
        } else { return $match[0] }
    },
    $message);
于 2013-10-30T23:14:56.383 に答える