2012-09-25 54 views
6

我在使用PHP5.4和MySql使用PDO时遇到异常。PHP5 MySql和PDO异常

我已阅读几乎所有其他帖子,博客,手册,代码段,我可以与此错误有关的所有内容,并尝试了所有我没有看到过的内容。

所以我希望它是特定于我在特定代码中做错的事情,您可以将它指出给我。

以下是错误:

SQLSTATE[HY000]: General error: 2014 Cannot execute queries while other unbuffered queries are active. Consider using PDOStatement::fetchAll(). Alternatively, if your code is only ever going to run against mysql, you may enable query buffering by setting the PDO::MYSQL_ATTR_USE_BUFFERED_QUERY attribute.

这里是代码,导致这种错误的部分:

第一部分:

 $stmt = $this->dbConn->prepare("CALL getPopularProducts()"); 
     $stmt->execute(); 
     $rows = $stmt->fetchAll(\PDO::FETCH_ASSOC); 

     //$stmt->closeCursor(); 

     foreach ($rows as $row) { 
      $p = new entity\LightingPole(); 
      /* doing basic set stuff here so code omitted */ 

      // apply category to product 
      $categroyTranslator = new ProductCategoryTranslator(); 
      $categroyTranslator->applyProductCategory($p); 

第二部分:

 public function applyProductCategory(entity\Product $product) { 
      $productId = $product->getProductId(); 
      try { 
       /** exception thrown on this line **/ 
       $stmt = $this->dbConn->prepare("CALL getCategoryByProductId(?)"); 

       $stmt->bindParam(1, $productId, \PDO::PARAM_INT); 
       $stmt->execute(); 

       while ($row = $stmt->fetch(\PDO::FETCH_ASSOC)){ 
        $category = new entity\ProductCategory(); 

        $product->setCategory($category); 
       } 
      } 
      catch (\PDOException $e) { 
       echo $e->getMessage(); 
       print($e->getTraceAsString()); 
      } 
     } 

这里是我的数据库类:

namespace lib\database; 

class Database 
{ 
    protected static $instance; 

    public static function getInstance() 
    { 
     if(self::$instance == null) 
     { 
      $dsn = "mydsn"; 
      $user = "myuser"; 
      $password = "mypassword"; 
      self::$instance->setAttribute(\PDO::ATTR_EMULATE_PREPARES, false); 
      self::$instance->setAttribute(\PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, true); 
      self::$instance->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION); 
     } 
     return self::$instance; 
    } 

    private function __construct() {} 

    private function __clone() {} 
} 

您可能会注意到我不得不$stmt->closeCursor()一个电话,我已经注释掉。当我加入这一行的代码,我得到以下错误:

SQLSTATE[HY000]: General error: 2006 MySQL server has gone away

我们解释它以纯功能方面,有什么我基本上这里做的是越来越受欢迎的产品清单,通过他们循环和让所有的相关的产品数据,如产品类别等...

所以这个错误,发生在第一个产品在循环中,即第二次我呼吁applyProductCategory()它工作正常,没有问题。另一件事是,applyProductCategory下面大约有4个调用来检索其他类型的关联数据,并且在做这件事时从来没有发生任何错误。

所以最后,我所有的热门产品都很好,除非第一个产品从来没有与其关联的ProductCategory。

期待找到我错过的方式来造成这种情况。希望你能指出我正确的方向。

+0

你为什么要逃避'PDO'? – Erik

+1

@Erik,我不是逃避PDO我使用PHP命名空间和斜杠是必需的,所以PHP不会在我的班级寻找PDO。 – samazi

+0

酷!你每天都会学到新的东西:) – Erik

回答

2

使用未设置($语句)之前的权利试图在那里它抛出错误

unset($stmt); 
    $stmt = $this->dbConn->prepare("CALL getCategoryByProductId(?)"); 

我碰到了同样的错误之前和固定它的一些原因。我之前在这里找到答案PDO Unbuffered queries

+0

非常感谢你的工作,就像一个魅力。 – samazi

+0

只需要注意,我将$ unset($ stmt)直接放在$ rows = fetchAll()之后,因为错误是在一个单独的类中抛出的,所以$ stmt在这个新的范围内。 – samazi

+0

Gotcha。这就说得通了。很高兴它的工作。 – FajitaNachos