DBIx-TxnPool

 view release on metacpan or  search on metacpan

lib/DBIx/TxnPool.pm  view on Meta::CPAN

deadlock occurs a pool repeats your callbacks for every item again. You can
define a second callback which will be executed for every item after wrapped
transaction. For example there can be non-SQL statements, for example a deleting
files, cleanups and etc.

=head1 CONSTRUCTOR

Please to see L</SYNOPSIS> section

=head2 Shortcuts:

The C<txn_item> should be first. Other sortcuts can follow in any order.
Parameters should be the last.

=over

=item txn_item B<(Required)>

The transaction item callback. There should be SQL statements and code should be safe for repeating (when a deadlock
occurs). The C<$_> consists a current item. You can modify it if one is hashref for example. Passing arguments will be
I<DBIx::TxnPool> object and I<current item> respectively. B<Please don't catch exceptions here (by try{} or eval{} for
example)> - by this way deadlocks are defined outside under the hood!

=item txn_sort B<(Optional)>

Here you can define sort function for your data before a transaction will be
made. If you have only one type SQL statement in L<txn_item|/"txn_item
(Required)"> but you didn't sort keys before transaction you can have deadlocks
(they will be resolved and transaction will be repeated but you will lose a
processing time) unless you define this function. This method minimize deadlock
events!

=item txn_post_item B<(Optional)>

The post transaction item callback. This code will be executed once for each item (defined in C<$_>). It is located
outside of the transaction. And it will be called if whole transaction was successful. Passing arguments are
I<DBIx::TxnPool> object and I<current item> respectively. You can do here your own error handling in callback. If your
code here will throw an excetption it will be propagated above.

=item txn_commit B<(Optional)>

This callback will be called after each SQL commit statement. Here you can put
code for logging for example. The first argument is I<DBIx::TxnPool> object

=back

=head2 Parameters:

=over

=item dbh B<(Required)>

The dbh to be needed for begin_work & commit method (wrap in a transaction).

=item size B<(Optional)>

The size of pool when a commit method will be called when feeding reaches the same size.

=item block_signals B<(Optional)>

An arrayref of signals (strings) which should be blocked in slippery places for
this I<pool>. Defaults are [ qw( TERM INT ) ]. You can change globaly this list
by setting: C<< $DBIx::TxnPool::BlockSignals = [ qw( TERM INT ALARM ... ) ] >>.
For details to see here L</"SIGNAL HANDLING">

=item max_repeated_deadlocks B<(Optional)>

The limit of consecutive deadlocks. The default is 5. After limit to be reached
the L</add> throws exception.

=back

=head1 METHODS

=over

=item add

You can add item of data to the pool. This method makes a wrap to transaction.
It can finish transaction if pool reaches up to size or can repeat a whole
transaction again if deadlock exception was thrown. The size of transaction may
be less than your defined size!

=item dbh

The accessor of C<dbh>. It's readonly.

=item finish

It makes a final transaction if pool is not empty.

=item amount_deadlocks

The amount of deadlocks (repeated transactions)

=back

=head1 SIGNAL HANDLING

In DBD::mysql and may be in other DB drivers there is a some bad behavior the
bug as i think. If a some signal will arrive (TERM, INT and other) in your
program during a some SQL socket work this driver throws an exception like
"MySQL lost connection". It happens because the C<recv> or C<read> system calls
into MySQL driver return with error code C<EINTR> if signal arrives inside this
system call. A right written software should recall a system call again because
the C<EINTR> is not fatal error. But i think MySQL driver decides this error as
I<lost connection error>. I<"Deferred Signals"> (or L<Safe
Signals|perlipc/"Deferred Signals (Safe Signals)">) of perl don't help because
the MySQL driver uses direct system calls.

Workaround is to use L<Signal::Mask> module for example and to block these
signals (TERM / INT) during working with DBI subroutines. The version 0.09 of
C<DBIx::TxnPool> has helpers for this. The C<DBIx::TxnPool> wraps all slippery
places by blocking your preferred signals (defaults are C<TERM> & C<INT> ones)
before entering and by unblocking after (for example the callback handler
L<txn_item|/"txn_item (Required)"> and transaction code). This should minimize
raised errors like the "MySQL lost connection".

=head1 AUTHOR

This module has been written by Perlover <perlover@perlover.com>



( run in 0.881 second using v1.01-cache-2.11-cpan-0bb4e1dffa6 )