simplexml_load_string warnings and error with a cdata string - php

I have a very long XML composed of articles and I use
$stream = new Stream\File($file, 1024);
$parser = new Parser\StringWalker();
$streamer = new XmlStringStreamer($parser, $stream);
while ($node = $streamer->getNode()) {
$simpleXmlNode = simplexml_load_string($node);
//little debug here
echo (string)$simpleXmlNode->codiceOD;
//
if(isset($simpleXmlNode->gruppo)) {
foreach($simpleXmlNode->gruppo->children() as $child) {
echo ' - ' . ($child);
}
}
echo '<br>';
}
It works very well except for a single line inside an article.
It's Italian language
<datiTecnici><![CDATA[POL<->SCHIENALE. MODULATORE DI SPINTA REGOLABILE. MULTIPOSIZIONATORE DI INCLINAZIONE. RIVESTIMENTO IN PELLE SMERIGLIATA, INTERNO IN SPUGNA HR ALTA DENSITA'. SCOCCA IN FAGGIO MULTISTRATO. BASE IN ALLUMINIO PRESSOFUSO VERNICIATO. BRACCIOLI IN POLIURETANO INTEGRALE CON ANIMA IN ACCIAIO. SEDILE REGOLABILE IN ALTEZZA MEDIANTE PISTONE A GAS (CORSA 10CM). PORTATA MAX 150KG.MISURE: H 117-127CM; L 63CM; P 60CM. (H TERRA<->SEDUTA 44-54CM). 21KG.]]></datiTecnici>
It raises
Warning: simplexml_load_string(): Entity: line 62: parser error : Extra content at the end of the document in /web/htdocs/www.site.net/home/import/iterator.php on line 81
Warning: simplexml_load_string(): in /web/htdocs/www.site.net/home/import/iterator.php on line 81
Warning: simplexml_load_string(): ^ in /web/htdocs/www.site.net/home/import/iterator.php on line 81
Notice: Trying to get property 'codiceOD' of non-object in /web/htdocs/www.site.net/home/import/iterator.php on line 82
Then stops.
I noticed that it has something to do with the length of the content inside CDATA. In fact it works fine if I cut the string a little (don't know how much yet).
What can I do?

I """solved""" it by splitting the big xml into much smaller xmls.
I don't know why it works now

Related

PHP xpath() undefined offset 0 but element exists // LARAVEL

i am really having trouble getting this to work. xpath works fine in other functions in the same file. I am trying to get a specific item from the XML file, which works fine when i dd() it. But when i try to load the exact same code into a variable it prompts "undefined offset 0". I am working local with Laravel.
XML
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<idPkg:Graphic xmlns:idPkg="http://ns.adobe.com/AdobeInDesign/idml/1.0/packaging" DOMVersion="15.1">
<Color Self="Color/u2a64f" Model="Process" Space="RGB" ColorValue="204 204 204" />
</idPkg:Graphic>
PHP
function getColor($colorID){ //$colorID = Color/u2a64f
$xml= simplexml_load_file('/Resources/Graphic.xml');
$colorNode = $xml->xpath('//Color[#Self="'.$colorID.'"]');
dd($colorNode[0]->attributes()->ColorValue);
/* outputs:
SimpleXMLElement {#316 ▼
+"0": "204 204 204"
}
*/
$fillColor = $colorNode[0]->attributes()->ColorValue; // Line of error
/* outputs:
ErrorException (E_NOTICE)
Undefined offset: 0
*/
return $fillColor;
}
EDIT:
what i just found out: when i replace the variable in xpath with the content of the variable it works.
function getColor($colorID){ //$colorID = Color/u2a64f
$xml= simplexml_load_file('/Resources/Graphic.xml');
// doesnt work
$path = '//Color[#Self="'.$colorID.'"]';
// does work
$path = '//Color[#Self="Color/u2a64f"]';
$colorNode = $xml->xpath($path);
dd($colorNode[0]->attributes()->ColorValue);
/* outputs:
SimpleXMLElement {#316 ▼
+"0": "204 204 204"
}
*/
$fillColor = $colorNode[0]->attributes()->ColorValue; // Line of error
/* outputs:
ErrorException (E_NOTICE)
Undefined offset: 0
*/
return $fillColor;
}
i just cant get my head around it... I am glad for any hints or help!
Nevermind i found the solution myself.
After checking my code again i saw that sometimes some XML nodes dont have the attribute FillColor. So i checked my param first if it is set and then proceed to xpath.

I want to add x customers on Prestashop via code but with extra fields

I'm trying to add customers with a code but the PrestaShop is giving me a bug.
I'm using PHP and XML
$XMLRQString = '<?xml version="1.0" encoding="utf-8"?>'.
'<x:Winmax4GetEntitiesRQ xmlns:x="urn:Winmax4GetEntitiesRQ">'.
'</x:Winmax4GetEntitiesRQ >';
$Params=array(
'CompanyCode'=>'',
'UserLogin'=>'',
'UserPassword'=>'',
'Winmax4GetEntitiesRQXML'=> $XMLRQString
);
$return = $client->GetEntities($Params);
$XMLRSString = new SimpleXMLElement($return->GetEntitiesResult);
foreach ($XMLRSString->Entities->Entity as $entity)
{
$default_lang= Configuration::get('PS_LANG_DEFAULT');
$customer=new Customer();
$customer->email= $entity->Email;
$customer->lastname= $entity->EntityType;
$customer->firstname= [$default_lang => $entity->Name];
$customer->contribuinte= $entity->TaxPayerID;
$customer->passwd= $entity->TaxPayerID;
$customer->active = 1;
$customer->add();
}
ERROR: (1/1) ContextErrorException Warning: preg_match() expects
parameter 2 to be string, array given
in Validate.php line 172
at ValidateCore::isCustomerName(array(object(SimpleXMLElement))) in
ObjectModel.php line 1149
at ObjectModelCore->validateField('firstname',
array(object(SimpleXMLElement))) in ObjectModel.php line 981
at ObjectModelCore->validateFields() in ObjectModel.php line 284
at ObjectModelCore->getFields() in ObjectModel.php line 551
at ObjectModelCore->add(true, true) in Customer.php line 264
at CustomerCore->add() in create_clients.php line 66
When storing values from SimpleXML, if you just refer to the element itself by it's tag name - this will be an instance of SimpleXMLElement. As you want the actual content of the element, the simplest way to do this is to cast it to a string...
$customer->firstname= (string)$entity->Name;

file_get_html error, not working

I'm using Simple HTML Dom to try scrape a HTML table.
I follow their instructions and have looked at many other code examples, but the file_get_html just doesn't seem to work.
Here is my code:
<?php
// Simple HTML Dom Parser
include('simple_html_dom.php');
//$worlds = ["Amera", "Antica", "Astera", "Aurera", "Aurora", "Bellona", "Belobra", "Beneva", "Calmera", "Calva", "Calvera", "Candia", "Celesta", "Chrona", "Danera", "Dolera", "Efidia", "Eldera", "Ferobra", "Fidera", "Fortera", "Garnera", "Guardia", "Harmonia", "Honera", "Hydera", "Inferna", "Iona", "Irmada", "Julera", "Justera", "Kenora", "Kronera", "Laudera", "Luminera", "Magera", "Menera", "Morta", "Mortera", "Neptera", "Nerana", "Nika", "Olympa", "Osera", "Pacera", "Premia", "Pythera", "Quilia", "Refugia", "Rowana", "Secura", "Serdebra", "Shivera", "Silvera", "Solera", "Tavara", "Thera", "Umera", "Unitera", "Veludera", "Verlana", "Xantera", "Xylana", "Yanara", "Zanera", "Zeluna"];
//foreach ($worlds as $world) {
// All HTML from the online list
$html = file_get_html('https://secure.tibia.com/community/?subtopic=worlds&world=Antica');
// Search for the online list table content
foreach ($html->find('tr[class=Table2]') as $row) {
$name = $row->find('td', 0)->plaintext;
$level = $row->find('td', 1)->plaintext;
$vocation = $row->find('td', 2)->plaintext;
echo $name . ' | ' . $level . ' | ' . $vocation . '<br>';
}
//}
?>
And I get these errors:
Warning: file_get_contents(): stream does not support seeking in D:\xampp\htdocs\simple_html_dom.php on line 76
Warning: file_get_contents(): Failed to seek to position -1 in the stream in D:\xampp\htdocs\simple_html_dom.php on line 76
Fatal error: Uncaught Error: Call to a member function find() on boolean in D:\xampp\htdocs\index.php:13 Stack trace: #0 {main} thrown in D:\xampp\htdocs\index.php on line 13
What am I doing wrong?
The table I am trying to scrape is the "Players Online" table on:
https://secure.tibia.com/community/?subtopic=worlds&world=Antica
Try this:
$html = str_get_html(file_get_contents($url));
This is a simple_html_dom library problem with the latest versions of PHP.
To correct it, simply change "$offset = -1," to "$offset = 0," in the parameters of the "file_get_html" function in the "simple_html_dom.php" file.
I don't know much about simpledom but i think you might need to use a more robust library like https://github.com/FriendsOfPHP/Goutte

how to create xml file using php and mysql? [duplicate]

This question already has answers here:
CakePHP Xml utility library triggers DOMDocument warning
(4 answers)
How to Construct xml in php with Special Characters?
(2 answers)
Closed 8 years ago.
I am trying to make a xml file from the data stored in my local db using php. But i am having a problem with it. as when I hard code the value I am able to get the xml file but when i am trying to call from the database i am not able to do it? so can some one help me out with it.
so here is the code that i wrote..
<?php
include 'config.php';
include 'database.php';
$sql = "select title, content, url from table limit 100";
$results = Database::GetAll($sql);
$xml = new DomDocument("1.0","UTF-8");
$content = $xml->createElement("content");
$content = $xml->appendChild($content);
foreach($results as $result) {
$item = $xml->createElement("item");
$item = $content->appendChild($item);
$title = $xml->createElement("title",$result['title']);
$title = $item->appendChild($title);
$description = $xml->createElement("description",$result['content']);
$description = $item->appendChild($description);
$link = $xml->createElement("link",htmlspecialchars($result['url']));
$link = $item->appendChild($link);
}
$xml->FormatOutput = true;
$output = $xml->saveXML();
$xml->save("xmls.xml");
?>
here Database::GetAll($sql) is a class that i have created, it executes the query and gets the table contents. the config file consists of all the database credentials and database.php is the file with the class of database.
The XML that i would want is
<content>
<item>
<title>....</title>
<description>....</description>
<url>....</url>
</item>
<item>
<title>....</title>
<description>....</description>
<url>....</url>
</item>
<item>
<title>....</title>
<description>....</description>
<url>....</url>
</item>
...till 100 values..
</content>
here the .... between the tags represent the datas retrieved from the database using mysql.
var_dump($results) gives me all the three required values upto the 100th row.
and these are the errors that I am getting while using my code..
Warning: DOMDocument::createElement(): unterminated entity reference loc=hpa1&icid=hpa1_bestofsale_010715 in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference locale=en_US&repriceOrder=true in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference subCatView=true&adcell=hpmemberjeans in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference deptId=dept20000020&subcatId=cat1003450012&N=1003070048&extDim=true&cm_re=S2-_-CAT-_-SPORT_WATCHES in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference ab=HP_BSpot_B4_40OffFootwear in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference pid=8672,8541,8532,8699,107705,8664,8806,8539,8808,8540,8826,8828,8542,104632,107703,8827&sortExpression=manual&heig in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference cm_sp=LN-_-Save+Up+to+75%25+Off+Select+Items++-_-Up+to+50%25+Off+Select+Body+Care&cp=4090263.46772866 in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference CP=ILC-FLASH:20offShoes&sortmfr=N in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference pid=8672,8541,8532,8699,107705,8664,8806,8539,8808,8540,8826,8828,8542,104632,107703,8827&sortExpression=manual&heig in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference so=2 in C:\xampp\htdocs\practice\d\xmls.php on line 23
Warning: DOMDocument::createElement(): unterminated entity reference node=10470257011&smid=ATVPDKIKX0DER&pf_rd_m=ATVPDKIKX0DER&pf_rd_t=701&pf_rd_s=center-3&pf_rd_r=0ZC491KTZNEXXHNV96NM&pf_rd_i=30&pf in C:\xampp\htdocs\practice\d\xmls.php on line 23
updated xml file output as displayed..
This page contains the following errors:
error on line 2 at column 3431: Encoding error
Below is a rendering of the page up to the first error.
Free shipping on orders worth $99 at LogoSportswearFree shipping on orders worth $99 at LogoSportswearhttp://www.logosoftwear.com/Save up to 75% on sale styles at loft.comGet a discount up to 75% on sale styles at loft.comhttp://www.loft.com/nfp-sale-cat-091312/cat1100006?supCat=catl00008&loc=hpa1&icid=hpa1_bestofsale_010715Free shipping on orders worth $200 or more at lechateau.comFree shipping on orders worth $200 or more at lechateau.comhttp://www.lechateau.com/style/index.jsp?storeId=334&locale=en_US&repriceOrder=trueSave up to 65% on outer wear at landsend.comGet a discount up to 65% on outer wear at landsend.comhttp://www.landsend.com/Free precious set with purchase worth $130 at loccitane.comFree precious set with purchase worth $130 at loccitane.com. Use the coupon code to avail the offer.http://usa.loccitane.com/precious-skin,82,1,65481,673013.htm#xcms_position=05_precious#xcms_campaign=shop_now_>Save 15% when you spend under $100 at kohls.comGet a discount of 15% when you spend under $100 at kohls.com. Use the coupon code to avail the offer.http://www.kohls.com/Save 10% on denim for the family at kmart.comGet a discount of 10% on denim for the family at kmart.comhttp://www.kmart.com/clothing-shoes-jewelry-specialty-shops-jeans-shop/b-1339616014?filter=storeOrigin&subCatView=true&adcell=hpmemberjeansSave up to 30% on dinner ware at kirklands.comGet a discount up to 30% on dinner ware at kirklands.comhttp://www.kirklands.com/category/Kitchen-Dining/Dinnerware/pc/2753/2681.uts?icid=hppromo5010115Save up to 50% on cargo pants at kingsizedirect.comGet a discount up to 50% on cargo pants at kingsizedirect.comhttp://www.kingsizedirect.com/Big-and-Tall-Cargo-Pants.aspx?DeptId=23955Free shipping on orders worth $75 at justmysizeFree shipping on orders worth $75 at justmysizehttp://www.hanes.com/justmysizeFree shipping site wide on all US orders at jomashop.comFree shipping site wide on all US orders at jomashop.com. Use the coupon code to avail the offer.http://www.jomashop.com/Save 20% on watches at jcpenney.comGet a discount of 20% on watches at jcpenney.com. Use the coupon code to avail the offer.http://www.jcpenney.com/jewelry-watches/watches/all-watches/cat.jump?id=cat100240089&deptId=dept20000020&subcatId=cat1003450012&N=1003070048&extDim=true&cm_re=S2-_-CAT-_-SPORT_WATCHESSave up to 60% on coats at jackthreads.comGet a discount up to 60% on coats at jackthreads.comhttps://www.jackthreads.com/sales/coats-are-up-to-60-off/15162
so how can i get this?
thank you
Thank you all for helping me out, with all your help and a little help from google i found the answe for it..
the updated code is as follow..
$xml = new DomDocument("1.0","UTF-8");
$content = $xml->createElement("content");
$content = $xml->appendChild($content);
foreach($results as $result) {
$item = $xml->createElement("item");
$title = $xml->createElement("title",htmlspecialchars($result['title']));
$title = $item->appendChild($title);
$description = $xml->createElement("description",htmlspecialchars($result['content']));
$description = $item->appendChild($description);
$link = $xml->createElement("link",htmlspecialchars($result['url']));
$link = $item->appendChild($link);
$item = $content->appendChild($item);
}
$xml->FormatOutput = true;
$output = $xml->saveXML();
$xml->save("xmls.xml");
I have only included the xml file. you can just create a connection with your db and use this code.

Unable to fetch Price

I am trying to fetch price from a online store.
Here i am using this code..
<?php
function getPrice($site){
$html = file_get_contents($site);
$dom = new DOMDocument();
$dom->loadHTML($html);
$contents = $dom->document.getElementsByTagName("span");
$price = "";
for($i = 0; $i < $contents->length; $i++){
$content= $contents->item($i);
if($content->getAttribute('class') == "fk-font-verybig pprice vmiddle fk-bold"){
$price = $content->getAttribute('value');
}
}
echo $price;
}
$website = "http://www.flipkart.com/sogo-ss-5365-750-w-pop-up-toaster/p/itmdz3hgfjzgfp4v?pid=PUTDYWT2UHPCDCG8&offer=DOTDOnPopUpToaster_Sep2.&icmpid=hp_dotd_3_DOTDOnPopUpToaster_Sep2.";
getPrice($website);
?>
my script return error
Warning: DOMDocument::loadHTML(): Unexpected end tag : span in Entity, line: 261 in E:\Local server\htdocs\store\scripts\getprice.php on line 5
Warning: DOMDocument::loadHTML(): htmlParseEntityRef: no name in Entity, line: 293 in E:\Local server\htdocs\store\scripts\getprice.php on line 5
...................................................................
Warning: DOMDocument::loadHTML(): htmlParseEntityRef: expecting ';' in Entity, line: 6160 in E:\Local server\htdocs\store\scripts\getprice.php on line 5
Notice: Undefined property: DOMDocument::$document in E:\Local server\htdocs\store\scripts\getprice.php on line 6
Fatal error: Call to undefined function getElementsByTagName() in E:\Local server\htdocs\store\scripts\getprice.php on line 6
Is it ok to fetch price like this because the store keep changing price of its product.
Is there any other alternative way to do so?
Will this script affect my server performance because ever time user visit a product page on my website it will fetch prices from 5 different stores to comapare prices.
$contents = $dom->document.getElementsByTagName("span");
Your $dom->document is failing because DOMDocument class does not have a property named 'document'.
Notice: Undefined property: DOMDocument::$document in E:\Local server\htdocs\store\scripts\getprice.php on line 6
So this might work
$contents = $dom->getElementsByTagName("span");
The above should work.
I recommend iterating over $contents instead of echo.
Even print_r would help you see the structure of the nodes in $contents.

Categories