Author: timbo
Date: Mon Jun 16 08:00:32 2008
New Revision: 11426
Modified:
dbi/trunk/lib/DBD/Gofer/Transport/Base.pm
Log:
Improve retry-on-error logic.
Include checking the executed flag.
Append note with retry count to errstr if too many retries.
Modified: dbi/trunk/lib/DBD/Gofer/Transport/Base.pm
==============================================================================
--- dbi/trunk/lib/DBD/Gofer/Transport/Base.pm (original)
+++ dbi/trunk/lib/DBD/Gofer/Transport/Base.pm Mon Jun 16 08:00:32 2008
@@ -173,26 +173,26 @@
sub response_retry_preference {
my ($self, $request, $response) = @_;
- my $retry;
-
# give the user a chance to express a preference (or undef for default)
if (my $go_retry_hook = $self->go_retry_hook) {
- $retry = $go_retry_hook->($request, $response, $self);
- $self->trace_msg(sprintf "response_needs_retransmit: go_retry_hook
returned %s\n",
+ my $retry = $go_retry_hook->($request, $response, $self);
+ $self->trace_msg(sprintf "go_retry_hook returned %s\n",
(defined $retry) ? $retry : 'undef');
+ return $retry if defined $retry;
}
- if (not defined $retry) {
- my $errstr = $response->errstr || '';
- $retry = 1 if $errstr =~ m/induced by DBI_GOFER_RANDOM/;
- }
+ # This is the main decision point. We don't retry requests that got as far
+ # as executing because the error is probably from the database (not
+ # transport) so retrying is unlikely to help. But note that any severe
+ # transport error occuring after execute is likely to return a new
+ # response object that doesn't have the execute flag set. Beware!
+ return 0 if $response->executed_flag_set;
- if (not defined $retry) {
- my $idempotent = $request->is_idempotent; # i.e. is SELECT or ReadOnly
was set
- $retry = 1 if $idempotent;
- }
+ return 1 if ($response->errstr || '') =~ m/induced by DBI_GOFER_RANDOM/;
+
+ return 1 if $request->is_idempotent; # i.e. is SELECT or ReadOnly was set
- return $retry;
+ return undef; # we couldn't make up our mind
}
@@ -219,7 +219,10 @@
my $request_meta = $request->meta;
if (($request_meta->{retry_count}||=0) >= $retry_limit) {
- $self->trace_msg("response_needs_retransmit:
$request_meta->{retry_count} is too many retries\n");
+ my $retry_count = $request_meta->{retry_count};
+ $self->trace_msg("response_needs_retransmit: $retry_count is too many
retries\n");
+ # XXX should be possible to disable altering the err
+ $response->errstr(sprintf "%s (after %d retries by gofer)",
$response->errstr, $retry_count);
return 0;
}
++$request_meta->{retry_count}; # count for this request