Регулярка запрет замены ссылки в src

R
На сайте с 03.07.2006
Offline
214
812

Есть регулярка, взял тут: http://daringfireball.net/2010/07/improved_regex_for_matching_urls

Помогите, пожалуйста, научить её не менять ссылки в уже готовых тегах например в <iframe src="http://youtube.com/?someurl"> или <a href="url"></a>


$search[] = "#(?i)"
."\b"
."" // Capture 1: entire matched URL
."(?:"
."(([a-z][\w-]+:" // URL protocol and colon
."(?:"
."/{1,3}" // 1-3 slashes
."|" // or
."[a-z0-9%])" // Single letter or digit or '%'
// (Trying not to match e.g. "URI::Escape")
.")"
."|" // or
."(www\d{0,3}[.]" // "www.", "www1.", "www2." … "www999."
."|" // or
."[a-z0-9.\-]+[.][a-z]{2,4}/))" // looks like domain name followed by a slash
.")"
."(?:" // One or more:
."([^\s()<>]+" // Run of non-space, non-()<>
."|" // or
."\(([^\s()<>]+|(\([^\s()<>]+\)))*\)" // balanced parens, up to 2 levels
."))+"
."(?:" // End with:
."(\(([^\s()<>]+|(\([^\s()<>]+\)))*\)" // balanced parens, up to 2 levels
."|" // or
."[^\s`!()\[\]{};:'\".,<>?«»“”‘’])" // not a space or one of these punct chars
.")"
."#";

$replace[] = " <a rel=\"nofollow\" target=\"_blank\" href=\"{$site_http}index.php?action=link&url=http://\$3\$4\$7\">\$3\$4\$7</a> ";

$text = preg_replace($search, $replace, $text);
[umka]
На сайте с 25.05.2008
Offline
456
#1

Сделать это одной регуляркой вряд ли возможно.

Проще сначала выбрать все нужные url-ы в массив, присвоить им метки, заменить эти url-ы на метки, сделать замену вашей регуляркой, а потом сделать обратную замену меток на сохранённые url-ы.

Лог в помощь!
R
На сайте с 03.07.2006
Offline
214
#2
'[umka:
;11550981']Сделать это одной регуляркой вряд ли возможно.
Проще сначала выбрать все нужные url-ы в массив, присвоить им метки, заменить эти url-ы на метки, сделать замену вашей регуляркой, а потом сделать обратную замену меток на сохранённые url-ы.

Вопрос остаётся актуальным, как выбрать все url из текста кроме тех, что уже находятся в активных тегах?

[umka]
На сайте с 25.05.2008
Offline
456
#3

Так задача-то какая? Выделить ссылками все урлы, находящиеся вне тэгов? Или только вне каких-то определённых тэгов?

Если первое, то это довольно просто:

$text=preg_replace('#(>[^<]*|\A[^<]*)(https?://.+)([\s\t\r\n\Z<])#U','\1<a href="\2">\2</a>\3',$text);
R
На сайте с 03.07.2006
Offline
214
#4
'[umka:
;11551105']Так задача-то какая? Выделить ссылками все урлы, находящиеся вне тэгов? Или только вне каких-то определённых тэгов?
Если первое, то это довольно просто:
$text=preg_replace('#(>[^<]*|\A[^<]*)(https?://.+)([\s\t\r\n\Z<])#U','\1<a href="\2">\2</a>\3',$text);

Почти оно, спасибо.

Думаю, надо проверять на наличие кавычки " перед http, кавычки быть не должно, тогда нужно делать replace, но я не нашёл как это реализовать.

(>[^<]*|\A[^<]*) поставил в свой код перед ."\b" и почти заработало. Хотя я не уверен что понимаю почему именно так.

Можете подробнее объяснить как читается (>[^<]*|\A[^<]*) ?

Перестали преобразовываться ссылки с www без http

[umka]
На сайте с 25.05.2008
Offline
456
#5
rengen:

Можете подробнее объяснить как читается (>[^<]*|\A[^<]*) ?

Читается так:

>[^<]* — какой-то тэг закрывается и не открывается

или

\A[^<]* — с начала строки ни один тэг не открывается

Более подробно на pcre.ru

rengen:

Перестали преобразовываться ссылки с www без http

А без указания протокола это и не ссылка вовсе :) Т.к. протокол может быть любой, от "gopher" до "imap".

R
На сайте с 03.07.2006
Offline
214
#6
'[umka:
;11551278']Читается так:
>[^<]* — какой-то тэг закрывается и не открывается
или
\A[^<]* — с начала строки ни один тэг не открывается

Более подробно на pcre.ru




А без указания протокола это и не ссылка вовсе :) Т.к. протокол может быть любой, от "gopher" до "imap".

Может в 1 из 10 тысяч случаев это gopher или imap. :)

Но мне это нужно для банальных пользователей на сайте не связанным с техническими вопросами.

Думаю, надо проверять на наличие кавычки " перед http, кавычки быть не должно, тогда нужно делать replace, но я не нашёл как это реализовать.

Можете помочь?

R
На сайте с 03.07.2006
Offline
214
#7

Открыл справочник и разобрался сам. :)

Преобразовывает все неактивные ссылки, а ссылки уже использованные в тегах оставляет в покое.

Также адекватно преобразовывает ссылки без http если указан www.


$search[] = "#((?<!\"|'|\">|=)((https?:\/\/)|((?<!\/)www\.))(.*?[a-z_\/0-9\-\#=&]))(?=(\.|,|;|\?|\!)?(\"|'|«|»|\[|\s|\r|\n|$))#iS"; $replace[] = " <a rel=\"nofollow\" target=\"_blank\" href=\"{$site_http}index.php?action=link&url=http://\$4\$5\">\$4\$5</a> ";

$text = preg_replace($search, $replace, $text);

[umka] спасибо за помощь, не плюсану, потому что уже плюсовал когда-то...

[umka]
На сайте с 25.05.2008
Offline
456
#8
rengen:
Открыл справочник и разобрался сам. :)

На сёрче этот поступок — настоящий подвиг!

Не взирая на трудность выбранной темы, вы на собственном примере показали остальным пионерам и октябрятам важность умения пользоваться справочной информацией для достижения целей.

Молодец!

Авторизуйтесь или зарегистрируйтесь, чтобы оставить комментарий