/    Sign up×
Community /Pin to ProfileBookmark

Creating Well Formed XML!

Hi All,

I have the following XML string…

[CODE]<?xml version=”1.0″ encoding=”UTF-8″?>
<data>
<username>bWlkYXNwcmludC5jb20=</username>
<password>NUM3NEQwRTI=</password>
<products><product>
<type>Poster</type>
<height units=”millimeters”>297</height>

<width units=”millimeters”>210</width>
</product><product>
<type>Poster</type>
<height units=”millimeters”>420</height>
<width units=”millimeters”>297</width>
</product><product>
<type>Poster</type>

<height units=”millimeters”>594</height>
<width units=”millimeters”>420</width>
</product><product>
<type>Poster</type>
<height units=”millimeters”>841</height>
<width units=”millimeters”>594</width>

</product><product>
<type>Poster</type>
<height units=”millimeters”>1189</height>
<width units=”millimeters”>841</width>
</product></products>
<test></test>
</data>[/CODE]

…and this modified function I’m using to parse it into a well formed structure…

[code=php]function formatXML($xml)
{
// parse into continuous str
$xml = str_replace(“n”, ”, $xml);
$xml = str_replace(‘ ‘, ”, $xml);
$xml = str_replace(“t”, ”, $xml);
$xml = str_replace(‘> ‘, ”, $xml);
$xml = str_replace(‘ <‘, ”, $xml);

// http://recurser.com/articles/2007/04/05/format-xml-with-php/
$xml = preg_replace(‘/(>)(<)(/*)/’, “$1n$2$3”, $xml);
$token = strtok($xml, “n”);
$result = ”;
$pad = 0;
$matches = array();
while ($token !== false)
{
if (preg_match(‘/.+</w[^>]*>$/’, $token, $matches)) {
$indent = 0;
} elseif (preg_match(‘/^</w/’, $token, $matches)) {
$pad–;
} elseif (preg_match(‘/^<w[^>]*[^/]>.*$/’, $token, $matches)) {
$indent=1;
} else {
$indent = 0;
}
$line = str_repeat(“t”, $pad) . $token;
$result .= $line . “n”;
$token = strtok(“n”);
$pad += $indent;
}

return $result;
}[/code]

…which results in this…

[CODE]<?xml version=”1.0″ encoding=”UTF-8″?>
<data>
<username>bWlkYXNwcmludC5jb20=</username>
<password>NUM3NEQwRTI=</password>
<products>
<product>
<type>Poster</type>
<height units=”millimeters”>297</height>

<width units=”millimeters”>210</width>
</product>
<product>
<type>Poster</type>
<height units=”millimeters”>420</height>
<width units=”millimeters”>297</width>
</product>

<product>
<type>Poster</type>
<height units=”millimeters”>594</height>
<width units=”millimeters”>420</width>
</product>
<product>
<type>Poster</type>

<height units=”millimeters”>841</height>
<width units=”millimeters”>594</width>
</product>
<product>
<type>Poster</type>
<height units=”millimeters”>1189</height>
<width units=”millimeters”>841</width>

</product>
</products>
[COLOR=”Red”]<test>
</test>
</data>[/COLOR][/CODE]

My problem is with the empty <test></test> tag. When it is processed by my function a newline character is placed in it and the next tag (the closing </data> tag gets tabbed over).

I can’t work out a fix for the life of me!

Can anyone help?

Thanks!

dai.hop

to post a comment
PHP

2 Comments(s)

Copy linkTweet thisAlerts:
@NogDogApr 30.2009 — You could just force it with preg_replace():
[code=php]
$result = preg_replace('#<([^>]+)>s+</1>#', "<$1></$1>", $result);
[/code]
Copy linkTweet thisAlerts:
@dai_hopauthorMay 01.2009 — Hi NogDog,

Top piece of code. The only problem now is that the closing </data> tag is still tabbed. Have I put your line in the right place?

[code=php]function formatXML($xml)
{

// parse into continuous str
$xml = str_replace("n", '', $xml);
$xml = str_replace(' ', '', $xml);
$xml = str_replace("t", '', $xml);
$xml = str_replace('> ', '', $xml);
$xml = str_replace(' <', '', $xml);

// http://recurser.com/articles/2007/04/05/format-xml-with-php/
$xml = preg_replace('/(>)(<)(/*)/', "$1n$2$3", $xml);
$token = strtok($xml, "n");
$result = '';
$pad = 0;
$matches = array();
while ($token !== false)
{
if (preg_match('/.+</w[^>]*>$/', $token, $matches)) {
$indent = 0;
} elseif (preg_match('/^</w/', $token, $matches)) {
$pad--;
} elseif (preg_match('/^<w[^>]*[^/]>.*$/', $token, $matches)) {
$indent = 1;
} else {
$indent = 0;
}
$line = str_repeat("t", $pad) . $token;
$result .= $line . "n";
$token = strtok("n");
$pad += $indent;
}
$result = preg_replace('#<([^>]+)>s+</1>#', "<$1></$1>", $result); // line inserted here
return $result;
}[/code]
×

Success!

Help @dai_hop spread the word by sharing this article on Twitter...

Tweet This
Sign in
Forgot password?
Sign in with TwitchSign in with GithubCreate Account
about: ({
version: 0.1.9 BETA 5.28,
whats_new: community page,
up_next: more Davinci•003 tasks,
coming_soon: events calendar,
social: @webDeveloperHQ
});

legal: ({
terms: of use,
privacy: policy
});
changelog: (
version: 0.1.9,
notes: added community page

version: 0.1.8,
notes: added Davinci•003

version: 0.1.7,
notes: upvote answers to bounties

version: 0.1.6,
notes: article editor refresh
)...
recent_tips: (
tipper: @AriseFacilitySolutions09,
tipped: article
amount: 1000 SATS,

tipper: @Yussuf4331,
tipped: article
amount: 1000 SATS,

tipper: @darkwebsites540,
tipped: article
amount: 10 SATS,
)...