Get data from XML with PHP - php

below is part of my XML where I try to get data from, basicly I need to insert them to array where "role" is key and "entry" is value.
Here is XML:
<CommunicationDetailList>
<CommunicationDetail>
<Role>Phone1</Role>
<Entry>727831333</Entry>
</CommunicationDetail>
<CommunicationDetail>
<Role>Mobile</Role>
<Entry>727834125</Entry>
</CommunicationDetail>
<CommunicationDetail>
<Role>Fax1</Role>
<Entry>123456789</Entry>
</CommunicationDetail>
<CommunicationDetail>
<Role>EMail1</Role>
<Entry>moj#mail.sk</Entry>
</CommunicationDetail>
</CommunicationDetailList>
This is my PHP code, unfotunately it doesn't work correctly (add just first one not rest of it, so I have access just to Phone1):
//this is somewhere on top of my code
$doc = new DOMDocument();
//Load XML to DOM
$doc->loadXml($xml);
.
.
// here I parse rest of XML, where `<tags>` are unique
.
.
//and here is that important part
$communicationDetails = $doc->getElementsByTagName( "CommunicationDetailList" );
foreach( $communicationDetails as $detail )
{
$keys = $detail->getElementsByTagName( "Role" );
$key = $keys->item(0)->nodeValue;
$values = $detail->getElementsByTagName( "Entry" );
$value = $values->item(0)->nodeValue;
//adding login and password to array
$data[$key] = $value;
}
Can someone help me to access to this XML

Try using SimpleXMLElement like this
<?php
$xml = 'data.xml';
//load xml from file
$doc = simplexml_load_file($xml);
// or load from string
// $doc = simplexml_load_string($xmlString);
foreach($doc->CommunicationDetail as $detail){
//print $detail->Role . ' - ' . $detail->Entry . PHP_EOL;
$data[(string)$detail->Role] = (string)$detail->Entry;
// we cast the xml elements as strings to be used as keys and values in the array
}
print_r($data);
//output is
Array
(
[Phone1] => 727831333
[Mobile] => 727834125
[Fax1] => 123456789
[EMail1] => moj#mail.sk
)

Try this may be it help
foreach( $communicationDetails as $detail )
{
$keys = $detail->getElementsByTagName( "Role" );
$values = $detail->getElementsByTagName( "Entry" );
$length = $keys->length;
for($i = 0; $i <= $length; $i++)
{
$key = $keys->item($i)->nodeValue;
$value = $values->item($i)->nodeValue;
$data[$key] = $value;
}
}

The problem is with
$item(0)
If you were to use a iterated loop like
for ($i=0; $i<count($keys); $i++) { echo $keys[$i]; }
Then it would go through the entire array.

Related

replace values of keys in json1 from Json2

I am very very new to php.. actually i am from java domain. But, i have to do some work in php for integration. My scenario is, i have one json array which will have 4 keys for ex:
one json --> {"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"}.
I will be getting another JSON which ever edited from admin panel. for example if i updated any key, only that key will coming in the
second JSON --> for ex: {"blog_heading":"def"}
Now, i have to replace the value of second json to first json. example output for above scenario like I am very very new to php.. actually i am from java domain. But, i have to do some work in php for integration. My scenario is, i have one json array which will have 4 keys for ex:
output json --> {"id":7,"active":1,"blogId":"abc","blog_heading":"def"}.
So i am trying as below,
$id = json_decode($data_string);
$id2 = json_encode($post);
$id5 = json_decode($id2);
$id6 = array();
foreach ($id as $key => $value)
{
$log->debug($key . ': ' . $value);
if (array_key_exists($key, $id5->data)) {
$log->debug($key . 'element is in the array');
$log->debug($value . 'element is in the array');
//array_push($id5, "apple", "raspberry");
$id3 = array($key => $value);
$id3[$key] = $value;
$log->debug($id3);
}else{
$log->debug($key . 'element is not in the array');
}
}
$id7 = json_encode($id2);
$log->debug($id7);
id5 data is : $id5
DEBUG - 2017-06-05T02:26:20-04:00 - stdClass Object
(
[meta] => stdClass Object
(
[table] => story
[type] => item
)
[data] => stdClass Object
(
[id] => 7
[active] => 1
[blogId] => abc
[blog_heading] => xyz
)
)
==================
Log of $id :
stdClass Object
(
[active] => 1
[blog_heading] => def
[id] => 7
)
Please suggest me how can i achieve this... Anything i am doing wrong here
Please try that:
$j1 = '{"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"}';
$j2 = '{"blog_heading":"def"}';
$result = json_encode(
array_merge(
json_decode($j1, true),
json_decode($j2, true)
)
);
<?php
$json1='{"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"}';
$json2='{"blog_heading":"def"}';
$json1=json_decode($json1);
$json2=json_decode($json2);
foreach ($json1 as $key => $value) {
if($json2->$key){
$json1->$key=$json2->$key;
}
}
$json1=json_encode($json1);
$json2=json_encode($json2);
If you have only one element in array,Do like this
$a = json_decode('{"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"}',true);
$b = json_decode('{"blog_heading":"def"}',true);
$a['blog_heading'] = $b['blog_heading'];
print_r($a);
If you have multiple element like this :
$c = json_decode('[{"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"},
{"id":8,"active":1,"blogId":"abc","blog_heading":"xyz"}]',true);
$d = json_decode('[{"blog_heading":"def"},{"blog_heading":"hello"}]',true);
$return = array();
for ($i=0; $i < count($c); $i++) {
$c[$i]['blog_heading'] = $d[$i]['blog_heading'];
$return[] = $c[$i];
}
print_r($return);
If you want to replace value by specific id
$c = json_decode('[{"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"},
{"id":8,"active":1,"blogId":"abc","blog_heading":"xyz"}]',true);
$d = json_decode('[{"id":7,"blog_heading":"def"},{"id":9,"blog_heading":"hello"}]',true);
$return = array();
for ($i=0; $i < count($c); $i++) {
if($d[$i]['id'] == $c[$i]['id']) {
$c[$i]['blog_heading'] = $d[$i]['blog_heading'];
}
$return[] = $c[$i];
}
print_r($return);
Checking dynamic key value pair :
$c = json_decode('[{"id":7,"active":1,"blogId":"abc","blog_heading":"xyz"},
{"id":8,"active":1,"blogId":"abc","blog_heading":"xyz"}]',true);
$d = json_decode('[{"id":6,"blog_heading":"def"},{"id":9,"blog_heading":"hello"}]',true);
$return = array();
for ($i=0; $i < count($c); $i++) {
$result = array_intersect_key($c[$i], $d[$i]);
foreach ($result as $key => $value) {
$c[$i][$key] = $d[$i][$key];
}
$return[] = $c[$i];
}
print_r($return);
Check demo here

How can I don't use global variables in this page?

on php document, I made this function.
function getPrices($url) {
global $priceList; // declare global . point of this.
$src = file_get_contents_curl($url);
$dom = new DOMDocument();
$selector = new DOMXPath($dom);
$results = $selector->query('//table/tr/td/span');
foreach($results as $node) {
array_push($priceList, $node->nodeValue);
}
}
and bottom of page, I called it several.
$priceList = array();
getPrices("http://finance.naver.com/item/sise_day.nhn?code=005930");
getPrices("http://finance.naver.com/item/sise_day.nhn?code=005930&page=2");
getPrices("http://finance.naver.com/item/sise_day.nhn?code=005930&page=3");
and display it.
echo $priceList[1];
echo $priceList[2];
echo $priceList[3];
The problem is I'm using CMS kinds of Joomla, Wordpress, and they do not support using global variable So I don't know how to I make this without using global. How can I make it? I need many pages to scrapping, so I'm very afraid. if I scrap just one page,
return in function,
and
$priceList = getPrices("http://finance.naver.com/item/sise_day.nhn?code=$code");
But I don't know many scrapping case. Please help me...
Generally speaking, you shouldn't be using global variables anyways. It's bad practice. Here is one way you can restructure it:
function getPrices($url) {
// this is just a local scoped temp var
$priceList = array();
$src = file_get_contents_curl($url);
$dom = new DOMDocument();
$selector = new DOMXPath($dom);
$results = $selector->query('//table/tr/td/span');
foreach($results as $node) {
array_push($priceList, $node->nodeValue);
}
// return the price list
return $priceList;
}
// here is your real price list
$priceList = array();
// array of urls
$urls = array(
"http://finance.naver.com/item/sise_day.nhn?code=005930",
"http://finance.naver.com/item/sise_day.nhn?code=005930&page=2",
"http://finance.naver.com/item/sise_day.nhn?code=005930&page=3"
// etc..
);
// loop through the urls and assign the results to the price list
foreach ($urls as $url) {
$priceList[] = getPrices($url);
}
Now you have $priceList as an array to do whatever with. Or, if you are looking to immediately output.. you can just skip putting it into $priceList and do your output in the loop above
You could return the partial results from the function and merge them into the complete results array.
<?php
$result = [];
$result = array_merge($result, getSomeValues());
$result = array_merge($result, getSomeValues());
$result = array_merge($result, getSomeValues());
var_export($result);
function getSomeValues() {
static $i = 0;
// returning a partial result of three elements
return [ $i++, $i++, $i++ ];
}
prints
array (
0 => 0,
1 => 1,
2 => 2,
3 => 3,
4 => 4,
5 => 5,
6 => 6,
7 => 7,
8 => 8,
)
You could store the partial results as elements of an array of results.
This way you'd keep some of the information of "what" produced the result.
(You could even use the url as array index)
<?php
$result = [];
$result[] = getSomeValues();
$result[] = getSomeValues();
$result[] = getSomeValues();
// now $result is an array of arrays of (some scalar value)
// so your iteration has to be changed
foreach( $results as $presult ) {
foreach( $presult as $element ) {
..do something with $element
}
}
// or you can "hide" the nesting with
$it = new RecursiveIteratorIterator(new RecursiveArrayIterator($result));
foreach($it as $e ) {
echo $e, ', ';
} // see http://docs.php.net/spl
function getSomeValues() {
static $i = 0;
return [ $i++, $i++, $i++ ];
}
The RecursiveIteratorIterator/foreach part prints 0, 1, 2, 3, 4, 5, 6, 7, 8,

how to skip the duplicate occurence of a row of data using ArrayObject in PHP?

am trying to print out only the unique values. since am receiving a huge object array from the I am trying to use now the ArrayObject class of PHP to iterate
$arrayobject = new ArrayObject($data);
$iterator = $arrayobject->getIterator();
while($iterator->valid()){
echo $iterator->current()->USERID. " : " .$iterator->current()->SUBCATID."<br/>";
$iterator->next();
}
here's the current result of that
201087 : 1
201146 : 1
201087 : 3
201087 : 2
as you can see, the first data has two other duplicates
and also, the first and second data has similar subcatid..
the objective is, print only the unique userid and subcatid..
how to skip those duplicate data, given that sample code of mine
as a starting point ?
Not quite sure I understand the question but maybe....
You can either sort the array and remember the current userid so your script can skip duplicates until it reaches another id.
<?php
$data = data();
usort(
$data,
function($a,$b) {
return strnatcmp($a->USERID, $b->USERID);
}
);
$current = null;
foreach( $data as $e ) {
if ( $current!=$e->USERID ) {
$current = $e->USERID;
echo $e->USERID, ' ', $e->SUBCATID, "\n";
}
}
function data() {
$x = array(
array(201087,1),
array(201146,1),
array(201087,3),
array(201087,2),
array(222222,3)
);
foreach($x as $y) {
$o = new StdClass;
$o->USERID = $y[0];
$o->SUBCATID = $y[1];
$data[] = $o;
}
return $data;
}
or the script remembers all previously processed ids, e.g. in a hashmap/array
<?php
$data = data();
$processed = array();
foreach( $data as $e ) {
if ( !isset($processed[$e->USERID]) ) {
$processed[$e->USERID] = true;
echo $e->USERID, ' ', $e->SUBCATID, "\n";
}
}
function data() {
$x = array(
array(201087,1),
array(201146,1),
array(201087,3),
array(201087,2),
array(222222,3)
);
foreach($x as $y) {
$o = new StdClass;
$o->USERID = $y[0];
$o->SUBCATID = $y[1];
$data[] = $o;
}
return $data;
}
both scripts print
201087 1
201146 1
222222 3
$ids = array(1,2,3,4,4);
$ids = array_unique($ids); // remove duplicates

How do I create variables from XML data in PHP?

Been trying to figure this out for a short while now but having now luck, for example I have an external xml document like this:
<?xml version="1.0" ?>
<template>
<name>My Template Name</name>
<author>John Doe</author>
<positions>
<position>top-a</position>
<position>top-b</position>
<position>sidebar-a</position>
<position>footer-a</position>
</positions>
</template>
How can I process this document to create variables like this:
$top-a = top-a;
$top-b = top-b;
$sidebar-a = sidebar-a;
$footer-a = footer-a
If you can't make them into variables, how would you put them into an array?
Any help will be greatly appreciated.
From the PHP web site at http://www.php.net/manual/en/function.xml-parse.php:
Ashok dot 893 at gmail dot com 26-Apr-2010 05:52
This is very simple way to convert all applicable objects into associative array. This works with not only SimpleXML but any kind of object. The input can be either array or object. This function also takes an options parameter as array of indices to be excluded in the return array. And keep in mind, this returns only the array of non-static and accessible variables of the object since using the function get_object_vars().
<?php
function objectsIntoArray($arrObjData, $arrSkipIndices = array())
{
$arrData = array();
// if input is object, convert into array
if (is_object($arrObjData)) {
$arrObjData = get_object_vars($arrObjData);
}
if (is_array($arrObjData)) {
foreach ($arrObjData as $index => $value) {
if (is_object($value) || is_array($value)) {
$value = objectsIntoArray($value, $arrSkipIndices); // recursive call
}
if (in_array($index, $arrSkipIndices)) {
continue;
}
$arrData[$index] = $value;
}
}
return $arrData;
}
?>
Usage:
<?php
$xmlUrl = "feed.xml"; // XML feed file/URL
$xmlStr = file_get_contents($xmlUrl);
$xmlObj = simplexml_load_string($xmlStr);
$arrXml = objectsIntoArray($xmlObj);
print_r($arrXml);
?>
This will give the following result:
Array
(
[name] => My Template Name
[author] => John Doe
[positions] => Array
(
[position] => Array
(
[0] => top-a
[1] => top-b
[2] => sidebar-a
[3] => footer-a
)
)
)
You want the built in class Simplexml
Take a look at SimpleXML:
http://www.php.net/manual/en/simplexml.examples-basic.php
It parses XML into a "map-like" structure which you could then use to access your content. For your particular case,
$xml = new SimpleXMLElement($xmlstr);
$top_a = $xml->template->positions[0]
The simplest method is to use SimpleXML:
$xml = simplexml_load_string(... your xml here...);
$values = array()
foreach($xml->positions as $pos) {
$values[$pos] = $pos;
}
You do not want to auto-create variables in the manner you suggest - it litters your variable name space with garbage. Consider what happens if someone sends over an XML snippet which has <position>_SERVER</position> and you create a variable of that name - there goes your $_SERVER superglobal.
why not doing the array directly?
var positions = document.getElementsByTagName("positions");
var positions_final_arr = [];
for(int i = 0; i < positions.length; i++){
positions_final_arr[i] = [];
var inner_pos = positions[i].getElementsbyTagName("position");
for(int l = 0; l < inner_pos.length; l++){
positions_final_arr[i][l] = inner_pos[i].value;
}
}
console.log(positions_final_arr);
$str = "your xml";
$xml = simplexml_load_string($str);
$result = array();
foreach ($xml->positions as $pos) {
foreach ($pos->position as $p) {
$element = (string)$p[0];
$result[$element] = $element;
}
}
var_dump($result);
Use SimpleXML to parse the file into an object/array structure, then simply use list:
$sxml = new SimpleXMLElement($xml);
$positions = (array)$sxml->positions->children();
list($top_a, $top_b, $sidebar_a, $footer_a) = $positions['position'];
$dom = new DOMDocument;
$dom->loadXML('<root><position>a</position></root>'); //your string here
//$dom->loadXML(file_get_contents($file_with_pxml)); - from file
$position = $dom->getElementsByTagName('position');
for ($i=0; $i<$position->length; $i++)
{
$item = $position->item($i);
${$item->nodeValue} = $item->nodeValue;//$$item->nodeValue = $item->nodeValue;
}
But as I know - you can't create variable with dash in name in PHP
<?php
$xmlUrl = "feed.xml"; // XML feed file/URL
$xmlStr = file_get_contents($xmlUrl);
$xmlObj = simplexml_load_string($xmlStr);
$arrXml = json_decode(json_encode($xmlObj), true); # the magic!!!
print_r($arrXml);
?>
This will give the following result:
Array
(
[name] => My Template Name
[author] => John Doe
[positions] => Array
(
[position] => Array
(
[0] => top-a
[1] => top-b
[2] => sidebar-a
[3] => footer-a
)
)
)

How to parse this table and extract data from it?

I have the following table: http://www.nbs.rs/kursnaListaModul/srednjiKurs.faces?lang=lat
It is a currency exchange list and I need to extract some data from it. On left side of the table are currency ID numbers. Would it be possible to extract data from specified rows based on their IDs?
For example, from the table above, I want to extract currencies with IDs 978, 203, and 348.
Output should be:
EUR 104,2182
CZK 4,2747
HUF 38,7919
By looking at similar examples here, I came up with this: http://pastebin.com/hFZs1H7C
I need somehow to detect IDs and the print proper values... I'm noob when it comes to programming and I need your help.
<?php
$data = file_get_contents('http://www.nbs.rs/kursnaListaModul/srednjiKurs.faces?lang=lat');
$dom = new domDocument;
#$dom->loadHTML($data);
$dom->preserveWhiteSpace = false;
$tables = $dom->getElementsByTagName('table');
$rows = $tables->item(1)->getElementsByTagName('tr');
foreach ($rows as $row) {
$cols = $row->getElementsByTagName('td');
foreach ($cols as $col) {
echo $col;
}
}
?>
Collecting the table data as array for later usage:
$dom = new DomDocument;
$dom->loadHtmlFile('http://www.nbs.rs/kursnaListaModul/srednjiKurs.faces?lang=lat');
$xpath = new DomXPath($dom);
// collect header names
$headerNames = array();
foreach ($xpath->query('//table[#id="index:srednjiKursLista"]//th') as $node) {
$headerNames[] = $node->nodeValue;
}
// collect data
$data = array();
foreach ($xpath->query('//tbody[#id="index:srednjiKursLista:tbody_element"]/tr') as $node) {
$rowData = array();
foreach ($xpath->query('td', $node) as $cell) {
$rowData[] = $cell->nodeValue;
}
$data[] = array_combine($headerNames, $rowData);
}
print_r($data);
Output:
Array
(
[0] => Array
(
[ŠIFRA VALUTE] => 978
[NAZIV ZEMLJE] => EMU
[OZNAKA VALUTE] => EUR
[VAŽI ZA] => 1
[SREDNJI KURS] => 104,2182
)
...
)
Example usage:
foreach ($data as $entry) {
printf(
'%s %s' . PHP_EOL,
$entry['OZNAKA VALUTE'],
$entry['SREDNJI KURS']
);
}
You can use xpath and domdocument features of PHP to extract specific data from html(or xml.)
$src = new DOMDocument('1.0', 'utf-8');
$src->formatOutput = true;
$src->preserveWhiteSpace = false;
$content = file_get_contents("http://www.nbs.rs/kursnaListaModul/srednjiKurs.faces?lang=lat");
#$src->loadHTML($content);
$xpath = new DOMXPath($src);
$values=$xpath->query('//td[ contains (#class, "tableCell") ]');
foreach($values as $value)
{
echo $value->nodeValue."<br />";
}
this will print innerHTML of every td element with class="tableCell".

Categories