Populating multiple attributes into XML using PHP and MYSQL - php

I want to save my records from mysql table using PHP to an XML file.I am successfully retrieving records and saving into the database.
I want to populate my xml with ALL THE records in my customer table.(CustomerAccountNumber,CustomerAccountName ,AccountBalance, InvAddressLine1)
Here is my code:
<?
$newAcct=$db_accnt;
$newAcctname=$db_accntname;
$newAcctbalance=$db_accntbalance;
$xmldoc=new DOMDocument();
$xmldoc->load('XML/customer.xml');
$newElement = $xmldoc->createElement('Row');
$newAttribute = $xmldoc->createAttribute('CustomerAccountNumber');
$newAttribute->value = $newAct;
$newElement->appendChild($newAttribute);
$root->appendChild($newElement);
?>
My Question is :
How can I generate customer.xml and how can i save thousand of records in efficient way so that based on the database in THIS FORMAT :
<?xml version="1.0" standalone="yes"?>
<Rows>
<Row CustomerAccountNumber="CU002" CustomerAccountName="Customer 1" AccountBalance="289.00" />
<Row CustomerAccountNumber="5U002" CustomerAccountName="Customer 2" AccountBalance="1899.00" />
<Row CustomerAccountNumber="CU004" CustomerAccountName="Customer 3" AccountBalance="289.00" />
<Row CustomerAccountNumber="5U032" CustomerAccountName="Customer 4" AccountBalance="1899.00" />
</Rows>
I am not getting the clue what I need to do to generate multiple attributes for each record.Kindly help me

You can use XMLWriter
$xml =new XMLWriter();
$xml->openURI('file.xml');
$xml->setIndent(true);
$xml->startDocument('1.0', 'UTF-8', 'yes');
$xml->startElement('Rows');
while ( // fetch from DB ) {
$xml->startElement('Row');
$xml->writeattribute("CustomerAccountNumber", "1");
$xml->writeattribute("CustomerAccountName", "2");
$xml->writeattribute("AccountBalance", "3");
$xml->endElement();
}
$xml->endElement();
$xml->flush();

even if it's a XML, it's still a text file, you can just write it with file_put_contents().
$xml='<?xml version="1.0" standalone="yes"?>
<Rows>';
while($row=$result->mysqli_fetch_array()){
$xml.='<Row CustomerAccountNumber="'.$row[0].'" CustomerAccountName="'.$row[1].'" AccountBalance="'.$row[2].'" />';
}
$xml.='</Rows>';
file_put_contents("customer.xml", $xml);

You might want to consider using SimpleXML, which will help you in you .xml generation. It will be as simple as :
$row->addAttribute("CustomerAccountName", "name");
Documentation here : http://www.php.net/manual/en/simplexml.examples-basic.php

Related

Adding Nodes to Existing XML

The problem i was having is the Root XML was being produced every time it writes to the XML.
The Main issue was setting up Child and Defining the Root. From the help of Łza
I now understand the Root XML Node is ignored.
So then you setup and create a Child and then add your content, And example of the correct format is.
$xml = simplexml_load_file('FILENAME.xml'); // Load XML File Need to add IF Statment to create if does not exist
$result = $xml->addchild('Result'); // Ignore Root NODE and Add Child Results
$result->addChild('Time', gmdate('D-M-Y -H:i:s')); // Rest of the below adds Child to Result and outputs results
$result->addChild('Channel', $Site);
$result->addChild('Type', '**');
$result->addChild('Process', $Status);
$result->addChild('SKU', $code->SKU);
$result->addChild('item', $item);
$result->addChild('Status', '$Feedback');
$result->addChild('ErrorID', '$Error');
$result->addChild('Message', '$Message');
$xml->asXml('FILENAME.xml'); //Write to file would be
// All of the above Code is using variables from another part of the script
The output would be
<Root>
<Result>
<Time>Fri-May-2013 -09:15:22</Time>
<Channel>20</Channel>
<Type>**</Type>
<Process>Update</Process>
<SKU>98746524765</SKU>
<Item/>
<Status>Problem</Status>
<ErrorID>999-Error</ErrorID>
<Message>Unknown file format support</Message>
</Result>
<Result>
<Time>Fri-May-2013 -09:15:22</Time>
<Channel>20</Channel>
<Type>**</Type>
<Process>Update</Process>
<SKU>5412254785</SKU>
<Item/>
<Status>Problem</Status>
<ErrorID>123-Error</ErrorID>
<Message>Invalid Item</Message>
</Result>
</Root>
Thanks
Try to use SimpleXMLElement library instead hardcoded xml creation. This is maybe more complicate to use at the begining, but much more safe (I mean avoid possible errors in xml structure when you hardcode the xml) and easy to use when you just get start to use it.
And easy to add/remove nodes, childnodes.
This is an example for your code:
$xml = new SimpleXMLElement('<xml/>');
$data = $xml->addChild('data');
$result = $data->addChild('Result');
$result->addChild('Time', gmdate('D-M-Y -H:i:s'));
$result->addChild('Channel', $SiteID);
// ... and the same way create all your xml nodes.
// if you want add next <result> node witch all elements repeat the code, (or put it in loop if you want more <result> elements):
$result = $data->addChild('Result');
$result->addChild('Time', gmdate('D-M-Y -H:i:s'));
$result->addChild('Channel', $SiteID);
// and after create all nodes save the file:
$xml->asXml('DHError.xml');
above code will create xml:
<xml>
<data>
<Result>
<Time>Fri-May-2013 -12:14:39</Time>
<Channel>data</Channel>
</Result>
<Result>
<Time>Fri-May-2013 -12:14:39</Time>
<Channel>data</Channel>
</Result>
</data>
</xml>
Thats it. Then if you need to load and process the xml it would be easy:
To load the File simply use:
$xml2 = simplexml_load_file('DHError.xml');
// to add new node <Result>:
$resultNext = $xml2->data->addchild('Result');
$resultNext->addChild('Time', gmdate('D-M-Y -H:i:s'));
$resultNext->addChild('Channel', $SiteID);
//and save file
$xml2->asXml('DHError.xml');
this create a xml:
<?xml version="1.0" ?>
<xml>
<data>
<Result>
<Time>Fri-May-2013 -12:27:24</Time>
<Channel>data</Channel>
</Result>
<Result>
<Time>Fri-May-2013 -12:27:24</Time>
<Channel>data</Channel>
</Result>
<Result>
<Time>Fri-May-2013 -12:27:24</Time>
<Channel>data</Channel>
</Result>
</data>
</xml>

Trouble reading XML tag attributes with PHP

Given the following
<data type="new">
<time>1</time>
<time>2</time>
</data>
<data type="old">
<time>3</time>
<time>4</time>
</data
The goal being to type something along the following
<?php
$test = simplexml_load_file('http://....')
echo $test->data['type="old"']->time[0] //I want this to return 3
?>
and get the value of 3!
I hate tried using attributes but I'm still on the search for the solution.
Thanks,
JTC
The actually doc I'm trying to parse from
<data type="current observations">
<time-layout time-coordinate="local">
<start-valid-time period-name="current">2013-05-27T13:53:00-04:00</start-valid-time>
</time-layout>
</data>
I attempted the following but got an Invalid expression warning.
$weather = simplexml_load_file('http://...');
$time=$weather->xpath('//data[#type="current observations"]/"time-layout"/"start-valid- time"');
echo $time[0];
Here's a code snippet using SimpleXMLElement and XPath. I've added a root datas node so the XML could be parsed, I'm guessing yours is well formed.
<?php
$xml = <<<XML
<datas>
<data type="new">
<time>1</time>
<time>2</time>
</data>
<data type="old">
<time>3</time>
<time>4</time>
</data>
</datas>
XML;
$sxe = new SimpleXMLElement($xml);
$time = $sxe->xpath('//data[#type="old"]/time');
echo $time[0];
Output
3
OK, taking your actual XML document which is well-formed, you could do this...
$data = $weather->xpath('/data[#type="current observations"]');
$time_layout = $data[0]->xpath('time-layout[#time-coordinate="local"]');
$start_valid_time = $time_layout[0]->xpath('start-valid-time[#period-name="current"]');
echo (string)$start_valid_time[0];
See it in action here.

Saving XML In Correct Format Using PHP And DOM

i am facing a problem in updating my XML using PHP & DOM.My XML file is in this format:
Original XML (& desired xml layout):
<?xml version="1.0" standalone="yes"?>
<Rows>
<Row CustomerAccountNumber="COU002" />
<Row CustomerAccountNumber="COU023" />
<Row CustomerAccountNumber="C2335" />
<Row CustomerAccountNumber="CvbU002" />
And the code that saves i.e adds the new record to the XML(customer.xml) is:
<?php
$xmldoc=new DOMDocument();
$xmldoc->load('XML/customer.xml');
$newAct= 'c12345';
$root = $xmldoc->firstChild;
$newElement= $xmldoc->createElement('CustomerAccountNumber');
$root->appendChild($newElement);
$newText= $xmldoc->createTextNode($newAct);
$newElement->appendChild($newText);
$xmldoc->save('XML/customer.xml');
?>
Issue : The Code is generating the new record in this format:
<Rows>
<Row CustomerAccountNumber="COU002" />
<Row CustomerAccountNumber="COU023" />
<Row CustomerAccountNumber="C2335" />
<Row CustomerAccountNumber="CvbU002" />
<CustomerAccountNumber>c12345</CustomerAccountNumber>
</Rows>
I couldn't understand where i am making mistake.All i want to retain my original XML format.I want output file in the above mentioned original format(See top).Kindly guide me and point me where i am making mistake that is generating incorrect format within the file itself.Plz help
Your issue is that you are currently creating a new CustomerAccountNumber element. Instead, you want to create a new Row element, and then create a new CustomerAccountNumber attribute:
$newElement = $xmldoc->createElement('Row');
$newAttribute = $xmldoc->createAttribute('CustomerAccountNumber');
$newAttribute->value = $newAct;
$newElement->appendChild($newAttribute);
$root->appendChild($newElement);

Pulling a specific field with php out of a xml upload

I've been trying to get the id field to pull and have no idea where I'm going wrong. The rest of the data pulls correctly but I'm trying to add something new to some existing code and everything I've tried hasn't worked. Below is my XML and the PHP code I've been working off of.
I haven't worked with a combo of xml and php before so I could really use a push in the right direction.
<?xml version="1.0" encoding="UTF-8"?>
<enterprise>
<person>
<sourcedid>
<source>Spirit Awards</source>
<id>SP8675309</id>
</sourcedid>
<userid>...</userid>
<name>
<fn>...</fn>
</name>
<email>...</email>
</person>
PHP code:
function get_userid(){
return $this->uid;
}
function __construct($xmlData){
$this->uid = (string)$xmlData->id;
}
SimpleXMLdocs makes this ... well ... simple. The XML you've posted is missing a closing </enterprise> tag. Assuming the XML you're actually parsing includes the closing tag, consider:
$str = '<?xml version="1.0" encoding="UTF-8"?>
<enterprise>
<person>
<sourcedid>
<source>Spirit Awards</source>
<id>SP8675309</id>
</sourcedid>
<userid>...</userid>
<name>
<fn>...</fn>
</name>
<email>...</email>
</person>
</enterprise>
';
$xml = simplexml_load_string($str);
$var = (string) $xml->person->sourcedid->id;
echo $var; // outputs: SP8675309

Manipulate xml file with php and dom

I have XML file as below:
<?xml version="1.0" encoding="UTF-8"?>
<root version="8.0.0.0">
<songs name="Album">
<row>
<song artist="artist_name">Track1</song>
</row>
<row>
<song artist="artist_name">Track2</song>
</row>
<row>
<song artist="artist_name">Track3</song>
</row>
<row>
<song artist="artist_name">Track4</song>
</row>
</songs>
</root>
Now i want to update this file with some more rows. How i can append data on top of the existing row elements? Also while adding new elements i want to check the tracks like - Track1, Track2 are not duplicates.
Currently i'm manipulating this xml file with php:dom, but its appending data at the bottom of the existing rows.
PHP code used to do above things is
<?php
//Creates XML string and XML document using the DOM
$dom = new DOMDocument();
$dom->formatOutput = true;
$dom->Load('C:/wamp/www/xml/test1.xml');
$root = $dom->firstChild;
$list = $root->childNodes->item(1);
if(isset($_POST['submit'])){
$artistName = $_POST['name'];
$track = $_POST['track'];
$row = $dom->createElement('row');
$list->appendChild($row);
$song = $dom->createElement('song');
$row->appendChild($song);
$song->setAttribute('artist', $artistName);
$wcm_node = $dom->createTextNode($track);
$song->appendChild($wcm_node);
}
// Code to format XML after appending data
$outXML = $dom->saveXML(); // put string in outXML
//now create a brand new XML document
$xml = new DOMDocument();
$xml->preserveWhiteSpace = false;
$xml->formatOutput = true; //yup, going to try to make this format again
//pass the output of the first bunch of stuff we did to the new XML document:
$xml->loadXML($outXML);
//now display the cleanly formatted output without using LIBXML_NOBLANKS (which may have undesired consequences
$xml->save('test1.xml'); // save as file
}
?>
Please let me know, how i can do it.
Thanks
That's not appending but prepending. DOM has a method for that, too:
DOMNode::insertBefore — Adds a new child before a reference node
Example (demo):
$dom = new DOMDocument;
$dom->loadXml('<rows><row xml:id="r1"/></rows>');
$dom->documentElement->insertBefore(
$dom->createElement('row', 'new row'),
$dom->getElementById('r1')
);
$dom->formatOutput = TRUE;
echo $dom->saveXml();
Output:
<?xml version="1.0"?>
<rows>
<row>new row</row>
<row xml:id="r1"/>
</rows>

Categories