I'm currently trying to get an URL from a BBCode. There are four possibilities for it, and that's my current problem:

[url]http://stackoverflow.com/[/url]
[url='http://stackoverflow.com/']http://stackoverflow.com/[/url]
[url="http://stackoverflow.com/"]http://stackoverflow.com/[/url]
[url=http://stackoverflow.com/]http://stackoverflow.com/[/url]

I need both. This is, what i have so far:

/\[url(?:\=\'([^\'"]+)\')?](.+?)\[\/url]/i

But that does just work with case 1 & 2.

EDIT:

This works better:

/\[url(?:\=(?:[\"|'])?(.*)(?:[^[]+)?)?\](.*)\[\/url\]/i

But still not perfect.

EDIT:

I guess, i got it. It may need some optimization, but it seems to work:

/\[url(?:\=("|\'|)?(.*)?\1)?\](.*)\[\/url\]/i

See regexp-tester

有帮助吗?

解决方案

You can use this pattern:

$pattern = '~\[url(?|=[\'"]?([^]"\']+)[\'"]?]([^[]+)|](([^[]+)))\[/url]~';
$replacement = '<a href="$1">$2</a>';

$result = preg_replace($pattern, $replacement, $subject);

The idea is to preserve the groups numbers for each branch of the alternation using the branch reset feature. In this way, group 1 contains always the url and group 2 the link description. When there is no description, the url is used in place, that's why the url is twice enclosed in a capture group for the second branch.

其他提示

Try this, it will work

<?php
  $urlsearch  = "(http|ftp|https):\/\/[\w-]+(\.[\w-]+)+([\w.,@?^=%&amp;:\/~+#-]*[\w@?^=%&amp;\/~+#-])?";
  $text = preg_replace( "/\[url\]($urlsearch)\[\/url\]/", "<a href=\"$1\">$1</a>", $text );
  $text = preg_replace( "(\[url\=[\"']?($urlsearch)[\"']?\](.+?)\[/url\])", "<a href=\"$1\">$5</a>", $text );

  print_r( $text );
?>
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top