Jump to content

Importing XML Feed Into MYSQL Server


SmithyWiffy
Go to solution Solved by Barand,

Recommended Posts

Hi 

 

I've searched the net high and low for an answer and found a script on this forum which I have used as shown below however the script seems to run fine and output to the screen with the correct data, however it doesn't update the database on the server. I've checked permissions and ran a simple query static query which works: (mysqli_query($con,"INSERT INTO feeforeviews (FEEDBACKID,COUNT,DATE)

VALUES ('99999,10,3 Hour(s) ago')");) and it updates the "feeforeviews" table fine.
 
This is the script I would like working if possible which parses the file feefofeedtest.xml and should import the data in the database table "feeforeviews"
 
I modified the script from here:
 
 
Any help greatly appreciated.
 
<?php
// Create connection
$con=mysqli_connect("localhost","user","pass","database");
 
// Check connection
if (mysqli_connect_errno())
  {
  echo "Failed to connect to MySQL: " . mysqli_connect_error();
  }
?>
 
 
 <?php
$xml = simplexml_load_file('feefofeedtest.xml');
$data = $fields = array();
foreach ($xml->xpath('FEEDBACK') as $FEEDBACK) {
    $fields = array_keys((array)($FEEDBACK));
    $data[] = '(' . join(', ', (array)$FEEDBACK) . ')';
}
 
$sql = "INSERT INTO feeforeviews (" . join(', ', $fields) . ") VALUES\n" ;
$sql .= join (",\n", $data);
 
echo "<pre>$sql</pre>";
?>
 
This outputs the following onscreen which looks fine, however it doesn't update the server.
 
INSERT INTO feeforeviews (FEEDBACKID, COUNT, DATE, HREVIEWDATE, DESCRIPTION, PRODUCTCODE, LINK, FACEBOOKSHARELINK, PRODUCTRATING, SERVICERATING, CUSTOMERCOMMENT, SHORTCUSTOMERCOMMENT, READMOREURL) VALUES
(99998, 1, 3 Hour(s) ago, 2014-03-18T10:19:03, Personalised Swarovski Crystal Hiball Glass, DG10387, http://www.keepitpersonal.co.uk, http://www.facebook.com/sharer.php?u=http%3A%2F%2Fwww.feefo.com%2FGB%2Fen%2Freviews%2FKeep-It-Personal%2F%3Fid%3D326784%26servicefeedbackid%3D83637, 5, ++, ++, jgsjhgdfhjgjsd, Service rating : jgsjhgdfhjgjsd, http://www.feefo.com/GB/en/reviews/Keep-It-Personal/?id=326784&servicefeedbackid=83637),
(88888, 2, 5 Hour(s) ago, 2014-03-18T08:02:34, Personalised Swarovski Champagne Flute, DG10492, http://www.keepitpersonal.co.uk, http://www.facebook.com/sharer.php?u=http%3A%2F%2Fwww.feefo.com%2FGB%2Fen%2Freviews%2FKeep-It-Personal%2F%3Fid%3D326784%26servicefeedbackid%3D86279, NA, ++, Excellent website, easy to understand and use, jgsjhgdfhjgjsd, http://www.feefo.com/GB/en/reviews/Keep-It-Personal/?id=326784&servicefeedbackid=86279)
 
 
Example XML file:
 
<?xml version="1.0" encoding="UTF-8"?><FEEDBACKLIST>
    <FEEDBACK>
        <FEEDBACKID>99998</FEEDBACKID>
        <COUNT>1</COUNT>
        <DATE> 3 Hour(s) ago</DATE>
        <HREVIEWDATE>2014-03-18T10:19:03</HREVIEWDATE>
        <DESCRIPTION>Personalised Swarovski Crystal Hiball Glass</DESCRIPTION>
        <PRODUCTCODE>DG10387</PRODUCTCODE>
        <HREVIEWRATING>5</HREVIEWRATING>
        <PRODUCTRATING>++</PRODUCTRATING>
        <SERVICERATING>++</SERVICERATING>
        <CUSTOMERCOMMENT>jgsjhgdfhjgjsd</CUSTOMERCOMMENT>
        <SHORTCUSTOMERCOMMENT>Service rating : jgsjhgdfhjgjsd</SHORTCUSTOMERCOMMENT>
    </FEEDBACK>
    <FEEDBACK>
        <FEEDBACKID>88888</FEEDBACKID>
        <COUNT>2</COUNT>
        <DATE> 5 Hour(s) ago</DATE>
        <HREVIEWDATE>2014-03-18T08:02:34</HREVIEWDATE>
        <DESCRIPTION>Personalised Swarovski Champagne Flute</DESCRIPTION>
        <PRODUCTCODE>DG10492</PRODUCTCODE>
        <PRODUCTRATING>NA</PRODUCTRATING>
        <SERVICERATING>++</SERVICERATING>
        <CUSTOMERCOMMENT>Excellent website, easy to understand and use</CUSTOMERCOMMENT>
        <SHORTCUSTOMERCOMMENT>jgsjhgdfhjgjsd</SHORTCUSTOMERCOMMENT>
    </FEEDBACK></FEEDBACKLIST>

 

Link to comment
Share on other sites

I don't have the knowledge to construct the correct string :(, i've tried to find more examples online but this is what I've got but it's pulling up an error:

 

Parse error: syntax error, unexpected ';' 

 

mysqli_query($con,"INSERT INTO feeforeviews (" . join(', ', $fields) . ") VALUES\n" ;
mysqli_query($con,' .= join (",\n", $data);
 
Any ideas?
Link to comment
Share on other sites

I think I am getting further, the code (see below) is executing but it pulls up an error:

 

Error creating database: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'Hour(s) ago, 2014-03-18T10:19:03, Personalised Swarovski Crystal Hiball Glass, D' at line 2

 

$sql = "INSERT INTO feeforeviews (" . join(', ', $fields) . ") VALUES\n" ;

$sql .= join (",\n", $data);

if (mysqli_query($con,$sql))

  {

  echo "Database my_db created successfully";

  }

else

  {

  echo "Error creating database: " . mysqli_error($con);

  }

Link to comment
Share on other sites

String values in your query need to be enclosed in single quotes

EG

VALUES (..., '3 Hour(s) ago', '2014-03-18T10:19:03', 'Personalised Swarovski Crystal Hiball Glass', 'D', ... )

In the code you copied/pasted these quotes were already present in the XML data. They are not present in yours so you need to insert them when joining the values.

 

So this line

$data[] = '(' . join(', ', (array)$FEEDBACK) . ')';

needs to be

$data[] = "('" . join("', '", (array)$FEEDBACK) . "')";
Link to comment
Share on other sites

Thanks that's fixed this issue however I've stumbled across another issue now with ' apostrophes now.

 

The customer comments can include any characters and it looks like I will need to escape them before inserting into the DB.

 

The following link has an example which I think will fix the issue http://www.php.net/manual/en/mysqli.real-escape-string.php but I've tried to implement without success - I am so close now, any ideas? :)

 

$xml = simplexml_load_file('feefofeedtest.xml');
$data = $fields = array();
foreach ($xml->xpath('FEEDBACK') as $FEEDBACK) {
    $fields = array_keys((array)($FEEDBACK));
$data[] = "('" . join("', '", (array)$FEEDBACK) . "')";}
 
$sql = "INSERT IGNORE INTO feeforeviews (" . join(', ', $fields) . ") VALUES\n" ;
$sql .= join (",\n", $data);
if (mysqli_query($con,$sql))
  {
  echo "Database my_db created successfully";
  }
else
  {
  echo "Error creating database: " . mysqli_error($con);
  }
Link to comment
Share on other sites

something like this, still doesn't work though :)

 

$xml = simplexml_load_file('feefofeedtest.xml');
$data = $fields = array();
foreach ($xml->xpath('FEEDBACK') as $FEEDBACK) {
    $fields = array_keys((array)($FEEDBACK));
$data[] = "('" . join("', '", (array)$FEEDBACK) . "')", mysql_real_escape_string($CUSTOMERCOMMENT), mysql_real_escape_string($SHORTCUSTOMERCOMMENT);}
 
$sql = "INSERT IGNORE INTO feeforeviews (" . join(', ', $fields) . ") VALUES\n" ;
$sql .= join (",\n", $data);
if (mysqli_query($con,$sql))
  {
  echo "Database my_db created successfully";
  }
else
  {
  echo "Error creating database: " . mysqli_error($con);
  }
 
?>
Link to comment
Share on other sites

Mea culpa. Should be escaping the the data anyway.

 

Try this to escape each field

foreach ($xml->xpath('FEEDBACK') as $FEEDBACK) {
    $fields = array_keys((array)($FEEDBACK));
    $data[] = "('" . join("', '", array_map(array($con, real_escape_string), (array)$FEEDBACK)) . "')";
}
Link to comment
Share on other sites

Many thanks that's solved this problem, but i've just come across yet another issue...Column count doesn't match value count at row 1

 

The problem appears to be that the XML TREE doesn't contain the tags which are not populated. For example <FEEDBACKID>77787</FEEDBACKID> includes <HREVIEWRATING>5</HREVIEWRATING>, however  <FEEDBACKID>86279</FEEDBACKID> does not include this tag so I assume we get the error..doh.

 

 

 

<?xml version="1.0" encoding="UTF-8"?><FEEDBACKLIST>
    <FEEDBACK>
        <FEEDBACKID>77787</FEEDBACKID>
        <COUNT>1</COUNT>
        <DATE> 3 Hour(s) ago</DATE>
        <HREVIEWDATE>2014-03-18T10:19:03</HREVIEWDATE>
        <DESCRIPTION>Special character's</DESCRIPTION>
        <PRODUCTCODE>DG10387</PRODUCTCODE>
        <HREVIEWRATING>5</HREVIEWRATING>
        <PRODUCTRATING>++</PRODUCTRATING>
        <SERVICERATING>++</SERVICERATING>
        <CUSTOMERCOMMENT>jgsjhgdfhjgjsd'</CUSTOMERCOMMENT>
        <SHORTCUSTOMERCOMMENT>Service rating : jgsjhgdfhjgjsd</SHORTCUSTOMERCOMMENT>
    </FEEDBACK>
   <FEEDBACK>
        <FEEDBACKID>86279</FEEDBACKID>
        <COUNT>2</COUNT>
        <DATE> 5 Hour(s) ago</DATE>
        <HREVIEWDATE>2014-03-18T08:02:34</HREVIEWDATE>
        <DESCRIPTION>Personalised Swarovski Champagne Flute</DESCRIPTION>
        <PRODUCTCODE>DG10492</PRODUCTCODE>
        <PRODUCTRATING>NA</PRODUCTRATING>
        <SERVICERATING>++</SERVICERATING>
        <CUSTOMERCOMMENT>Excellent website, easy to understand and use</CUSTOMERCOMMENT>
        <SHORTCUSTOMERCOMMENT>Excellent website, easy to understand and use</SHORTCUSTOMERCOMMENT>
    </FEEDBACK>
    </FEEDBACKLIST>
Link to comment
Share on other sites

FEEDBACKID COUNT DATE HREVIEWDATE DESCRIPTION PRODUCTCODE LINK FACEBOOKSHARELINK HREVIEWRATING PRODUCTRATING SERVICERATING CUSTOMERCOMMENT SHORTCUSTOMERCOMMENT READMOREURL ITEM PRODUCTLATEST SERVICELATEST VENDORCOMMENT SHORTVENDORCOMMENT DATE2 VENDORCOMMENT3 CUSTOMERCOMMENT4 SERVICERATING5 PRODUCTRATING6

Link to comment
Share on other sites

From that list it appears your xml records only contain (different) subsets of the whole record. You may have to break the rules and do a separate insert for each record.

$xml = simplexml_load_file('feefofeedtest.xml');
$data = $fields = array();
foreach ($xml->xpath('FEEDBACK') as $FEEDBACK) {
    $fields = array_keys((array)($FEEDBACK));
    $data = "('" . join("', '", (array)$FEEDBACK) . "')";
    $sql = "INSERT IGNORE INTO feeforeviews (" . join(', ', $fields) . ") VALUES\n" ;
    $sql .= join (",\n", $data);
    if (!mysqli_query($con,$sql))
    {
        echo "Error creating database: " . mysqli_error($con);
    }
}
Link to comment
Share on other sites

Thanks for your reply Barand, their appears to be a syntax error somewhere by Values now by the looks of it...

 

Warning: join() [function.join]: Invalid arguments passed in /home/giftshop/public_html/responsive/feefo/testfeefo.php on line 20
Error creating database: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '' at line 1

---------------------------------------

 

Warning: join() [function.join]: Invalid arguments passed in /home/giftshop/public_html/responsive/feefo/testfeefo.php on line 20
INSERT IGNORE INTO feeforeviews (FEEDBACKID, COUNT, DATE, HREVIEWDATE, DESCRIPTION, PRODUCTCODE, LINK, FACEBOOKSHARELINK, PRODUCTRATING, SERVICERATING, CUSTOMERCOMMENT, SHORTCUSTOMERCOMMENT, READMOREURL) VALUES

Link to comment
Share on other sites

  • Solution

try

$xml = simplexml_load_file('feefofeedtest.xml');
$data = $fields = array();
foreach ($xml->xpath('FEEDBACK') as $FEEDBACK) {
    $fields = array_keys((array)($FEEDBACK));
    $data = join("', '", array_map(array($con, real_escape_string), (array)$FEEDBACK));
    $sql = "INSERT IGNORE INTO feeforeviews (" . join(', ', $fields) . ") VALUES ('$data')" ;
    if (!mysqli_query($con,$sql))
    {
        echo "Error creating database: " . mysqli_error($con);
    }
}

 

Link to comment
Share on other sites

This thread is more than a year old. Please don't revive it unless you have something important to add.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.