2010-03-11 11 views
8

Sto passando attraverso this tutorial su PDO e sono arrivato al punto sulle transazioni. Saltare le parti di connessione, ho questo codice php:PDO: le transazioni non vengono ripristinate?

try 
{ 
    $db->beginTransaction(); 

    $db->exec('DROP TABLE IF EXISTS animals'); 

    $db->exec('CREATE TABLE animals (' 
     .'animal_id MEDIUMINT(8) NOT NULL AUTO_INCREMENT PRIMARY KEY,' 
     .'animal_type VARCHAR(25) NOT NULL,' 
     .'animal_name VARCHAR(25) NOT NULL)' 
     .'ENGINE=INNODB'); 

    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("emu", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("funnel web", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("lizard", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("dingo", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("kangaroo", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("wallaby", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("wombat", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("koala", "bruce")'); 
    $db->exec('INSERT INTO animals (animal_type, animal_name) VALUES ("kiwi", "bruce")'); 

    $db->commit(); 

    echo 'Table re-created and data entered successfully.'; 
} 
catch(PDOException $e) 
{ 
    $db->rollback(); 

    echo $e->getMessage(); 
} 

Funziona alla grande e, come ho pensato che sarebbe, a meno che ho messo in un errore da qualche parte. Come se avessi creato un errore nella quarta frase di inserimento, avrei trovato tre animali nel mio database. Ma pensavo che le cose dovessero essere ripristinate, nel senso che avrei trovato il database come lo era prima di eseguire questo script.

Ho frainteso qualcosa? Cosa mi manca? Le funzioni di transazione e di rollback fanno qualcosa di diverso da quello che penso che dovrebbero fare? Il rilascio e la creazione di dichiarazioni "rompono" la transazione in qualche modo? Cosa sta succedendo qui?


Aggiornamento: Se sposto la linea $db->beginTransaction(); modo la transazione inizia solo dopo che la tabella è stata creata, ottengo il comportamento che mi aspettavo. Quindi, se la terza istruzione di inserimento falliva, avrei una tabella vuota (poiché è stata appena ricreata) dopo il rollback della transazione. Ancora chiedendo perché non funziona quando la caduta e creare affermazioni sono nella transazione anche se ...

risposta

18

consultare il manuale di riferimento di PHP: PDO::beginTransaction

Alcune basi di dati, tra cui MySQL, emettere automaticamente un implicito COMMIT quando un'istruzione DDL (database definition language) come DROP TABLE o CREATE TABLE viene emessa all'interno di una transazione. Il COMMIT implicito ti impedirà di annullare eventuali altre modifiche all'interno del limite della transazione.

Questo spiega perché questo accade, ed è una limitazione di MySQL, non di PDO/PHP.

+0

Ahaaa. Ciò ha senso! Grazie :) – Svish

2

assicurarsi che tutte le tabelle supportino le transazioni. ad esempio MyISAM non supporta.

+2

che è più un commento che una risposta. – hakre

Problemi correlati