Methods update/delete on resultset use now new as_query method to updated/delete...
[dbsrgits/DBIx-Class.git] / lib / DBIx / Class / Storage / DBI / Cursor.pm
CommitLineData
5cf243f6 1package DBIx::Class::Storage::DBI::Cursor;
28927b50 2
3use base qw/DBIx::Class::Cursor/;
4
5use strict;
6use warnings;
7
5cf243f6 8=head1 NAME
9
10DBIx::Class::Storage::DBI::Cursor - Object representing a query cursor on a
11resultset.
12
13=head1 SYNOPSIS
14
15 my $cursor = $schema->resultset('CD')->cursor();
16 my $first_cd = $cursor->next;
17
18=head1 DESCRIPTION
19
20A Cursor represents a query cursor on a L<DBIx::Class::ResultSet> object. It
21allows for traversing the result set with L</next>, retrieving all results with
22L</all> and resetting the cursor with L</reset>.
23
24Usually, you would use the cursor methods built into L<DBIx::Class::ResultSet>
25to traverse it. See L<DBIx::Class::ResultSet/next>,
26L<DBIx::Class::ResultSet/reset> and L<DBIx::Class::ResultSet/all> for more
27information.
28
29=head1 METHODS
30
31=head2 new
32
5cf243f6 33Returns a new L<DBIx::Class::Storage::DBI::Cursor> object.
34
35=cut
36
28927b50 37sub new {
cb5f2eea 38 my ($class, $storage, $args, $attrs) = @_;
28927b50 39 #use Data::Dumper; warn Dumper(@_);
cb5f2eea 40 $class = ref $class if ref $class;
28927b50 41 my $new = {
cb5f2eea 42 storage => $storage,
28927b50 43 args => $args,
44 pos => 0,
1346e22d 45 attrs => $attrs,
dbaee748 46 _dbh_gen => $storage->{_dbh_gen},
1346e22d 47 };
48
cb5f2eea 49 return bless ($new, $class);
28927b50 50}
51
59af6677 52=head2 as_query
53
658fa250 54=over 4
55
0f6fc705 56=item Arguments: See L<DBIx::Class::ResultSet/as_query>
658fa250 57
4dc99a01 58=item Return Value: \[ $sql, @bind ]
658fa250 59
60=back
61
59af6677 62Returns the SQL statement and bind vars associated with the invocant.
63
64=cut
65
66sub as_query {
0f6fc705 67 my ( $self, $opts ) = @_;
68
69 $self->throw_exception( "as_query needs a hashref" )
70 if defined $opts and ref $opts ne 'HASH';
71
72 $opts->{skip_parens} ||= 0;
59af6677 73
74 my $storage = $self->{storage};
75 my $sql_maker = $storage->sql_maker;
76 local $sql_maker->{for};
77
78 my @args = $storage->_select_args(@{$self->{args}});
79 my ($sql, $bind) = $storage->_prep_for_execute(@args[0 .. 2], [@args[4 .. $#args]]);
0f6fc705 80 $sql = "($sql)" unless $opts->{skip_parens};
81 return \[ $sql, @$bind ];
59af6677 82}
83
5cf243f6 84=head2 next
85
21b5c39d 86=over 4
87
ebc77b53 88=item Arguments: none
21b5c39d 89
d601dc88 90=item Return Value: \@row_columns
21b5c39d 91
5cf243f6 92=back
93
685dad64 94Advances the cursor to the next row and returns an array of column
95values (the result of L<DBI/fetchrow_array> method).
5cf243f6 96
97=cut
98
dbaee748 99sub _dbh_next {
100 my ($storage, $dbh, $self) = @_;
1346e22d 101
dbaee748 102 $self->_check_dbh_gen;
cb5f2eea 103 if ($self->{attrs}{rows} && $self->{pos} >= $self->{attrs}{rows}) {
71e65b39 104 $self->{sth}->finish if $self->{sth}->{Active};
cb5f2eea 105 delete $self->{sth};
106 $self->{done} = 1;
107 }
108 return if $self->{done};
109 unless ($self->{sth}) {
dbaee748 110 $self->{sth} = ($storage->_select(@{$self->{args}}))[1];
5c91499f 111 if ($self->{attrs}{software_limit}) {
112 if (my $offset = $self->{attrs}{offset}) {
cb5f2eea 113 $self->{sth}->fetch for 1 .. $offset;
5c91499f 114 }
115 }
28927b50 116 }
cb5f2eea 117 my @row = $self->{sth}->fetchrow_array;
118 if (@row) {
119 $self->{pos}++;
120 } else {
121 delete $self->{sth};
122 $self->{done} = 1;
123 }
28927b50 124 return @row;
125}
126
dbaee748 127sub next {
128 my ($self) = @_;
129 $self->{storage}->dbh_do($self->can('_dbh_next'), $self);
130}
131
5cf243f6 132=head2 all
133
21b5c39d 134=over 4
135
ebc77b53 136=item Arguments: none
21b5c39d 137
d601dc88 138=item Return Value: \@row_columns+
21b5c39d 139
5cf243f6 140=back
141
21b5c39d 142Returns a list of arrayrefs of column values for all rows in the
143L<DBIx::Class::ResultSet>.
5cf243f6 144
145=cut
146
dbaee748 147sub _dbh_all {
148 my ($storage, $dbh, $self) = @_;
1346e22d 149
dbaee748 150 $self->_check_dbh_gen;
cb5f2eea 151 $self->{sth}->finish if $self->{sth}->{Active};
152 delete $self->{sth};
dbaee748 153 my ($rv, $sth) = $storage->_select(@{$self->{args}});
1a14aa3f 154 return @{$sth->fetchall_arrayref};
155}
156
dbaee748 157sub all {
158 my ($self) = @_;
6296f45b 159 if ($self->{attrs}{software_limit}
160 && ($self->{attrs}{offset} || $self->{attrs}{rows})) {
161 return $self->SUPER::all;
162 }
dbaee748 163 $self->{storage}->dbh_do($self->can('_dbh_all'), $self);
164}
165
5cf243f6 166=head2 reset
167
5cf243f6 168Resets the cursor to the beginning of the L<DBIx::Class::ResultSet>.
169
170=cut
171
28927b50 172sub reset {
173 my ($self) = @_;
1346e22d 174
dbaee748 175 # No need to care about failures here
176 eval { $self->{sth}->finish if $self->{sth} && $self->{sth}->{Active} };
1346e22d 177 $self->_soft_reset;
178}
179
180sub _soft_reset {
181 my ($self) = @_;
182
cb5f2eea 183 delete $self->{sth};
cb5f2eea 184 delete $self->{done};
dbaee748 185 $self->{pos} = 0;
28927b50 186 return $self;
187}
188
dbaee748 189sub _check_dbh_gen {
1346e22d 190 my ($self) = @_;
191
dbaee748 192 if($self->{_dbh_gen} != $self->{storage}->{_dbh_gen}) {
193 $self->{_dbh_gen} = $self->{storage}->{_dbh_gen};
194 $self->_soft_reset;
1346e22d 195 }
196}
197
28927b50 198sub DESTROY {
199 my ($self) = @_;
1346e22d 200
dbaee748 201 # None of the reasons this would die matter if we're in DESTROY anyways
19fb8520 202 local $@;
dbaee748 203 eval { $self->{sth}->finish if $self->{sth} && $self->{sth}->{Active} };
28927b50 204}
205
2061;