2009-05-08 18 views
14

PDO ayrıntılarına girmeye çalışıyorum. Bu yüzden bu kodlanmış:PDO Filtrelenmemiş sorgular

$cn = getConnection(); 

// get table sequence 
$comando = "call p_generate_seq('bitacora')"; 
$id = getValue($cn, $comando); 

//$comando = 'INSERT INTO dsa_bitacora (id, estado, fch_creacion) VALUES (?, ?, ?)'; 
$comando = 'INSERT INTO dsa_bitacora (id, estado, fch_creacion) VALUES (:id, :estado, :fch_creacion)'; 
$parametros = array (
    ':id'=> (int)$id, 
    ':estado'=>1, 
    ':fch_creacion'=>date('Y-m-d H:i:s') 
); 
execWithParameters($cn, $comando, $parametros); 

benim getValue fonksiyonu çalışıyor ve ben tablo için bir sonraki dizisi olsun. Ben execWithParameters içine almak zaman, ben bu istisna olsun:

PDOException: 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. in D:\Servidor\xampp_1_7_1\htdocs\bitacora\func_db.php on line 77

Ben bağlantı özelliklerini değiştirmeye çalıştı ama çalışmıyor.

Bunlar benim çekirdek db işlevleri şunlardır: Bunun için bir ışık tutabilir

function getConnection() { 
    try { 
     $cn = new PDO("mysql:host=$host;dbname=$bd", $usuario, $clave, array(
       PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, 
      )); 

     $cn->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, true); 
     return $cn; 
    } catch (PDOException $e) { 
     print "Error!: " . $e->getMessage() . "<br/>"; 
     die(); 
    } 
} 
function getValue($cn, $comando) { 
    $resul = $cn->query($comando); 
     if (!$resul) return null; 
     while($res = $resul->fetch()) { 
      $retorno = $res[0][0]; 
      break; 
     } 
     return $retorno; 
} 
function execWithParameters($cn, $comando, $parametros) { 
    $q = $cn->prepare($comando); 
    $q->execute($parametros); 
    if ($q->errorInfo() != null) { 
     $e = $q->errorInfo(); 
     echo $e[0].':'.$e[1].':'.$e[2]; 
    } 
} 

biri mi? PD. Lütfen otonomik kimlik yapmamanızı önermeyin, çünkü başka bir sistemden çıkıyorum.

+0

p_generate_seq nedir? SHOW PROSEDÜRÜ p_generate_seq – VolkerK

+0

sorun, orada yok, aynı hata SELECT MAX (id) FROM dsa_bitacora –

cevap

21

Sorun, mysql'in belirli bir zamanda yalnızca bir seçkin imlecine izin vermesidir. Fetch() yöntemini kullanarak ve bekleyen tüm verileri tüketmemeniz durumunda, bir imleci açık bırakıyorsunuz demektir.

Önerilen yaklaşım, fetchAll() yöntemini kullanarak tüm verileri tüketmektir. Bir alternatif closeCursor() yöntemini kullanmaktır.

Eğer bu işlevi değiştirirseniz

, sana daha mutlu olacağını düşünüyorum: Eğer XAMPP 1.7.1 kullanıyorsanız

<?php 
function getValue($cn, $comando) { 
    $resul = $cn->query($comando); 
    if (!$resul) return null; 
    foreach ($resul->fetchAll() as $res) { 
      $retorno = $res[0]; 
      break; 
    } 
    return $retorno; 
} 
?> 
+0

Yukarıdaki gibi bağlantı işlevlerini biliyorum ama aynı sorunu yaşıyorum. FetchALL() yöntemi makinemde düzgün çalışmıyor gibi görünüyor. Cevabınızdan beri herhangi bir tavsiye veya alternatif var mı? – JM4

8

Sorun şu ki, PDO'yu çok tanıyamıyorum --- getValue çağrınız döndükten sonra, sorgu hala bağlantıya bağlı (Yalnızca ilk değer için soruyorsunuz, henüz bağlantı birkaç döndürür veya bunu yapmak için bekliyor).

Belki getValue dönmeden önce

$resul->closeCursor(); 

eklenerek düzeltilebilir.

Aksi takdirde, getValue sorguları her zaman bir (veya yeterli sayıda) değeri döndürürse, fetchAll kullanımı tercih edilir.

+0

tx ile olur ... Ben sadece closeCursor ve fetchAll denedim ve aynı özel durum yükselterek tutar. –

0

Benim bir arkadaşım xampp 1.7.1 build ile aynı sorunu vardı. Xampp/php/* 'i 5.2.9-2 php.net ile değiştirdikten ve gerekli tüm dosyaları xampp/apache/bin dizinine kopyaladıktan sonra iyi çalıştı.

0

, sadece 1.7.2 sürümüne geçmeniz gerekmektedir. Eğer (yani bir UPDATE, INSERT, vs) verileri döndüren bir sorgu işin yoksa

16

Ben PDOStatement :: closeCursor() çalışacak sanmıyorum.

Daha iyi bir çözüm PDOStatement ::) (yürütmek çağrıldıktan sonra basitçe unset() PDOStatement nesnesi şudur: en az 5 farklı Stackoverflow

$stmt = $pdo->prepare('UPDATE users SET active = 1'); 
$stmt->execute(); 
unset($stmt); 
+0

bunu kontrol etmeli, teşekkürler –

+0

Aynı problemi bir php özyinelemeli fonksiyonda da vardı. Bu cevap problemi için teşekkürler, şöyle çözüldü: $ satır = $ sth-> fetchAll (PDO :: FETCH_ASSOC); \t \t \t unset ($ sth); \t \t \t foreach ($ satır olarak $ satır). Önceden sahip olduğum şey: while ($ row = $ sth-> Getir (PDO :: FETCH_ASSOC)). Teşekkür ederim! – Alqin

2

Ben sadece tüm internet etrafında Googling 15 dakika harcamak ve görüntülenen sorularım, benim hatamın yanlış PHP versiyonundan, MySQL kütüphanesinin yanlış sürümünden veya başka bir sihirli siyah kutudan oluştuğu iddia edilen sorular ...

Tüm kodumu "fetchAll" kullanarak değiştirdim ve hatta aradım closeCursor() ve her bir sorgu sonra sorgu nesnesinde() sertleşmemiş. Dürüstçe umutsuz başlamıştı! Ayrıca MYSQL_ATTR_USE_BUFFERED_QUERY bayrağı denedim ama işe yaramadı.

FINALLY Pencereden her şeyi attım ve PHP hatasını inceledim ve olduğu yerde kod satırını izledim. Benim original_bytes ve new_bytes hem imzasız bigints ve bu hiç bir işi olsaydı original_bytes daha doğrusu BÜYÜK new_bytes nerede, o nerede olurdu anlamına geliyordu çünkü

SELECT AVG((original_bytes-new_bytes)/original_bytes) as saving 
    FROM (SELECT original_bytes, new_bytes FROM jobs ORDER BY id DESC LIMIT 100) AS t1 

Neyse, sorun oldu Kötü bir MySQL "aralık dışı" hatası. Ve bu, küçük bir süre için benim minification servisimi çalıştırdıktan sonra rastgele oldu.

Neden sadece bu basit hata vermek yerine bu garip MySQL hatası aldım, benden öte! Ham sorguyu çalıştırdığımda aslında SQLBuddy'de (hafif PHPMyAdmin) ortaya çıktı. PDO istisnalarım vardı, bu yüzden bana MySQL hatası vermiş olmalı.

Aldırma, alt satır: Hiç bu hatayı alırsanız

, ham MySQL aslında doğru ve HALA çalışma olup olmadığını kontrol edin !!!

+1

Sadece bu şifreli ve işe yaramaz hata ile karşı karşıya geldi ve bu cevap sayesinde bir an için kutunun dışında düşündüm. Sorguyu hata ayıklamak için önemli olduğunu kanıtladığı aynı bağlantıda "GÖSTERİ GÖSTER". Benim durumumda, hata: Bilinmeyen veya yanlış saat dilimi: PDO örneğini oluştururken tanımladığım 'Avrupa/Londra'. Teşekkürler @Henrik. –