line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package SQL::Maker; |
2
|
15
|
|
|
15
|
|
255008
|
use strict; |
|
15
|
|
|
|
|
31
|
|
|
15
|
|
|
|
|
554
|
|
3
|
15
|
|
|
15
|
|
65
|
use warnings; |
|
15
|
|
|
|
|
20
|
|
|
15
|
|
|
|
|
357
|
|
4
|
15
|
|
|
15
|
|
434
|
use 5.008001; |
|
15
|
|
|
|
|
44
|
|
|
15
|
|
|
|
|
905
|
|
5
|
|
|
|
|
|
|
our $VERSION = '1.21'; |
6
|
|
|
|
|
|
|
use Class::Accessor::Lite 0.05 ( |
7
|
15
|
|
|
|
|
99
|
ro => [qw/quote_char name_sep new_line strict driver select_class/], |
8
|
15
|
|
|
15
|
|
7682
|
); |
|
15
|
|
|
|
|
14879
|
|
9
|
|
|
|
|
|
|
|
10
|
15
|
|
|
15
|
|
1518
|
use Carp (); |
|
15
|
|
|
|
|
22
|
|
|
15
|
|
|
|
|
217
|
|
11
|
15
|
|
|
15
|
|
6261
|
use SQL::Maker::Select; |
|
15
|
|
|
|
|
37
|
|
|
15
|
|
|
|
|
485
|
|
12
|
15
|
|
|
15
|
|
6403
|
use SQL::Maker::Select::Oracle; |
|
15
|
|
|
|
|
28
|
|
|
15
|
|
|
|
|
389
|
|
13
|
15
|
|
|
15
|
|
81
|
use SQL::Maker::Condition; |
|
15
|
|
|
|
|
22
|
|
|
15
|
|
|
|
|
416
|
|
14
|
15
|
|
|
15
|
|
64
|
use SQL::Maker::Util; |
|
15
|
|
|
|
|
16
|
|
|
15
|
|
|
|
|
235
|
|
15
|
15
|
|
|
15
|
|
7904
|
use Module::Load (); |
|
15
|
|
|
|
|
13603
|
|
|
15
|
|
|
|
|
295
|
|
16
|
15
|
|
|
15
|
|
258
|
use Scalar::Util (); |
|
15
|
|
|
|
|
16
|
|
|
15
|
|
|
|
|
970
|
|
17
|
|
|
|
|
|
|
|
18
|
|
|
|
|
|
|
sub load_plugin { |
19
|
1
|
|
|
1
|
0
|
12
|
my ($class, $role) = @_; |
20
|
1
|
50
|
|
|
|
9
|
$role = $role =~ s/^\+// ? $role : "SQL::Maker::Plugin::$role"; |
21
|
1
|
|
|
|
|
5
|
Module::Load::load($role); |
22
|
|
|
|
|
|
|
|
23
|
15
|
|
|
15
|
|
66
|
no strict 'refs'; |
|
15
|
|
|
|
|
19
|
|
|
15
|
|
|
|
|
28079
|
|
24
|
1
|
|
|
|
|
10
|
for (@{"${role}::EXPORT"}) { |
|
1
|
|
|
|
|
6
|
|
25
|
1
|
|
|
|
|
2
|
*{"${class}::$_"} = *{"${role}::$_"}; |
|
1
|
|
|
|
|
10
|
|
|
1
|
|
|
|
|
3
|
|
26
|
|
|
|
|
|
|
} |
27
|
|
|
|
|
|
|
} |
28
|
|
|
|
|
|
|
|
29
|
|
|
|
|
|
|
sub new { |
30
|
29
|
|
|
29
|
1
|
41440
|
my $class = shift; |
31
|
29
|
50
|
|
|
|
144
|
my %args = @_ == 1 ? %{$_[0]} : @_; |
|
0
|
|
|
|
|
0
|
|
32
|
29
|
50
|
|
|
|
77
|
unless ($args{driver}) { |
33
|
0
|
|
|
|
|
0
|
Carp::croak("'driver' is required for creating new instance of $class"); |
34
|
|
|
|
|
|
|
} |
35
|
29
|
|
|
|
|
44
|
my $driver = $args{driver}; |
36
|
29
|
100
|
|
|
|
70
|
unless ( defined $args{quote_char} ) { |
37
|
18
|
|
|
|
|
14
|
$args{quote_char} = do{ |
38
|
18
|
100
|
|
|
|
45
|
if ($driver eq 'mysql') { |
39
|
10
|
|
|
|
|
22
|
q{`} |
40
|
|
|
|
|
|
|
} else { |
41
|
8
|
|
|
|
|
18
|
q{"} |
42
|
|
|
|
|
|
|
} |
43
|
|
|
|
|
|
|
}; |
44
|
|
|
|
|
|
|
} |
45
|
29
|
50
|
|
|
|
70
|
$args{select_class} = $driver eq 'Oracle' ? 'SQL::Maker::Select::Oracle' : 'SQL::Maker::Select'; |
46
|
|
|
|
|
|
|
|
47
|
29
|
|
|
|
|
190
|
return bless { |
48
|
|
|
|
|
|
|
name_sep => '.', |
49
|
|
|
|
|
|
|
new_line => "\n", |
50
|
|
|
|
|
|
|
strict => 0, |
51
|
|
|
|
|
|
|
%args |
52
|
|
|
|
|
|
|
}, $class; |
53
|
|
|
|
|
|
|
} |
54
|
|
|
|
|
|
|
|
55
|
|
|
|
|
|
|
sub new_condition { |
56
|
88
|
|
|
88
|
1
|
11331
|
my $self = shift; |
57
|
|
|
|
|
|
|
|
58
|
88
|
|
|
|
|
332
|
SQL::Maker::Condition->new( |
59
|
|
|
|
|
|
|
quote_char => $self->{quote_char}, |
60
|
|
|
|
|
|
|
name_sep => $self->{name_sep}, |
61
|
|
|
|
|
|
|
strict => $self->{strict}, |
62
|
|
|
|
|
|
|
); |
63
|
|
|
|
|
|
|
} |
64
|
|
|
|
|
|
|
|
65
|
|
|
|
|
|
|
sub new_select { |
66
|
84
|
|
|
84
|
1
|
374
|
my $self = shift; |
67
|
84
|
50
|
|
|
|
197
|
my %args = @_==1 ? %{$_[0]} : @_; |
|
0
|
|
|
|
|
0
|
|
68
|
|
|
|
|
|
|
|
69
|
84
|
|
|
|
|
193
|
return $self->select_class->new( |
70
|
|
|
|
|
|
|
name_sep => $self->name_sep, |
71
|
|
|
|
|
|
|
quote_char => $self->quote_char, |
72
|
|
|
|
|
|
|
new_line => $self->new_line, |
73
|
|
|
|
|
|
|
strict => $self->strict, |
74
|
|
|
|
|
|
|
%args, |
75
|
|
|
|
|
|
|
); |
76
|
|
|
|
|
|
|
} |
77
|
|
|
|
|
|
|
|
78
|
|
|
|
|
|
|
# $builder->insert($table, \%values, \%opt); |
79
|
|
|
|
|
|
|
# $builder->insert($table, \@values, \%opt); |
80
|
|
|
|
|
|
|
sub insert { |
81
|
3
|
|
|
3
|
1
|
11
|
my ($self, $table, $values, $opt) = @_; |
82
|
3
|
|
50
|
|
|
32
|
my $prefix = $opt->{prefix} || 'INSERT INTO'; |
83
|
|
|
|
|
|
|
|
84
|
3
|
|
|
|
|
8
|
my $quoted_table = $self->_quote($table); |
85
|
|
|
|
|
|
|
|
86
|
3
|
|
|
|
|
4
|
my (@columns, @bind_columns, @quoted_columns, @values); |
87
|
3
|
50
|
|
|
|
16
|
@values = ref $values eq 'HASH' ? %$values : @$values; |
88
|
3
|
|
|
|
|
39
|
while (my ($col, $val) = splice(@values, 0, 2)) { |
89
|
2
|
|
|
|
|
6
|
push @quoted_columns, $self->_quote($col); |
90
|
2
|
50
|
|
|
|
8
|
if (Scalar::Util::blessed($val)) { |
91
|
0
|
0
|
|
|
|
0
|
if ($val->can('as_sql')) { |
92
|
0
|
|
|
0
|
|
0
|
push @columns, $val->as_sql(undef, sub { $self->_quote($_[0]) }); |
|
0
|
|
|
|
|
0
|
|
93
|
0
|
|
|
|
|
0
|
push @bind_columns, $val->bind(); |
94
|
|
|
|
|
|
|
} else { |
95
|
0
|
|
|
|
|
0
|
push @columns, '?'; |
96
|
0
|
|
|
|
|
0
|
push @bind_columns, $val; |
97
|
|
|
|
|
|
|
} |
98
|
|
|
|
|
|
|
} else { |
99
|
2
|
50
|
33
|
|
|
5
|
Carp::croak("cannot pass in an unblessed ref as an argument in strict mode") |
100
|
|
|
|
|
|
|
if ref($val) && $self->strict; |
101
|
2
|
50
|
33
|
|
|
10
|
if (ref($val) eq 'SCALAR') { |
|
|
50
|
|
|
|
|
|
102
|
|
|
|
|
|
|
# $builder->insert(foo => { created_on => \"NOW()" }); |
103
|
0
|
|
|
|
|
0
|
push @columns, $$val; |
104
|
|
|
|
|
|
|
} |
105
|
|
|
|
|
|
|
elsif (ref($val) eq 'REF' && ref($$val) eq 'ARRAY') { |
106
|
|
|
|
|
|
|
# $builder->insert( foo => \[ 'UNIX_TIMESTAMP(?)', '2011-04-12 00:34:12' ] ); |
107
|
0
|
|
|
|
|
0
|
my ( $stmt, @sub_bind ) = @{$$val}; |
|
0
|
|
|
|
|
0
|
|
108
|
0
|
|
|
|
|
0
|
push @columns, $stmt; |
109
|
0
|
|
|
|
|
0
|
push @bind_columns, @sub_bind; |
110
|
|
|
|
|
|
|
} |
111
|
|
|
|
|
|
|
else { |
112
|
|
|
|
|
|
|
# normal values |
113
|
2
|
|
|
|
|
4
|
push @columns, '?'; |
114
|
2
|
|
|
|
|
7
|
push @bind_columns, $val; |
115
|
|
|
|
|
|
|
} |
116
|
|
|
|
|
|
|
} |
117
|
|
|
|
|
|
|
} |
118
|
|
|
|
|
|
|
|
119
|
|
|
|
|
|
|
# Insert an empty record in SQLite. |
120
|
|
|
|
|
|
|
# ref. https://github.com/tokuhirom/SQL-Maker/issues/11 |
121
|
3
|
100
|
66
|
|
|
9
|
if ($self->driver eq 'SQLite' && @columns==0) { |
122
|
1
|
|
|
|
|
26
|
my $sql = "$prefix $quoted_table" . $self->new_line . 'DEFAULT VALUES'; |
123
|
1
|
|
|
|
|
9
|
return ($sql); |
124
|
|
|
|
|
|
|
} |
125
|
|
|
|
|
|
|
|
126
|
2
|
|
|
|
|
21
|
my $sql = "$prefix $quoted_table" . $self->new_line; |
127
|
2
|
|
|
|
|
16
|
$sql .= '(' . join(', ', @quoted_columns) .')' . $self->new_line . |
128
|
|
|
|
|
|
|
'VALUES (' . join(', ', @columns) . ')'; |
129
|
|
|
|
|
|
|
|
130
|
2
|
|
|
|
|
17
|
return ($sql, @bind_columns); |
131
|
|
|
|
|
|
|
} |
132
|
|
|
|
|
|
|
|
133
|
|
|
|
|
|
|
sub _quote { |
134
|
29
|
|
|
29
|
|
33
|
my ($self, $label) = @_; |
135
|
|
|
|
|
|
|
|
136
|
29
|
|
|
|
|
65
|
SQL::Maker::Util::quote_identifier($label, $self->quote_char(), $self->name_sep()); |
137
|
|
|
|
|
|
|
} |
138
|
|
|
|
|
|
|
|
139
|
|
|
|
|
|
|
sub delete { |
140
|
16
|
|
|
16
|
1
|
212
|
my ($self, $table, $where, $opt) = @_; |
141
|
|
|
|
|
|
|
|
142
|
16
|
|
|
|
|
25
|
my $w = $self->_make_where_clause($where); |
143
|
16
|
|
|
|
|
31
|
my $quoted_table = $self->_quote($table); |
144
|
16
|
|
|
|
|
31
|
my $sql = "DELETE FROM $quoted_table"; |
145
|
16
|
100
|
|
|
|
30
|
if ($opt->{using}) { |
146
|
|
|
|
|
|
|
# $bulder->delete('foo', \%where, { using => 'bar' }); |
147
|
|
|
|
|
|
|
# $bulder->delete('foo', \%where, { using => ['bar', 'qux'] }); |
148
|
4
|
100
|
|
|
|
11
|
my $tables = ref($opt->{using}) eq 'ARRAY' ? $opt->{using} : [$opt->{using}]; |
149
|
4
|
|
|
|
|
8
|
my $using = join(', ', map { $self->_quote($_) } @$tables); |
|
6
|
|
|
|
|
7
|
|
150
|
4
|
|
|
|
|
8
|
$sql .= " USING " . $using; |
151
|
|
|
|
|
|
|
} |
152
|
16
|
|
|
|
|
26
|
$sql .= $w->[0]; |
153
|
16
|
|
|
|
|
15
|
return ($sql, @{$w->[1]}); |
|
16
|
|
|
|
|
53
|
|
154
|
|
|
|
|
|
|
} |
155
|
|
|
|
|
|
|
|
156
|
|
|
|
|
|
|
sub update { |
157
|
0
|
|
|
0
|
1
|
0
|
my ($self, $table, $args, $where) = @_; |
158
|
|
|
|
|
|
|
|
159
|
0
|
|
|
|
|
0
|
my ($columns, $bind_columns) = $self->make_set_clause($args); |
160
|
|
|
|
|
|
|
|
161
|
0
|
|
|
|
|
0
|
my $w = $self->_make_where_clause($where); |
162
|
0
|
|
|
|
|
0
|
push @$bind_columns, @{$w->[1]}; |
|
0
|
|
|
|
|
0
|
|
163
|
|
|
|
|
|
|
|
164
|
0
|
|
|
|
|
0
|
my $quoted_table = $self->_quote($table); |
165
|
0
|
|
|
|
|
0
|
my $sql = "UPDATE $quoted_table SET " . join(', ', @$columns) . $w->[0]; |
166
|
0
|
|
|
|
|
0
|
return ($sql, @$bind_columns); |
167
|
|
|
|
|
|
|
} |
168
|
|
|
|
|
|
|
|
169
|
|
|
|
|
|
|
# make "SET" clause. |
170
|
|
|
|
|
|
|
sub make_set_clause { |
171
|
1
|
|
|
1
|
0
|
1
|
my ($self, $args) = @_; |
172
|
|
|
|
|
|
|
|
173
|
1
|
|
|
|
|
2
|
my (@columns, @bind_columns); |
174
|
1
|
50
|
|
|
|
5
|
my @args = ref $args eq 'HASH' ? %$args : @$args; |
175
|
1
|
|
|
|
|
28
|
while (my ($col, $val) = splice @args, 0, 2) { |
176
|
2
|
|
|
|
|
4
|
my $quoted_col = $self->_quote($col); |
177
|
2
|
50
|
|
|
|
5
|
if (Scalar::Util::blessed($val)) { |
178
|
0
|
0
|
|
|
|
0
|
if ($val->can('as_sql')) { |
179
|
0
|
|
|
0
|
|
0
|
push @columns, "$quoted_col = " . $val->as_sql(undef, sub { $self->_quote($_[0]) }); |
|
0
|
|
|
|
|
0
|
|
180
|
0
|
|
|
|
|
0
|
push @bind_columns, $val->bind(); |
181
|
|
|
|
|
|
|
} else { |
182
|
0
|
|
|
|
|
0
|
push @columns, "$quoted_col = ?"; |
183
|
0
|
|
|
|
|
0
|
push @bind_columns, $val; |
184
|
|
|
|
|
|
|
} |
185
|
|
|
|
|
|
|
} else { |
186
|
2
|
50
|
33
|
|
|
8
|
Carp::croak("cannot pass in an unblessed ref as an argument in strict mode") |
187
|
|
|
|
|
|
|
if ref($val) && $self->strict; |
188
|
2
|
50
|
33
|
|
|
8
|
if (ref $val eq 'SCALAR') { |
|
|
50
|
|
|
|
|
|
189
|
|
|
|
|
|
|
# $builder->update(foo => { created_on => \"NOW()" }); |
190
|
0
|
|
|
|
|
0
|
push @columns, "$quoted_col = " . $$val; |
191
|
|
|
|
|
|
|
} |
192
|
|
|
|
|
|
|
elsif (ref $val eq 'REF' && ref $$val eq 'ARRAY' ) { |
193
|
|
|
|
|
|
|
# $builder->update( foo => \[ 'VALUES(foo) + ?', 10 ] ); |
194
|
0
|
|
|
|
|
0
|
my ( $stmt, @sub_bind ) = @{$$val}; |
|
0
|
|
|
|
|
0
|
|
195
|
0
|
|
|
|
|
0
|
push @columns, "$quoted_col = " . $stmt; |
196
|
0
|
|
|
|
|
0
|
push @bind_columns, @sub_bind; |
197
|
|
|
|
|
|
|
} |
198
|
|
|
|
|
|
|
else { |
199
|
|
|
|
|
|
|
# normal values |
200
|
2
|
|
|
|
|
3
|
push @columns, "$quoted_col = ?"; |
201
|
2
|
|
|
|
|
10
|
push @bind_columns, $val; |
202
|
|
|
|
|
|
|
} |
203
|
|
|
|
|
|
|
} |
204
|
|
|
|
|
|
|
} |
205
|
1
|
|
|
|
|
3
|
return (\@columns, \@bind_columns); |
206
|
|
|
|
|
|
|
} |
207
|
|
|
|
|
|
|
|
208
|
|
|
|
|
|
|
sub where { |
209
|
0
|
|
|
0
|
1
|
0
|
my ($self, $where) = @_; |
210
|
0
|
|
|
|
|
0
|
my $cond = $self->_make_where_condition($where); |
211
|
0
|
|
|
0
|
|
0
|
return ($cond->as_sql(undef, sub { $self->_quote($_[0]) }), $cond->bind()); |
|
0
|
|
|
|
|
0
|
|
212
|
|
|
|
|
|
|
} |
213
|
|
|
|
|
|
|
|
214
|
|
|
|
|
|
|
sub _make_where_condition { |
215
|
87
|
|
|
87
|
|
105
|
my ($self, $where) = @_; |
216
|
|
|
|
|
|
|
|
217
|
87
|
50
|
|
|
|
145
|
return $self->new_condition unless $where; |
218
|
87
|
100
|
66
|
|
|
303
|
if ( Scalar::Util::blessed( $where ) and $where->can('as_sql') ) { |
219
|
9
|
|
|
|
|
22
|
return $where; |
220
|
|
|
|
|
|
|
} |
221
|
|
|
|
|
|
|
|
222
|
78
|
|
|
|
|
138
|
my $w = $self->new_condition; |
223
|
78
|
100
|
|
|
|
298
|
my @w = ref $where eq 'ARRAY' ? @$where : %$where; |
224
|
78
|
|
|
|
|
596
|
while (my ($col, $val) = splice @w, 0, 2) { |
225
|
59
|
|
|
|
|
128
|
$w->add($col => $val); |
226
|
|
|
|
|
|
|
} |
227
|
78
|
|
|
|
|
225
|
return $w; |
228
|
|
|
|
|
|
|
} |
229
|
|
|
|
|
|
|
|
230
|
|
|
|
|
|
|
sub _make_where_clause { |
231
|
16
|
|
|
16
|
|
17
|
my ($self, $where) = @_; |
232
|
|
|
|
|
|
|
|
233
|
16
|
100
|
|
|
|
39
|
return ['', []] unless $where; |
234
|
|
|
|
|
|
|
|
235
|
13
|
|
|
|
|
24
|
my $w = $self->_make_where_condition($where); |
236
|
13
|
|
|
0
|
|
58
|
my $sql = $w->as_sql(undef, sub { $self->_quote($_[0]) }); |
|
0
|
|
|
|
|
0
|
|
237
|
13
|
50
|
|
|
|
60
|
return [$sql ? " WHERE $sql" : '', [$w->bind]]; |
238
|
|
|
|
|
|
|
} |
239
|
|
|
|
|
|
|
|
240
|
|
|
|
|
|
|
# my($stmt, @bind) = $sql−>select($table, \@fields, \%where, \%opt); |
241
|
|
|
|
|
|
|
sub select { |
242
|
76
|
|
|
76
|
1
|
139439
|
my $stmt = shift->select_query(@_); |
243
|
76
|
|
|
|
|
167
|
return ($stmt->as_sql,@{$stmt->bind}); |
|
73
|
|
|
|
|
154
|
|
244
|
|
|
|
|
|
|
} |
245
|
|
|
|
|
|
|
|
246
|
|
|
|
|
|
|
sub select_query { |
247
|
81
|
|
|
81
|
0
|
907
|
my ($self, $table, $fields, $where, $opt) = @_; |
248
|
|
|
|
|
|
|
|
249
|
81
|
50
|
|
|
|
228
|
unless (ref $fields eq 'ARRAY') { |
250
|
0
|
|
|
|
|
0
|
Carp::croak("SQL::Maker::select_query: \$fields should be ArrayRef[Str]"); |
251
|
|
|
|
|
|
|
} |
252
|
|
|
|
|
|
|
|
253
|
81
|
|
|
|
|
160
|
my $stmt = $self->new_select; |
254
|
81
|
|
|
|
|
144
|
for my $field (@$fields) { |
255
|
113
|
100
|
|
|
|
350
|
$stmt->add_select(ref $field eq 'ARRAY' ? @$field : $field); |
256
|
|
|
|
|
|
|
} |
257
|
|
|
|
|
|
|
|
258
|
81
|
100
|
|
|
|
198
|
if ( defined $table ) { |
259
|
78
|
100
|
|
|
|
132
|
unless ( ref $table ) { |
260
|
|
|
|
|
|
|
# $table = 'foo' |
261
|
70
|
|
|
|
|
147
|
$stmt->add_from( $table ); |
262
|
|
|
|
|
|
|
} |
263
|
|
|
|
|
|
|
else { |
264
|
|
|
|
|
|
|
# $table = [ 'foo', [ bar => 'b' ] ] |
265
|
8
|
|
|
|
|
13
|
for ( @$table ) { |
266
|
14
|
100
|
|
|
|
43
|
$stmt->add_from( ref $_ eq 'ARRAY' ? @$_ : $_ ); |
267
|
|
|
|
|
|
|
} |
268
|
|
|
|
|
|
|
} |
269
|
|
|
|
|
|
|
} |
270
|
|
|
|
|
|
|
|
271
|
81
|
100
|
|
|
|
178
|
$stmt->prefix($opt->{prefix}) if $opt->{prefix}; |
272
|
|
|
|
|
|
|
|
273
|
81
|
100
|
|
|
|
150
|
if ( $where ) { |
274
|
74
|
|
|
|
|
143
|
$stmt->set_where($self->_make_where_condition($where)); |
275
|
|
|
|
|
|
|
} |
276
|
|
|
|
|
|
|
|
277
|
81
|
100
|
|
|
|
157
|
if ( my $joins = $opt->{joins} ) { |
278
|
3
|
|
|
|
|
8
|
for my $join ( @$joins ) { |
279
|
3
|
50
|
|
|
|
14
|
$stmt->add_join(ref $join eq 'ARRAY' ? @$join : $join); |
280
|
|
|
|
|
|
|
} |
281
|
|
|
|
|
|
|
} |
282
|
|
|
|
|
|
|
|
283
|
81
|
100
|
|
|
|
172
|
if (my $o = $opt->{order_by}) { |
284
|
27
|
100
|
|
|
|
75
|
if (ref $o eq 'ARRAY') { |
|
|
100
|
|
|
|
|
|
285
|
6
|
|
|
|
|
11
|
for my $order (@$o) { |
286
|
12
|
100
|
|
|
|
24
|
if (ref $order eq 'HASH') { |
287
|
|
|
|
|
|
|
# Skinny-ish [{foo => 'DESC'}, {bar => 'ASC'}] |
288
|
3
|
|
|
|
|
11
|
$stmt->add_order_by(%$order); |
289
|
|
|
|
|
|
|
} else { |
290
|
|
|
|
|
|
|
# just ['foo DESC', 'bar ASC'] |
291
|
9
|
|
|
|
|
43
|
$stmt->add_order_by(\$order); |
292
|
|
|
|
|
|
|
} |
293
|
|
|
|
|
|
|
} |
294
|
|
|
|
|
|
|
} elsif (ref $o eq 'HASH') { |
295
|
|
|
|
|
|
|
# Skinny-ish {foo => 'DESC'} |
296
|
3
|
|
|
|
|
11
|
$stmt->add_order_by(%$o); |
297
|
|
|
|
|
|
|
} else { |
298
|
|
|
|
|
|
|
# just 'foo DESC, bar ASC' |
299
|
18
|
|
|
|
|
55
|
$stmt->add_order_by(\$o); |
300
|
|
|
|
|
|
|
} |
301
|
|
|
|
|
|
|
} |
302
|
81
|
100
|
|
|
|
148
|
if (my $o = $opt->{group_by}) { |
303
|
12
|
100
|
|
|
|
36
|
if (ref $o eq 'ARRAY') { |
|
|
100
|
|
|
|
|
|
304
|
6
|
|
|
|
|
8
|
for my $group (@$o) { |
305
|
12
|
100
|
|
|
|
20
|
if (ref $group eq 'HASH') { |
306
|
|
|
|
|
|
|
# Skinny-ish [{foo => 'DESC'}, {bar => 'ASC'}] |
307
|
3
|
|
|
|
|
13
|
$stmt->add_group_by(%$group); |
308
|
|
|
|
|
|
|
} else { |
309
|
|
|
|
|
|
|
# just ['foo DESC', 'bar ASC'] |
310
|
9
|
|
|
|
|
15
|
$stmt->add_group_by(\$group); |
311
|
|
|
|
|
|
|
} |
312
|
|
|
|
|
|
|
} |
313
|
|
|
|
|
|
|
} elsif (ref $o eq 'HASH') { |
314
|
|
|
|
|
|
|
# Skinny-ish {foo => 'DESC'} |
315
|
3
|
|
|
|
|
11
|
$stmt->add_group_by(%$o); |
316
|
|
|
|
|
|
|
} else { |
317
|
|
|
|
|
|
|
# just 'foo DESC, bar ASC' |
318
|
3
|
|
|
|
|
10
|
$stmt->add_group_by(\$o); |
319
|
|
|
|
|
|
|
} |
320
|
|
|
|
|
|
|
} |
321
|
81
|
100
|
|
|
|
141
|
if (my $o = $opt->{index_hint}) { |
322
|
3
|
|
|
|
|
8
|
$stmt->add_index_hint($table, $o); |
323
|
|
|
|
|
|
|
} |
324
|
|
|
|
|
|
|
|
325
|
81
|
100
|
|
|
|
191
|
$stmt->limit( $opt->{limit} ) if defined $opt->{limit}; |
326
|
81
|
100
|
|
|
|
147
|
$stmt->offset( $opt->{offset} ) if $opt->{offset}; |
327
|
|
|
|
|
|
|
|
328
|
81
|
50
|
|
|
|
158
|
if (my $terms = $opt->{having}) { |
329
|
0
|
|
|
|
|
0
|
while (my ($col, $val) = each %$terms) { |
330
|
0
|
|
|
|
|
0
|
$stmt->add_having($col => $val); |
331
|
|
|
|
|
|
|
} |
332
|
|
|
|
|
|
|
} |
333
|
|
|
|
|
|
|
|
334
|
81
|
50
|
|
|
|
125
|
$stmt->for_update(1) if $opt->{for_update}; |
335
|
81
|
|
|
|
|
128
|
return $stmt; |
336
|
|
|
|
|
|
|
} |
337
|
|
|
|
|
|
|
|
338
|
|
|
|
|
|
|
1; |
339
|
|
|
|
|
|
|
__END__ |