DBI does not define what happens wrt transactions when disconnect is called.
Up to DBD::ODBC 1.29, DBD::ODBC always called SQLEndTran(SQL_ROLLBACK) to roll
back any outstanding transactions (if AutoCommit was off) before calling
SQLDisconnect. This means the outstanding transaction that is rolled back is
hidden and that there is a difference between:
my $h = DBI->connect("dbi:ODBC:test","test","test", {AutoCommit => 0,
RaiseError=>1, PrintWarn => 1});
$h->do(q/insert into mje values(?, ?)/, undef, 1, "fred");
# disconnect not called
and
my $h = DBI->connect("dbi:ODBC:test","test","test", {AutoCommit => 0,
RaiseError=>1, PrintWarn => 1});
$h->do(q/insert into mje values(?, ?)/, undef, 1, "fred");
$h->disconnect or die $DBI::errstr;
because in the first case DBI catches the possible outstanding txn in DESTROY
and issues:
Issuing rollback() due to DESTROY without explicit disconnect() of
DBD::ODBC::db handle test.
but in the second case DBD::ODBC will rollback the transaction before
disconnecting and there is no error or warning.
I don't really like this behaviour and would like to change it so in the second
case above, DBD::ODBC issues a warning before rolling the txn back so you'd get
something like:
DBD::ODBC::db disconnect warning: Disconnect with transaction in progress -
rolling back
Obviously if you have PrintWarn turned off or are not using warnings it won't
make any difference to you. Anyone have any fundamental objections to this
change.
Martin
--
Martin J. Evans
Easysoft Limited
http://www.easysoft.com