Though the example below may seem long and complicated it's really not that bad, much of it is FYI for the beginners. You can skip to the bottom of this page to simply copy and paste the final code in one shot.
Goal: Using the en-ca-v1_demo database structure as your starting point (currently unavailable) lets say you want to list the names and corresponding ids of all the regions found in the World Wide Travel Guide's (WWTG) XML database on your own website.
Requirements: None other than a PHP enabled web server that is permitted to place fsockopen() calls to outside web services.
Recommendations: It is easier to build and execute custom code if you take advantage of the pre-built configuration settings and libraries already found inside the _config.php and _library.php files that come with a copy of any full or demo version of the WWTG templates. You can download a copy of the en-ca-v1_demo templates here; http://travelagentsoftware.com/forum/demoInfo.php. This example will presume that you have access to these two files and are using them in your own code. If you are not planning to 'include' these two files in your code then you'll have to refer to these examples and add the appropriate information/functions where necessary.
First off lets open the PHP code brackets and include our two resource files.
include_once "wwtg/_config.php";
include_once "wwtg/_library.php";
- The use of 'include', 'include_once', 'require' or 'require_once' is up to you, if you are unsure I recommend you use 'include_once'.
- Remember the location of these files is relative to the PHP file (where it will eventually reside on the server). If you are creating a PHP file that sits in the main folder of your website for example, i.e. the document root, then the example above is fine. However if the PHP file you are writing is located inside a subdirectory or sub-subdirectory below the main folder, you will need to walk down and back up into the correct directory to reach them, i.e. ../../wwtg/_config.php.
Next we need to build our XML request and store it inside a variable.
$XMLRequest = "<wwtgRequest>
<subscriptionId>" . $wwtg_cfg["subscriptionId"] . "</subscriptionId>
<request>
<sql>FROM `regions`</sql>
<returnFields>
<name>id</name>
<name>name</name>
</returnFields>
</request>
</wwtgRequest>";
- The naming conventions for the XML tags are the same for almost all requests to the WWTG XML server, the only tag that varies occasionally will be the 'sql' one. Sometimes this tag will be something else depending on the information your attempting to retrieve from the WWTG.
- The 'sql' tag must contain a portion of the SQL statement you wish to make on the WWTG XML servers. 'SELECT *' is automatically added when your request is processed and is not required. So the actually SQL call processed on the WWTG XML servers is 'SELECT * FROM `regions`;'
- Note the symbols used to encapsulate the word 'regions' are apostrophes not single quotes. If you use single quotes for this part of your SQL statement the request will fail, so be careful.
- Also note, these symbols and key words are not permitted as part of an SQL statement and will result in a failed request if used. semicolons (;), double quotes ("), tabs, line feeds, ALTER, COMMIT, CHANGE, CREATE, DELETE, DROP, GROUP, INSERT, INTO, JOIN, LOAD, MERGE, RENAME, SET, SHOW and UPDATE.
- The 'returnFields' tag contains the list of named fields you wnnt to see returned for each record discovered in the database. If the requests locates a valid record based on the statement found in the 'sql' tag, then the 'id' and 'name' fields will be returned.
Next we call the XML cache checking and feed requesting function call wwtg_getXML() from the _library.php file and store the results in another variable.
$regionsResponse = wwtg_getXML($XMLRequest);
- The wwtg_getXML() function will first check to see if the information being requested is already found in the local caching database. If not, it will then preform a sequence of fsockopen() function calls to find an appropriate WWTG XML server to connect to in order to request the information. Here is an example of what the XML feed would return in this case.
<?xml version="1.0" encoding="utf-8"?>
<wwtgResponse>
<request>
<sql request="FROM `regions`">
<record>
<id>1</id>
<name>North and Central America</name>
</record>
<record>
<id>2</id>
<name>The Caribbean</name>
</record>
<record>
<id>3</id>
<name>South America and the Antarctic</name>
</record>
<record>
<id>4</id>
<name>Europe</name>
</record>
<record>
<id>5</id>
<name>Africa</name>
</record>
<record>
<id>6</id>
<name>The Middle East</name>
</record>
<record>
<id>7</id>
<name>Asia</name>
</record>
<record>
<id>8</id>
<name>Australia and Oceana</name>
</record>
</sql>
</request>
</wwtgResponse>
- Once a response has been received it is stored locally in the cache and passed into the xml_parse_into_struct() function which goes through the XML feed and reorganizes it into a local array. That array pointer is then passed to the $regionsResponse variable.
- If you would like to view the contents of the array in its current state add this code next to display the output.
echo '<br /><pre>'; print_r($regionsResponse); echo '</pre><br />';
Here is a small sample of what you would see. Array
(
[0] => Array
(
[tag] => WWTGRESPONSE
[type] => open
[level] => 1
[value] =>
)
[1] => Array
(
[tag] => REQUEST
[type] => open
[level] => 2
[value] =>
)
[2] => Array
(
[tag] => SQL
[type] => open
[level] => 3
[attributes] => Array
(
[REQUEST] => FROM `regions`
)
[value] =>
)
[3] => Array
(
[tag] => RECORD
[type] => open
[level] => 4
[value] =>
)
[4] => Array
(
[tag] => ID
[type] => complete
[level] => 5
[value] => 1
)
[5] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
[6] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
[7] => Array
(
[tag] => NAME
[type] => complete
[level] => 5
[value] => North and Central America
)
[8] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
[9] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
[10] => Array
(
[tag] => RECORD
[type] => close
[level] => 4
)
[11] => Array
(
[tag] => SQL
[value] =>
[type] => cdata
[level] => 3
)
[12] => Array
(
[tag] => SQL
[value] =>
[type] => cdata
[level] => 3
)
[13] => Array
(
[tag] => RECORD
[type] => open
[level] => 4
[value] =>
)
[14] => Array
(
[tag] => ID
[type] => complete
[level] => 5
[value] => 2
)
[15] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
[16] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
[17] => Array
(
[tag] => NAME
[type] => complete
[level] => 5
[value] => The Caribbean
)
[18] => Array
(
[tag] => RECORD
[value] =>
[type] => cdata
[level] => 4
)
And so on and so on and so on...
To make the data readable we will need to further extract it into a custom array. We accomplish this by stepping through the original array, record by record, looking for what we want to keep and extracting it into a much smaller array. Here is how we did it for the WWTG templates.
if($regionsResponse) {
for($i = 0; $i < count($regionsResponse); $i++) {
if($regionsResponse[$i]["tag"] == "REQUEST" && $regionsResponse[$i]["type"] == "open") {
$i++;
while(!($regionsResponse[$i]["tag"] == "REQUEST" && $regionsResponse[$i]["type"] == "close")) {
if($regionsResponse[$i]["tag"] == "SQL" && $regionsResponse[$i]["type"] == "open") {
$sqlRequest = $regionsResponse[$i]["attributes"]["REQUEST"];
$i++;
// This sets up the starting point for a new array used to hold captured values for ease of later output.
$key = 0;
while(!($regionsResponse[$i]["tag"] == "SQL" && $regionsResponse[$i]["type"] == "close")) {
if($regionsResponse[$i]["tag"] == "RECORD" && $regionsResponse[$i]["type"] == "open") {
$i++;
while(!($regionsResponse[$i]["tag"] == "RECORD" && $regionsResponse[$i]["type"] == "close")) {
if($regionsResponse[$i]["tag"] == "ID" && $regionsResponse[$i]["type"] == "complete") {
$id = $regionsResponse[$i]["value"];
$regionsArray[$key]["id"] = $id;
} elseif($regionsResponse[$i]["tag"] == "NAME" && $regionsResponse[$i]["type"] == "complete") {
$name = $regionsResponse[$i]["value"];
$regionsArray[$key]["name"] = $name;
$key++;
}
$i++;
}
}
$i++;
}
}
$i++;
}
}
}
}
- The process above steps through the original array and strips out the information we really want to use, then copies it into a new array with named fields called '$regionsArray'. To display the contents of this new array you can use this temporary code.
echo '<br /><pre>'; print_r($regionsArray); echo '</pre><br />';
Here is what you would see. Array
(
[0] => Array
(
[id] => 1
[name] => North and Central America
)
[1] => Array
(
[id] => 2
[name] => The Caribbean
)
[2] => Array
(
[id] => 3
[name] => South America and the Antarctic
)
[3] => Array
(
[id] => 4
[name] => Europe
)
[4] => Array
(
[id] => 5
[name] => Africa
)
[5] => Array
(
[id] => 6
[name] => The Middle East
)
[6] => Array
(
[id] => 7
[name] => Asia
)
[7] => Array
(
[id] => 8
[name] => Australia and Oceana
)
) This is a lot easier to read as you can see.
All that's left to do now is breakout/use the final array somewhere in your website. Here is some code that writes the results into a table.
<table border="1" cellpadding="5" cellspacing="0">
<tr>
<td colspan="2" style="font-weight:bold; text-align:center;">Regious of the World</td>
</tr>
<tr style="font-weight:bold; text-align:center;">
<td>ID</td>
<td>Name</td>
</tr>
<?for($i = 0; $i < count($XMLArray); $i++):?>
<tr>
<td><?=$XMLArray[$i]["id"];?></td>
<td><?=$XMLArray[$i]["name"];?></td>
</tr>
<?endfor?>
</table>
- Here is what that final bit of auto-generated code would look like.
<table border="1" cellpadding="5" cellspacing="0">
<tr>
<td colspan="2" style="font-weight:bold; text-align:center;">Regious of the World</td>
</tr>
<tr style="font-weight:bold; text-align:center;">
<td>ID</td>
<td>Name</td>
</tr>
<tr>
<td>1</td>
<td>North and Central America</td>
</tr>
<tr>
<td>2</td>
<td>The Caribbean</td>
</tr>
<tr>
<td>3</td>
<td>South America and the Antarctic</td>
</tr>
<tr>
<td>4</td>
<td>Europe</td>
</tr>
<tr>
<td>5</td>
<td>Africa</td>
</tr>
<tr>
<td>6</td>
<td>The Middle East</td>
</tr>
<tr>
<td>7</td>
<td>Asia</td>
</tr>
<tr>
<td>8</td>
<td>Australia and Oceana</td>
</tr>
</table>
To summarize, here is a copy of all the code in a unified copy and paste.
<?
include_once "wwtg/_config.php";
include_once "wwtg/_library.php";
$XMLRequest = "<wwtgRequest>
<subscriptionId>" . $wwtg_cfg["subscriptionId"] . "</subscriptionId>
<request>
<sql>FROM `regions`</sql>
<returnFields>
<name>id</name>
<name>name</name>
</returnFields>
</request>
</wwtgRequest>";
$regionsResponse = wwtg_getXML($XMLRequest);
//echo '<br /><pre>'; print_r($regionsResponse); echo '</pre><br />';
if($regionsResponse) {
for($i = 0; $i < count($regionsResponse); $i++) {
if($regionsResponse[$i]["tag"] == "REQUEST" && $regionsResponse[$i]["type"] == "open") {
$i++;
while(!($regionsResponse[$i]["tag"] == "REQUEST" && $regionsResponse[$i]["type"] == "close")) {
if($regionsResponse[$i]["tag"] == "SQL" && $regionsResponse[$i]["type"] == "open") {
$sqlRequest = $regionsResponse[$i]["attributes"]["REQUEST"];
$i++;
// This sets up the starting point for a new array used to hold captured values for ease of later output.
$key = 0;
while(!($regionsResponse[$i]["tag"] == "SQL" && $regionsResponse[$i]["type"] == "close")) {
if($regionsResponse[$i]["tag"] == "RECORD" && $regionsResponse[$i]["type"] == "open") {
$i++;
while(!($regionsResponse[$i]["tag"] == "RECORD" && $regionsResponse[$i]["type"] == "close")) {
if($regionsResponse[$i]["tag"] == "ID" && $regionsResponse[$i]["type"] == "complete") {
$id = $regionsResponse[$i]["value"];
$regionsArray[$key]["id"] = $id;
} elseif($regionsResponse[$i]["tag"] == "NAME" && $regionsResponse[$i]["type"] == "complete") {
$name = $regionsResponse[$i]["value"];
$regionsArray[$key]["name"] = $name;
$key++;
}
$i++;
}
}
$i++;
}
}
$i++;
}
}
}
}
//echo '<br /><pre>'; print_r($regionsArray); echo '</pre><br />';
?>
<table border="1" cellpadding="5" cellspacing="0">
<tr>
<td colspan="2" style="font-weight:bold; text-align:center;">Regious of the World</td>
</tr>
<tr style="font-weight:bold; text-align:center;">
<td>ID</td>
<td>Name</td>
</tr>
<?for($i = 0; $i < count($regionsArray); $i++):?>
<tr>
<td><?=$regionsArray[$i]["id"];?></td>
<td><?=$regionsArray[$i]["name"];?></td>
</tr>
<?endfor?>
</table>
See, nothing to it... :-)