saving an output to .xml format - php

I a working on a sample project that gives positions of Telecom operators cell towers based on regions on google maps.
I am following the steps from the google maps API how-to
google maps instructions
i am stuck here. I have followed all the instructions and i am also getting XML output on my webpage from the database. Now as per the instructions that i have to follow, i have to save this output to an .XML file to my server for further processing, and adding markers on the google maps. The markers include the Lat - Long values and some information on the cell towers selected: cell-id, Location code and radio type.
I have searched for the solution but i am stuck at - PHP: DOMDocument::save and how to implement in my code.
The code for the same is attached for reference:
function parseToXML($htmlStr) {
$xmlStr = str_replace('<','<',$htmlStr);
$xmlStr = str_replace('>','>',$htmlStr);
$xmlStr = str_replace('"','"',$htmlStr);
$xmlStr=str_replace("'",''',$xmlStr);
$xmlStr = str_replace('&','&',$htmlStr);
return $xmlStr;
}
$t_query = "SELECT `radio_type`, `lac`,`cell-id`,`longitude`,`latitude` FROM `".DBNAME."`.`celltower` WHERE `mcc` = '".$mcc."' AND `mnc` = '".$mnc."'";
$t_query_exec = mysqli_query($con, $t_query);
if($t_num_rows = 0) {
die("Unable to fetch any data..Please try again..!!");
} else {
header("Content-type: text/xml");
//Begin XML file, echo parent node.
echo '<?xml version="1.0" encoding="utf-8"?>';
echo '<root>';
echo '<markers>';
//Iterating through rows, and printing XML nodes for each
while($t_var = mysqli_fetch_assoc($t_query_exec)) {
//Add to XML document node.
echo '<marker ';
echo 'radio_type="' .parseToXML($t_var['radio_type']) . '" ';
echo 'lac="' .parseToXML($t_var['lac']) . '" ';
echo 'cell-id="' .parseToXML($t_var['cell-id']) . '" ';
echo 'longitude="' . $t_var['longitude'] . '" ';
echo 'latitude="' .$t_var['latitude'] . '" ';
echo '/>';
}
echo '</markers>';
echo '</root>';
}
i just need to know that how can i save the output to an .XML file
Thanks in advance.

Just put your XML into a variable and save it with file_put_contents()
$xmlString = '<?xml version="1.0" encoding="utf-8"?>';
$xmlString .= '<root>';
$xmlString .= '<markers>';
//Iterating through rows, and printing XML nodes for each
while($t_var = mysqli_fetch_assoc($t_query_exec)) {
//Add to XML document node.
$xmlString .= '<marker ';
$xmlString .= 'radio_type="' .parseToXML($t_var['radio_type']) . '" ';
$xmlString .= 'lac="' .parseToXML($t_var['lac']) . '" ';
$xmlString .= 'cell-id="' .parseToXML($t_var['cell-id']) . '" ';
$xmlString .= 'longitude="' . $t_var['longitude'] . '" ';
$xmlString .= 'latitude="' .$t_var['latitude'] . '" ';
$xmlString .= '/>';
}
$xmlString .= '</markers>';
$xmlString .= '</root>';
file_put_contents('output.xml', $xmlString);

Related

Compress sitemap.xml into sitemap.xml.gz in php making the file damage

I am trying to convert the sitemap.xml into sitemap.xml.gz , The pages I am extracting from the database , it is converting into sitemap.xml , but when I am trying to compress this is not working . this is my code it is making the file damage .
header('content-type: application/x-gzip');
header('Content-Disposition: attachment; filename="sitemap.xml.gz"');
$xmlString = '<?xml version="1.0" encoding="UTF-8"?>';
$xmlString .= '<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd">';
include("admin/functions/dbconfig.php");
$sql = "select * from zz where aa between 1 and 30000";
$result = mysqli_query($conn,$sql);
while ($row = mysqli_fetch_array($result)){
$url = $row["aa"];
$xmlString .= '<url>';
$xmlString .= '<loc>http://mynewdomain.com/page.php?word='.htmlentities($url).'</loc>';
$xmlString .= '<lastmod>'.date("Y-m-d").'</lastmod>';
$xmlString .= '<changefreq>monthly</changefreq>';
$xmlString .= '<priority>0.5</priority>';
$xmlString .= '</url>';
}
$xmlString .= '</urlset>';
gzwrite("compress", gzencode($xmlString));
gzclose("compress");

Creating an XML file from PHP

I am trying to create XML files via PHP for Googles Merchant center.
I had previously done the same with creating a sitemap but now am having issues.
$xmlString = '<?xml version="1.0" encoding="UTF-8"?>';
$xmlString .= '<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd">';
$xmlString .= '<url>';
$xmlString .= '<loc>example.com</loc>';
$xmlString .= '<lastmod>'.date(DATE_ATOM,time()).'</lastmod>';
$xmlString .= '<changefreq>daily</changefreq>';
$xmlString .= '<priority>1.0</priority>';
$xmlString .= '</url>';
$xmlString .= '</urlset>';
$dom = new DOMDocument;
$dom->preserveWhiteSpace = FALSE;
$dom->loadXML($xmlString);
$dom->save('../sitemap.xml');
This is more or less what I have to create my sitemap except I am obviously creating more URLs by querying my database.
But then I do more or less the exact same thing for my product feed but it does not work.
$xmlString .= '<?xml version="1.0" encoding="UTF-8"?>';
$xmlString .= '<rss version="2.0" xmlns:g="http://base.google.com/ns/1.0">';
$xmlString .= '<channel>';
$xmlString .= '<title>Product Feed</title>';
$xmlString .= '<link>https://www.example.com/</link>';
$xmlString .= '<description>Product Feed</description>';
$xmlString .= '<item>';
$xmlString .= '<g:id>'.$product_id.'</g:id>';
$xmlString .= '<title>'.$product_name.'</title>';
$xmlString .= '<description>'.$product_description.'</description>';
$xmlString .= '<link>https://www.example.com/product/'.$product_url.'</link>';
$xmlString .= '<g:condition>new</g:condition>';
$xmlString .= '<g:price>'.$rounded_lowest_sale_price.'</g:price>';
$xmlString .= '<g:availability>in stock</g:availability>';
$xmlString .= '<g:image_link>https://www.example.com/media/product_images/'.$first_image.'</g:image_link>';
$xmlString .= '<g:mpn>'.$model_no.'</g:mpn>';
$xmlString .= '<g:brand>'.$brand.'</g:brand>';
$xmlString .= '<g:google_product_category>Business & Industrial > Material Handling</g:google_product_category>';
$xmlString .= '</item>';
}
$xmlString .= '</channel>';
$xmlString .= '</rss>';
echo $xmlString;
$dom = new DOMDocument;
$dom->preserveWhiteSpace = FALSE;
$dom->loadXML($xmlString);
$dom->save('../product_feeds/product_feed_int.xml');
It saves the XML file but all it contains is:
<?xml version="1.0"?>
without even the UTF-8 encoding.
If you don't use DOMDocument to create the xml you can put your string directly into a file
file_put_contents('../product_feeds/product_feed_int.xml', $xmlString);
consider to use & for & in
Business & Industrial
This might Help
<?php
$xmldoc = new DOMDocument();
$xmldoc->encoding = 'utf-8';
$xmldoc->xmlVersion = '1.0';
$xmldoc->formatOutput = true;
$xml_file_name = 'xmlfile.xml';
$root = $xmldoc->createElement('Cars');
$car_node = $xmldoc->createElement('car');
$attr_movie_id = new DOMAttr('car_model', 'ritz');
$car_node->setAttributeNode($attr_movie_id);
$child_node_title = $xmldoc->createElement('Make', 'Maruti');
$car_node->appendChild($child_node_title);
$child_node_year = $xmldoc->createElement('Year', 2012);
$car_node->appendChild($child_node_year);
$child_node_genre = $xmldoc->createElement('Type', 'Hatchback');
$car_node->appendChild($child_node_genre);
$child_node_ratings = $xmldoc->createElement('Ratings', 6.2);
$car_node->appendChild($child_node_ratings);
$root->appendChild($car_node);
$xmldoc->appendChild($root);
$xmldoc->save($xml_file_name);
echo "$xml_file_name created";
?>

Will string concat case performant issue in PHP?

I see some code like this in PHP
public function fetch()
{
$xml = '';
$xml .= '<' . '?xml version="1.0" encoding="utf-8"?' . '>' . "\n";
$xml .= '<rss version="2.0">';
$xml .= '<channel>';
$xml .= '<title>TEST</title>';
$xml .= '<description>TEST</description>';
foreach ($this->items as $item)
{
$xml .= '<item>';
$xml .= '<title>' . $item['title'] . '</title>';
$xml .= '<description>' . $item['body'] . '</description>';
$xml .= '</item>';
}
$xml .= '</channel>';
$xml .= '</rss>';
return $xml;
}
The code use a lots of stings concat (.=), do you think it is not a good way to do it ?
It look like will case unnecessary memory usage for me.
Those code was a part of "VIEW' of MCV, the function has already get the processed data in a array of "items". And the function is going to make the render.
Will you agree instead of
echo $this->fetch();
using a template file is better ? like this :
include('template.php');
and then in template.php :
<?xml version="1.0" encoding="utf-8">
<rss version="2.0">
<channel>
<title>TEST</title>
<description>TEST</description>
<?
foreach ($this->items as $item){
echo '<item>';
echo '<title>' . $item['title'] . '</title>';
echo '<description>' . $item['body'] . '</description>';
echo '</item>';
}
?>
</channel>
</rss>
I think the second approach would be better. Do you agree? or any other comment ?
Edit :
A user point out that using a template has it's lack too. So, when will you using the the template and when will not ? (those tutorials just always tell me i can use template anyways, i got a little confuse.)
Using a template is not necessarily better since it is an I/O operation (and I/O operation are often costly).
The concatenation in comparison is several times more performant. You could either remove the unnecessary concatenations (like the '<' . '?xml' part) or use HEREDOC / NOWDOC (http://php.net/manual/fr/language.types.string.php).
At the end of the day, it's mostly up to the developper's choice as long as the application is not purely performance-driven.
EDIT: as stated in comments, using an XML reader / writer class would prove more robust and increase maintainability.

XML Parsing Error: not well-formed, opening xml tags

This snippet of code use to work perfectly, nothing has changed except now it's giving off errors.
function wrapOutput($str){
header('content-type: text/xml; charset: utf-8');
$o = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
$o .= ' <rss version="2.0"
xmlns:media="http://search.yahoo.com/mrss/"
xmlns:amp="http://www.adobe.com/amp/1.0">' . PHP_EOL;
$o .= ' <channel>' . PHP_EOL;
$o .= $str;
$o .= ' </channel>' . PHP_EOL;
$o .= ' </rss>' . PHP_EOL;
return $o;
}
Something is going wrong and turning the xml tags into <'xml version="1.0" encoding="UTF-8"'>
Which results into the following error
XML Parsing Error: not well-formed
Location: http://localhost/mrss.php?feed=test
Line Number 1, Column 2:<'xml version="1.0" encoding="UTF-8"'>
-^
I think the problem is de quotes, beacause XML read like eval(), sou u can try escape \"\" quotes

XML source generated by PHP is messy [duplicate]

This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
format xml string
I'm generating an XML page like so:
header('Content-Type: text/html');
$xmlpage = '<?xml version="1.0" charset="utf-8"?>';
$xmlpage .= '<conv>';
$xmlpage .= '<at>6 January 2012 12:00</at>';
$xmlpage .= '<rate>1.56317</rate>';
$xmlpage .= '<from>';
$xmlpage .= '<code>'.$from.'</code>';
$xmlpage .= '<curr>Pound Sterling</curr>';
$xmlpage .= '<loc>UK</loc>';
$xmlpage .= '<amnt>'.$amnt.'</amnt>';
$xmlpage .= '</from>';
$xmlpage .= '</conv>';
echo $xmlpage;
When viewing the page source, it looks terrible:
<?xml version="1.0" charset="utf-8"?><conv><at>6 January 2012 12:00</at><rate>1.56317</rate><from><code>USD</code><curr>Pound Sterling</curr><loc>UK</loc><amnt>23</amnt></from><to><code>GBP</code><curr>United States Dollar</curr><loc>USA</loc><amnt>14.73</amnt></to></conv>
How can I make this so it's properly formatted and indented?
Add newlines with the \r\n or only \n characters. You'll need to place your strings in double quotes ("") for it to work, so either replace the double-quotes inside the strings with single ones ('), escape the double quotes (\"), add ."\r\n" as a linebreak or use HEREDOC.
Building your XML with a XML generator like the built-in SimpleXML will prevent these sort and numerous other types of problems and is usually far easier than building it by hand with strings.
You could:
Do it yourself by adding whitespace characters to your strings (\n, \t).
Output all your XML with a HEREDOC
You could create or even generate a DOMDocument and use saveXML()
The first two are quick and dirty (heredoc's better). The latter is more robust, but more code.
Use a HEREDOC. it'll be far easier to read than repeated string concatenation, allows tabs/multilines, and does variable interpolation for you:
$xmlpage = <<<EOL
<?xml version="1.0" charset="utf-8"?>
<conv>
<at>6 January 2012 12:00</at>
<rate>1.56317</rate>
<from>
<code>$from</code>
<curr>Pound Sterling</curr>
<loc>UK</loc>
<amnt>$amnt</amnt>
</from>
</conv>
EOL;
Use a stylesheet and an XML viewer to view it.
add a \n after every $xmlpage. You should be able to view it properly after the echo.
e.g.
$xmlpage = "<?xml version="1.0" charset="utf-8"?>\n";
$xmlpage .= "<conv>\n";
$xmlpage .= "<at>6 January 2012 12:00</at>\n";
$xmlpage .= "<rate>1.56317</rate>\n";
The simplest way would be to add the appropriate whitespace to the beginning of the strings, and the newlines to the ends.
$xmlpage = '<?xml version="1.0" charset="utf-8"?>';
$xmlpage .= '<conv>' . "\n";
$xmlpage .= "\t" . '<at>6 January 2012 12:00</at>' . "\n";
$xmlpage .= "\t" . '<rate>1.56317</rate>' . "\n";
$xmlpage .= '<from>' . "\n";
$xmlpage .= "\t" . '<code>'.$from.'</code>' . "\n";
$xmlpage .= "\t" . '<curr>Pound Sterling</curr>' . "\n";
$xmlpage .= "\t" . '<loc>UK</loc>' . "\n";
$xmlpage .= "\t" . '<amnt>'.$amnt.'</amnt>' . "\n";
$xmlpage .= '</from>' . "\n";
$xmlpage .= '</conv>';
Or something along those lines, depending on your desired output.
Here's my prettify function, which formats for output. You can modify it to suit your needs.
function prettifyXML( $xml )
{
// Break our XML up into sections of newlines.
$xml = preg_replace( '/(<[^\/][^>]*?[^\/]>)/', "\n" . '\1', $xml );
$xml = preg_replace( '/(<\/[^\/>]*>|<[^\/>]*?\/>)/', '\1' . "\n", $xml );
$xml = str_replace( "\n\n", "\n", $xml );
$xml_chunks = explode( "\n", $xml );
$indent_depth = 0;
$open_tag_regex = '/<[^\/\?][^>]*>/';
$close_tag_regex = '/(<\/[^>]*>|<[^>]*\/>)/';
// Fix the indenting.
foreach ( $xml_chunks as $index => $xml_chunk )
{
$close_tag_count = preg_match( $close_tag_regex, $xml_chunk );
$open_tag_count = preg_match( $open_tag_regex, $xml_chunk );
if ( $open_tag_count >= $close_tag_count )
{
$temp_indent_depth = $indent_depth;
}
else
{
$temp_indent_depth = $indent_depth - $close_tag_count;
}
$xml_chunks[ $index ] = str_repeat( "\t", $temp_indent_depth ) . $xml_chunk;
$indent_depth += $open_tag_count - $close_tag_count;
}
$xml = implode( "\n", $xml_chunks );
// Add tokens for attributes and values.
$attribute_regex = '/([\w:]+\="[^"]*")/';
$value_regex = '/>([^<]*)</';
$value_span_token = '########';
$attribute_span_token = '########';
$span_close_token = '########';
$xml = preg_replace( $value_regex, '>' . $value_span_token . '\1' . $span_close_token . '<', $xml );
$xml = preg_replace( $attribute_regex, $attribute_span_token . '\1' .$span_close_token, $xml );
$xml = htmlentities( $xml );
// Replace the tokens that we added previously with their HTML counterparts.
$xml = str_replace( $value_span_token, '<span class="value">', $xml );
$xml = str_replace( $attribute_span_token, '<span class="attribute">', $xml );
$xml = str_replace( $span_close_token, '</span>', $xml );
return $xml;
}
It's been relatively well tested to handle edge cases, though it's not highly efficient because it's only for viewing logs.

Categories