StackOverflow Auto-Link Davranışı taklit nasıl

6 Cevap php

PHP ile nasıl (MEZUNLARI Dehşet cool) StackOverflow otomatik bağlantı davranışları taklit edebilir?

Örneğin, aşağıdaki URL:

http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior

Bu dönüştürülmektedir:

<a title="how to mimic stackoverflow auto link behavior" rel="nofollow" href="http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior">stackoverflow.com/questions/1925455/…</a>

Ben gerçekten bu durumda title nitelik için umurumda değil.


Ve bu:

http://pt.php.net/manual/en/function.base-convert.php#52450

Bu dönüştürülmektedir:

<a rel="nofollow" href="http://pt.php.net/manual/en/function.base-convert.php#52450">pt.php.net/manual/en/…</a>

PHP nasıl benzer bir işlevi yapabilir?

PS: Check my comments on this question for some more examples and behaviors.

6 Cevap

Bu deneyin. URL-eşleşen regex desen Daring Fireball değil.

/**
 * Replace links in text with html links
 *
 * @param  string $text
 * @return string
 */
function auto_link_text($text)
{
   // a more readably-formatted version of the pattern is on http://daringfireball.net/2010/07/improved_regex_for_matching_urls
   $pattern  = '(?i)\b((?:[a-z][\w-]+:(?:/{1,3}|[a-z0-9%])|www\d{0,3}[.]|[a-z0-9.\-]+[.][a-z]{2,4}/)(?:[^\s()<>]+|\(([^\s()<>]+|(\([^\s()<>]+\)))*\))+(?:\(([^\s()<>]+|(\([^\s()<>]+\)))*\)|[^\s`!()\[\]{};:\'".,<>?«»“”‘’]))';

   $callback = create_function('$matches', '
       $url       = array_shift($matches);
       $url_parts = parse_url($url);

       $text = parse_url($url, PHP_URL_HOST) . parse_url($url, PHP_URL_PATH);
       $text = preg_replace("/^www./", "", $text);

       $last = -(strlen(strrchr($text, "/"))) + 1;
       if ($last < 0) {
           $text = substr($text, 0, $last) . "&hellip;";
       }

       return sprintf(\'<a rel="nofollow" href="%s">%s</a>\', $url, $text);
   ');

   return preg_replace_callback($pattern, $callback, $text);
}

Input Text:

This is my text.  I wonder if you know about asking questions on StackOverflow:
 Check This out http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior

 Also, base_convert php function?
http://pt.php.net/manual/en/function.base-convert.php#52450

http://pt.php.net/manual/en/function.base-convert.php?wtf=hehe#52450

Output Text:

This is my text.  I wonder if you know about asking questions on StackOverflow:
 Check This out <a rel="nofollow" href="http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior">stackoverflow.com/questions/1925455/&hellip;</a>

 Also, base_convert php function?
<a rel="nofollow" href="http://pt.php.net/manual/en/function.base-convert.php#52450">pt.php.net/manual/en/&hellip;</a>

<a rel="nofollow" href="http://pt.php.net/manual/en/function.base-convert.php?wtf=hehe#52450">pt.php.net/manual/en/&hellip;</a>

Bu aynı daringfireball.net regular expression dayalı, ancak URL (SO kesildi biraz daha Eric Coleman'ın Örneğin daha mantık, hem de maksimum URL derinliği için yapılandırma (SO 50 gibi görünüyor), maksimum yol derinlik ekler ) 2 gibi görünüyor, ve üç nokta karakteri (&hellip;).

Bildiğim kadarıyla bu, en azından kadar burada yorum ve yanıtları kadar tartışıldı ne gibi, SO URL yeniden tüm işlevselliğini çoğaltır.

function auto_link_text($text) {
    $pattern  = '#\b(([\w-]+://?|www[.])[^\s()<>]+(?:\([\w\d]+\)|([^[:punct:]\s]|/)))#';
    return preg_replace_callback($pattern, 'auto_link_text_callback', $text);
}

function auto_link_text_callback($matches) {
    $max_url_length = 50;
    $max_depth_if_over_length = 2;
    $ellipsis = '&hellip;';

    $url_full = $matches[0];
    $url_short = '';

    if (strlen($url_full) > $max_url_length) {
        $parts = parse_url($url_full);
        $url_short = $parts['scheme'] . '://' . preg_replace('/^www\./', '', $parts['host']) . '/';

        $path_components = explode('/', trim($parts['path'], '/'));
        foreach ($path_components as $dir) {
            $url_string_components[] = $dir . '/';
        }

        if (!empty($parts['query'])) {
            $url_string_components[] = '?' . $parts['query'];
        }

        if (!empty($parts['fragment'])) {
            $url_string_components[] = '#' . $parts['fragment'];
        }

        for ($k = 0; $k < count($url_string_components); $k++) {
            $curr_component = $url_string_components[$k];
            if ($k >= $max_depth_if_over_length || strlen($url_short) + strlen($curr_component) > $max_url_length) {
                if ($k == 0 && strlen($url_short) < $max_url_length) {
                    // Always show a portion of first directory
                    $url_short .= substr($curr_component, 0, $max_url_length - strlen($url_short));
                }
                $url_short .= $ellipsis;
                break;
            }
            $url_short .= $curr_component;
        }

    } else {
        $url_short = $url_full;
    }

    return "<a rel=\"nofollow\" href=\"$url_full\">$url_short</a>";
}

Örnek Girdi:

This is my text.  I wonder if you know about asking questions on StackOverflow:
Check This out http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior

Also, base_convert php function?
http://pt.php.net/manual/en/function.base-convert.php#52450

http://pt.php.net/manual/en/function.base-convert.php?wtf=hehe#52450

http://a.b/c/d/e/f/test

and http://a.b/c/d/e/f/g/h/i/j/k/l/m/n/o/p/q/r/s/t/u/v/z/y/w/z/test

Örnek Çıktı:

This is my text.  I wonder if you know about asking questions on StackOverflow:
Check This out <a href="http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior">http://stackoverflow.com/questions/1925455/&hellip;</a> 

Also, base_convert php function?
<a href="http://pt.php.net/manual/en/function.base-convert.php#52450">http://pt.php.net/manual/en/&hellip;</a> 

<a href="http://pt.php.net/manual/en/function.base-convert.php?wtf=hehe#52450">http://pt.php.net/manual/en/&hellip;</a> 

<a href="http://a.b/c/d/e/f/test">http://a.b/c/d/e/f/test</a> 

and <a href="http://a.b/c/d/e/f/g/h/i/j/k/l/m/n/o/p/q/r/s/t/u/v/z/y/w/z/test">http://a.b/c/d/&hellip;</a>

Bu sonra ne için örnek dize dönüştürmek olacaktır. Bu sadece tek başına bir URL'ye farklı bir kaynaktan geliyor gibi title dışarı bıraktı ve o önemli değildi dedi.

<?php
$urlInput="http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior";
preg_match('@http://(?:www\.)?(\S+/)\S*(?:\s|$)@i', $urlInput, $matches);
print('<a rel="nofollow" href="' . trim($matches[0]) . '">' . $matches[1] . '...</a>');
?>

Lütfen metin taramak için gerektiği kadar uzatın.

URL yolu unsurlardan sadece belirli sayıda maç istiyorsanız, bu RE kullanın:

'@http://(?:www\.)?((?:\S+?/){1,3})\S*(?:\s|$)@i'

Bu 3 yol elemanları (ev sahibi ve yukarı iki dizin) kadar dışarı çıkartacaktır. İstediğiniz yol öğelerinden sayısını tanımlamak için {1,3} üst sınır değişebilir.

\S sıfır maçlar için izin biten değiştirildi.

SO sonra gibi öngörülebilir bir URL varsa bir regex ile bağlantıları kapmak ve desen maç olanları filtrelemek için kolay olmalıdır. Yani URL http://example.com/stuff/1234 ardından http://example.com/stuff/1234/how-to-mimic bir regex ile oldukça önemsiz olacağını bulgu ise.

<?php
preg_match('/http:\/\/example.com\/(\w*)\/(\d)[\/*]/', $text, $matches);

if (is_array($matches))
{
  foreach ($matches as $match)
  {
    // do something...
  }
}
?>

Kevin Brock cevabı üzerine biraz dayanarak izin veren, fakat yapılandırılabilir params (klasör derinlik ve URL uzunluğu) ve bölü işareti olmadan URL'leri kabul eder:

$url = 'http://www.stackoverflow.com/questions/1925455/how-to-mimic-stackoverflow-auto-link-behavior';
$output = '';
$params = array (
    'length' => 10,
    'depth' => 2,
);
preg_match ('@http://(?:www\.)?([^/?# ]+)(/\S+)?(?=\s|$)@i', $url, $matches);
if (isset ($matches[2]))
{
    $parts = explode('/', substr($matches[2], 1));
    if (count($parts) > $params['depth'] && strlen($matches[1].$matches[2]) > $params['length'])
        $output = $matches[1].'/'.implode('/', array_slice($parts, 0, 2)).'/...';
    else
        $output = $matches[1].$matches[2];
}
else
    $output = $matches[1];

echo '<a href="'.$matches[0].'">'.$output.'</a>';

Umarım bu yardımcı olur

Regex (regular expression) to match a URL

https?://([-\w\.]+)+(:\d+)?(/([\w/_\.]*(\?\S+)?)?)?

PHP Örnek: Otomatik URL içindeki metni bağlamak.

$text = preg_replace('@(https?://([-\w\.]+)+(:\d+)?(/([\w/_\.]*(\?\S+)?)?)?)@', '<a href="$1">$1</a>', $text);