Reputation: 825
I have a string of key->value pairs in the following colon-separated format:
MIME-Version: 1.0
From: "Tim Lincecum"
Reply-To: "Tim Lincecum"
Return-path: "Tim Lincecum"
Content-Type: text/html; charset=iso-8859-1
Subject: Giants Win World Series!
How do I get an associative array such that arr['From'] = "Tim Lincecum",
etc.?
I know there's the explode()
function, but the only delimiter I see (colon) is in the middle of a key and a value rather than between each pair. How can I approach this?
Upvotes: 1
Views: 13543
Reputation: 48001
Avoiding a regular expression approach while parsing a text format that is not handled by a native PHP function/library will require exploding on one delimiter, then looping those results and exploding on another delimiter.
For simplicity and control, just use preg_match_all()
, then use array_column()
to form the associative structure from the payload of captured substrings.
Code: (Demo)
preg_match_all(
'/^([^:]+): (.+)/m',
$string,
$m,
PREG_SET_ORDER
);
var_export(
array_column($m, 2, 1)
);
The m
pattern modifier changes the meaning of ^
from "start of the string" to "start of a line".
If you'd like to remove the double quote wrapping that appears on some of the values, here is the pattern adjustment: Demo
/^([^:]+): ("?)(.+)\2/m
Upvotes: 0
Reputation: 490461
You could always use regex :)
$str = 'MIME-Version: 1.0' . "\r\n" .
'From: "Tim Lincecum"' . "\r\n" .
'Reply-To: "Tim Lincecum"' . "\r\n" .
'Return-path: "Tim Lincecum"' . "\r\n" .
'Content-Type: text/html; charset=iso-8859-1' . "\r\n" .
'Subject: Giants Win World Series!';
preg_match_all('/(.*?):\s?(.*?)(\r\n|$)/', $str, $matches);
$headers = array_combine(array_map('trim', $matches[1]), $matches[2]);
var_dump($headers);
array(6) {
["MIME-Version"]=>
string(3) "1.0"
["From"]=>
string(14) ""Tim Lincecum""
["Reply-To"]=>
string(14) ""Tim Lincecum""
["Return-path"]=>
string(14) ""Tim Lincecum""
["Content-Type"]=>
string(29) "text/html; charset=iso-8859-1"
["Subject"]=>
string(24) "Giants Win World Series!"
}
Upvotes: 7
Reputation: 10091
$temp = explode("\r\n", $string);
$sets = array();
foreach ($temp as $value) {
$array = explode(': ', $value);
$array[1] = trim($array[1], '"');
$sets[$array[0]] = $array[1];
}
$string
is the value you're getting from the database.
Upvotes: 3
Reputation: 255025
Since I did a good guess in comments - I think i need to repeat it here as an answer:
There is a newlines between parameters, so with
$parameters_pairs = explode("\r\n", $parameters_string);
you can split it into the name-value pairs, separated with colon.
Upvotes: 2