0

我在我们的 wordpress 网站上使用了一个 xml 文件,每次有人查看帖子时都会使用帖子 ID 进行更新。

文件结构是这样的……</p>

  <?xml version="1.0"?>
  <posts>
     <refresh>
        <datetime>2013-01-04 08:48:21</datetime>
     </refresh>
     <post id="21931">
        <postviews>5</postviews>
     </post>
     <post id="25420">
        <postviews>18</postviews>
     </post>
     <post id="17770">
        <postviews>25</postviews>
     </post>
     <post id="24925">
        <postviews>4</postviews>
     </post>
  </posts>

每次有人查看帖子时,如果帖子 ID 不在文件中,它会添加一个新节点,或者如果它存在,则会将当前值更新 1。

我遇到的问题是,有时文件没有被正确写入,最终被损坏并如下所示(错误总是在文件的底部)......</p>

  <?xml version="1.0"?>
  <posts>
     <refresh>
        <datetime>2013-01-04 08:48:21</datetime>
     </refresh>
     <post id="21931">
        <postviews>5</postviews>
     </post>
     <post id="25420">
        <postviews>18</postviews>
     </post>
     <post id="17770">
        <postviews>25</postviews>
     </post>
   </posts>         
   id="24925">
        <postviews>4</postviews>
     </post>
  </posts>

我已经和我们的托管公司谈过了,问题没有显示为服务器错误。写入 XML 文件的脚本可能有问题吗?我写的脚本如下……</p>

<?php

 // echo get_the_ID();

if($post->post_status != "publish" || is_user_logged_in()) { 

    //Get the wordpress postID
$postID = get_the_ID();

$postData = get_post($postID);  

// Don't do anything if the post isn't published or being viewed by logged in users - will give a false impression
// echo $postID.'<br />'.$postData->post_title.'<br />'.$postData->post_date_gmt.'<br />';

} else { 

//Get the wordpress postID
$postID = get_the_ID();

$postData = get_post($postID);  

// echo $postID.'<br />'.$postData->post_title.'<br />'.$postData->post_date_gmt.'<br />';

$xmlFile = get_stylesheet_directory().'/most-read/most-read-posts.xml';

// load the document
$xml = simplexml_load_file($xmlFile);


// Get the server time
$serverTime = date('Y-m-d H:i:s');

// Is their a refresh node with an entry of datetime?
$refreshNodeExists = $xml->xpath("//refresh");

// Count it if 
$countrefreshNodeExists = count($refreshNodeExists);

// If it does exists
if($countrefreshNodeExists != 0) { // If the ID is already in the file

    $xmlRefresh = $xml->refresh->datetime;

    // echo 'Refresh time is already set<br /><br />';

} else {

    // echo 'Refresh time is not set<br /><br />';

    $refreshNode = $xml->addChild('refresh');

    $refreshNode->addChild('datetime', $serverTime);

}

// Check the time elapsed between the server time and the refreshNode

// Get and format the refreshNode
$to_time = strtotime($xmlRefresh);

// Get and format the server time
$from_time = strtotime($serverTime);

// Calculate the time elapsed
$refreshTimeElapsed = round(abs($to_time - $from_time) / 60,2);

// How long do we want to have between file refreshing - in minutes?
$refreshInterval = 120;

// Check if the time elapsed is more or less than $refreshInterval
if ($refreshTimeElapsed > $refreshInterval) {

    // FOR TESTING ONLY - Show the time elapsed
    // echo 'Ooops were over the refresh limit. It\'s currently at: '.$refreshTimeElapsed.' minutes.<br /><br />';

    $fh = fopen($xmlFile, 'w') or die("can't open file");

    $stringData = '<?xml version="1.0"?><posts><refresh><datetime>'.date('Y-m-d H:i:s').'</datetime></refresh></posts>';

    fwrite($fh, $stringData);

    fclose($fh);

                /*$test = $xml->xpath("//post");

                if (!empty($test)) {

                    echo 'Houston, we have posts';

                } else {

                    echo 'That\'s a negative Houston, we have no posts here';

                }*/

    // Reset the datetime node with the current datetime to start the refresh loop again.
    $xml->refresh->datetime = date('Y-m-d H:i:s');

} else { // Don't need to do anything here really

    // FOR TESTING ONLY - show how much time has elapsed
    // echo 'No need to change the refresh node. It\'s only at '.$refreshTimeElapsed.' minutes.<br /><br />';

    // Check to see if the post id is already in the xml file - has it already been set?
    $nodeExists = $xml->xpath("//post[@id=".$postID."]");

    //Count the results
    $countNodeExists = count($nodeExists);

    if($countNodeExists > 0) { // If the ID is already in the file

        // echo 'ID already here';

        // get the correct node
        $result = $xml->xpath("//post[@id=".$postID."]/postviews");

        // heres the trick - the first result of xpath, and the node value (stored in [0])
        $result[0][0] = $result[0][0]+1;

    } else { // If the ID isn;'t there, add a new entry in the xml file for the post

        //echo 'ID added';

        $postNode = $xml->addChild('post'); // adding a new <post> to the top level node
        $postNode->addAttribute('id', $postID); // adding a <postid> inside the new <post>
        $postNode->addChild('postviews', 1); // adding a postviews inside the new <post>
    }

    // save the updated document and format it using the DOMDocument class

    //$xml->asXML($xmlFile);
    $dom = new DOMDocument('1.0');
    $dom->preserveWhiteSpace = false;
    $dom->formatOutput = true;
    $dom->loadXML($xml->asXML());
    $dom->save($xmlFile);

} // End if ($refreshTimeElapsed > $refreshInterval) {

} // End if logged in or not published

?>
4

1 回答 1

0

每次有人查看帖子时,如果帖子 ID 不在文件中,它会添加一个新节点,或者如果它存在,则会将当前值更新 1。

我敢打赌这是由多个同时处决引起的。您是否锁定了对该文件的访问权限?如果两个人同时查看一个帖子会发生什么?

我认为(长期)您最好将此信息存储在数据库或类似数据库中。我认为写入通用 XML 文件不会扩展。

于 2013-01-04T10:16:50.607 回答