Я пытаюсь сделать движок bbcode-ish для своего сайта. Но дело в том, что не ясно, какие коды доступны, потому что коды сделаны пользователями. И вдобавок ко всему, все это должно быть рекурсивным.
Например:
Hello my name is [name user-id="1"]
I [bold]really[/bold] like cheeseburgers
Это простые, и я добился того, чтобы это сработало.
Теперь проблема в том, что происходит, когда два из этих кодов находятся позади друг друга:
I [bold]really[/bold] like [bold]cheeseburgers[/bold]
Или внутри друг друга
I [bold]really like [italic]cheeseburgers[/italic][/bold]
Эти коды также могут иметь атрибуты
I [bold strengh="600"]really like [text font-size="24px"]cheeseburgers[/text][bold]
Следующий работал довольно хорошо, но не хватает в рекурсивной части (? R)
(?P<code>\[(?P<code_open>\w+)\s?(?P<attributes>[a-zA-Z-0-1-_=" .]*?)](?:(?P<content>.*?)\[\/(?P<code_close>\w+)\])?)
Я просто не знаю, куда поместить рекурсивный тег (? R).
Также система должна знать, что в этой строке здесь
I [bold]really like [italic]cheeseburgers[/italic][/bold] and [bold]football[/bold]
2 «кодовых объекта»:
1. [bold]really like [italic]cheeseburgers[/italic][/bold]
а также
2. [bold]football[/bold]
… и содержание первого
really like [italic]cheeseburgers[/italic]
в котором опять есть код
[italic]cheeseburgers[/italic]
какой контент
cheeseburgers
Я искал в Интернете в течение двух дней, и я не могу понять это.
Я думал о чем-то вроде этого:
Я надеюсь, что есть некоторые специалисты по регулярным выражениям, которые готовы мне помочь. 🙁
Спасибо!
РЕДАКТИРОВАТЬ
Поскольку это может быть трудно понять, вот входные данные и ожидаемый результат:
Входные данные:
[heading icon="rocket"]I'm a cool heading[/heading][textrow][text]<p>Hi!</p>[/text][/textrow]
Я хотел бы иметь массив как
array[0][name] = heading
array[0][attributes][icon] = rocket
array[0][content] = I'm a cool heading
array[1][name] = textrow
array[1][content] = [text]<p>Hi!</p>[/text]
array[1][0][name] = text
array[1][0][content] = <p>Hi!</p>
Написав несколько систем разбора BBCode, я могу предложить НЕ использовать только регулярные выражения. Вместо этого вам следует разобрать текст.
Как вы это делаете, зависит от вас, но в качестве общей идеи вы хотели бы использовать что-то вроде strpos
найти первый [
в вашей строке, затем проверьте, что следует за ним, чтобы увидеть, выглядит ли он как тег BBCode, и обработайте его, если так. Затем найдите [
снова начиная с того места, где вы оказались.
Это имеет определенные преимущества, такие как возможность проверять каждый код и пропускать его, если он недействителен, а также обеспечивать соблюдение правильного порядка закрытия тегов ([bold][italic]Nesting![/bold][/italic]
следует считать недействительным) и иметь возможность предоставлять значимые сообщения об ошибках пользователю, если что-то не так (возможно, недопустимый параметр), потому что синтаксический анализатор точно знает, что происходит, тогда как регулярное выражение выдаст что-то неожиданное и потенциально опасное.
Это может быть больше работы (или меньше, в зависимости от вашего навыка с регулярным выражением), но оно того стоит.
Других решений пока нет …