X-Git-Url: http://git.freeside.biz/gitweb/?a=blobdiff_plain;f=FS%2FFS%2FCursor.pm;h=d94151fed0b58e59870ec3432b410cf351bbcdf4;hb=2a5840941e01e1d6b83ad5f9e1039eb844dc5071;hp=f59d8cbb0d4e7c53f72d4c107f69176d466d8d27;hpb=2087a0f972b1ef1cb918d2c2316577e533ffd3f1;p=freeside.git diff --git a/FS/FS/Cursor.pm b/FS/FS/Cursor.pm index f59d8cbb0..d94151fed 100644 --- a/FS/FS/Cursor.pm +++ b/FS/FS/Cursor.pm @@ -2,12 +2,12 @@ package FS::Cursor; use strict; use vars qw($DEBUG $buffer); -use base qw( Exporter ); -use FS::Record qw(qsearch dbdef dbh); -use Data::Dumper; +use FS::Record; +use FS::UID qw(myconnect); use Scalar::Util qw(refaddr); -$DEBUG = 0; +$DEBUG = 2; + # this might become a parameter at some point, but right now, you can # "local $FS::Cursor::buffer = X;" $buffer = 200; @@ -39,21 +39,25 @@ and returns an FS::Cursor object to fetch the rows one at a time. sub new { my $class = shift; my $q = FS::Record::_query(@_); # builds the statement and parameter list + my $dbh = myconnect(); my $self = { query => $q, class => 'FS::' . ($q->{table} || 'Record'), buffer => [], + dbh => $dbh, }; bless $self, $class; # the class of record object to return $self->{class} = "FS::".($q->{table} || 'Record'); + # save for later, so forked children will not destroy me when they exit + $self->{pid} = $$; + $self->{id} = sprintf('cursor%08x', refaddr($self)); my $statement = "DECLARE ".$self->{id}." CURSOR FOR ".$q->{statement}; - my $dbh = dbh; my $sth = $dbh->prepare($statement) or die $dbh->errstr; my $bind = 1; @@ -103,9 +107,12 @@ sub refill { sub DESTROY { my $self = shift; - my $statement = "CLOSE ".$self->{id}; - dbh->do($statement); -} + return unless $self->{pid} eq $$; + $self->{dbh}->do('CLOSE '. $self->{id}) + or die $self->{dbh}->errstr; # clean-up the cursor in Pg + $self->{dbh}->rollback; + $self->{dbh}->disconnect; +} =back @@ -117,6 +124,12 @@ Replace all uses of qsearch with this. Doesn't support MySQL. +The cursor will close prematurely if any code issues a rollback/commit. If +you need protection against this use qsearch or fork and get a new dbh +handle. +Normally this issue will represent itself this message. +ERROR: cursor "cursorXXXXXXX" does not exist. + =head1 SEE ALSO L