File Coverage

blib/lib/Teng/Iterator.pm
Criterion Covered Total %
statement 58 60 96.6
branch 24 28 85.7
condition 15 33 45.4
subroutine 10 10 100.0
pod 3 3 100.0
total 110 134 82.0


line stmt bran cond sub pod time code
1             package Teng::Iterator;
2 69     69   555 use strict;
  69         156  
  69         2246  
3 69     69   406 use warnings;
  69         173  
  69         1621  
4 69     69   361 use Carp ();
  69         145  
  69         1311  
5 69     69   333 use Scalar::Util qw/looks_like_number/;
  69         144  
  69         4027  
6             use Class::Accessor::Lite (
7 69         633 rw => [qw/suppress_object_creation apply_sql_types guess_sql_types/],
8 69     69   32949 );
  69         89646  
9 69     69   7346 use DBI qw(:sql_types);
  69         184  
  69         73858  
10              
11             sub new {
12 61     61 1 655 my ($class, %args) = @_;
13              
14 61         324 return bless \%args, $class;
15             }
16              
17             sub next {
18 58     58 1 18182 my $self = shift;
19              
20 58         109 my $row;
21 58 100       229 if ($self->{sth}) {
22 57         1744 $row = $self->{sth}->fetchrow_hashref;
23 57   66     628 $self->{select_columns} ||= $self->{sth}->{$self->{teng}->{fields_case}};
24 57 100       314 unless ( $row ) {
25 5         21 $self->{sth}->finish;
26 5         50 $self->{sth} = undef;
27 5         21 return;
28             }
29             } else {
30 1         4 return;
31             }
32              
33 52 100       157 if ($self->{suppress_object_creation}) {
34 4         17 return $row;
35             } else {
36 48 100       231 $self->_apply_sql_types($row) if $self->{apply_sql_types};
37             return $self->{row_class}->new(
38             {
39             sql => $self->{sql},
40             row_data => $row,
41             teng => $self->{teng},
42             table => $self->{table},
43             table_name => $self->{table_name},
44             select_columns => $self->{select_columns},
45             }
46 48         509 );
47             }
48             }
49              
50             sub _apply_sql_types {
51 11     11   24 my ($self, $row) = @_;
52              
53 11         36 foreach my $column (keys %$row) {
54 29         49 my $type = $self->{table}->{sql_types}->{$column};
55 29 100       56 if (defined $type) {
    100          
56 27 100 33     332 if ( $type == SQL_BIGINT
    100 33        
      33        
      66        
      66        
      66        
      33        
      33        
      33        
57             or $type == SQL_BIT
58             or $type == SQL_TINYINT
59             or $type == SQL_NUMERIC
60             or $type == SQL_INTEGER
61             or $type == SQL_SMALLINT
62             or $type == SQL_DECIMAL
63             or $type == SQL_FLOAT
64             or $type == SQL_REAL
65             or $type == SQL_DOUBLE
66             ) {
67 9         17 $row->{$column} += 0;
68             } elsif ($type == SQL_BOOLEAN) {
69 9 50       86 if ($self->{teng}->{boolean_value}) {
70 9 100       21 if ($row->{$column}) {
71 6         59 $row->{$column} = $self->{teng}->{boolean_value}->{true};
72             } else {
73 3         7 $row->{$column} = $self->{teng}->{boolean_value}->{false};
74             }
75             } else {
76 0         0 $row->{$column} += 0;
77             }
78             } else {
79 9         27 $row->{$column} .= '';
80             }
81             } elsif ($self->{guess_sql_types}) {
82 1 50       13 if (looks_like_number($row->{$column})) {
83 1         5 $row->{$column} += 0;
84             } else {
85 0         0 $row->{$column} .= '';
86             }
87             }
88             }
89             }
90              
91             sub all {
92 21     21 1 1112 my $self = shift;
93              
94 21         85 my $result = [];
95              
96 21 50       122 if ($self->{sth}) {
97 21   33     594 $self->{select_columns} ||= $self->{sth}->{$self->{teng}->{fields_case}};
98 21         376 $result = $self->{sth}->fetchall_arrayref(+{});
99 21         2394 $self->{sth}->finish;
100 21         111 $self->{sth} = undef;
101              
102 21 50       105 if (!$self->{suppress_object_creation}) {
103             $result = [map {
104 21         73 $self->{row_class}->new(
105             {
106             sql => $self->{sql},
107             row_data => $_,
108             teng => $self->{teng},
109             table => $self->{table},
110             table_name => $self->{table_name},
111             select_columns => $self->{select_columns},
112             }
113             )
114 85         493 } @$result];
115             }
116             }
117              
118 21 100       323 return wantarray ? @$result : $result;
119             }
120              
121             1;
122              
123             __END__
124             =head1 NAME
125              
126             Teng::Iterator - Iterator for Teng
127              
128             =head1 DESCRIPTION
129              
130             This is an iterator class for L<Teng>.
131              
132             =head1 SYNOPSIS
133              
134             my $itr = Your::Model->search('user',{});
135            
136             my @rows = $itr->all; # get all rows
137              
138             # do iteration
139             while (my $row = $itr->next) {
140             ...
141             }
142              
143             =head1 METHODS
144              
145             =over
146              
147             =item $itr = Teng::Iterator->new()
148              
149             Create new Teng::Iterator's object. You may not call this method directly.
150              
151             =item my $row = $itr->next();
152              
153             Get next row data.
154              
155             =item my @ary = $itr->all;
156              
157             Get all row data in array.
158              
159             =item $itr->suppress_object_creation($bool)
160              
161             Set row object creation mode.
162              
163             =item $itr->apply_sql_types($bool)
164              
165             Set column type application mode.
166              
167             If column has SQL type and it is numeric, regard it as number and add 0 to the value.
168             If column has SQL type and it isn't numeric, regard it as string and add '' to the value.
169             If column doesn't have SQL type, the value won't be changed.
170              
171             =item $itr->guess_sql_types($bool)
172              
173             If this is true, this implies apply_sql_types also true.
174             If column has no SQL type, it guesses SQL type with its value.
175             When column value likes numeric, regard it as number and add 0 to the value.
176             If not, regard it as string and add '' to the value.
177              
178             =back
179              
180             =cut
181