user2933212 user2933212 -3 years ago 98
PHP Question

preg_match_all - Extract key / value from template

I am storing the following in a mysql database:

%URL% https://google.com
%TEXT% Hello world!
%LARGETEXT% Hello
My name is ...
I am from ...


My goal is to make the strings which are wrapped in % to PHP array keys and the string besides are the values.

The problem is, that my regex does not extract the multiline strings.

Here is the code:

preg_match_all ("/%(\w+)%(.*)/", $msg, $matches);


It does output:

[1]=>
array(3) {
[0]=>
string(5) "BASIC"
[1]=>
string(4) "TEXT"
[2]=>
string(9) "LARGETEXT"
}
[2]=>
array(3) {
[0]=>
string(18) " https://google.de"
[1]=>
string(13) " Hello world!"
[2]=>
string(6) " Hello"
}


At the second array only 'Hello' is shown, instead of:

Hello
My name is ...
I am from ...


I tryed various regex but i come always to the same result.

Answer Source

You may use

~%(\w+)%(.*?)(?=%\w+%|$)~s

See the regex demo

Details

  • % - a percent sign
  • (\w+) - Group 1: one or more word chars
  • % - a percent sign
  • (.*?) - Group 2: any 0+ chars (note that s modifier will let . match line break chars, too) as few as possible, up to the first occurrence of...
  • (?=%\w+%|$) - %, 1+ word chars, % or end of string.

An identical unrolled expression (more efficient one) will look like

~%(\w+)%([^%]*(?:%(?!\w+%)[^%]*)*)~

(no need for the s modifier). See the regex demo.

The [^%]*(?:%(?!\w+%)[^%]*)* matches any 0+ chars other than %, and then matches 0 or more consequent occurrences of % not followed with 1+ word chars and then % followed with any 0+ chars other than %.

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download