{ # This code implement the transactionalize { ... } using ( dbh ); my (@dbh_AO,$dbh_HRef,$error_E); sub transactionalize(&;$) { my ($body_CRef,$dbh_CRef)=@_; eval { ### Setting dbh_O ... push(@dbh_AO,(defined $dbh_CRef) ? $dbh_CRef->() : $Defaultdbh_O); local $dbh_AO[-1]->{RaiseError}=1; warn "@dbh_AO "; ### BEGIN TRANSACTION ... unless (exists $dbh_HRef->{$dbh_AO[-1]}) { $dbh_AO[-1]->begin_work; $dbh_HRef->{$dbh_AO[-1]}=$dbh_AO[-1]; }; ### Do the stuff here ... $body_CRef->(); ### COMMIT TRANSACTION ... if (@dbh_AO == 1) { for my $dbh_s (keys %$dbh_HRef) { ### $dbh_s $dbh_HRef->{$dbh_s}->commit(); }; }; pop(@dbh_AO); }; if ($@) { $error_E||=$@; ### ROLLBACK TRANSACTION ... if (@dbh_AO == 1) { for my $dbh_s (keys %$dbh_HRef) { ### $dbh_s eval { $dbh_HRef->{$dbh_s}->rollback(); }; }; }; pop(@dbh_AO); Carp::confess $error_E; }; } # transactionalize {}: sub using($) { my $dbh_O=shift; ### : $dbh_O return sub { return $dbh_O; }; }; };