DBIx-Custom / lib / DBI / Custom.pm /
Newer Older
295 lines | 6.801kb
first commit
yuki-kimoto authored on 2009-10-13
1
package DBI::Custom;
2
use Object::Simple;
add some method
yuki-kimoto authored on 2009-10-14
3
use DBI;
4
use SQL::Abstract;
first commit
yuki-kimoto authored on 2009-10-13
5

            
cleanup
yuki-kimoto authored on 2009-10-15
6
# Model
7
sub model : ClassAttr { auto_build => \&_inherit_model }
first commit
yuki-kimoto authored on 2009-10-13
8

            
cleanup
yuki-kimoto authored on 2009-10-15
9
# Inherit super class model
10
sub _inherit_model {
11
    $class = shict;
12
    my $super = do {
13
        no strict 'refs';
14
        ${"${class}::ISA"}[0];
15
    };
16
    my $model = eval{$super->can('model')}
17
                         ? $super->model->clone
18
                         : $class->Object::Simple::new;
cleanup
yuki-kimoto authored on 2009-10-14
19
    
20
    $class->model($model);
first commit
yuki-kimoto authored on 2009-10-13
21
}
22

            
cleanup
yuki-kimoto authored on 2009-10-15
23
# New
24
sub new {
25
    my $self = shift->Object::Simple::new(@_);
26
    my $class = ref $self;
27
    return bless {%{$class->model->clone}, %{$self}}, $class;
first commit
yuki-kimoto authored on 2009-10-13
28
}
29

            
cleanup
yuki-kimoto authored on 2009-10-15
30
# Initialize modle
31
sub initialize_model {
32
    my ($class, $callback) = @_;
first commit
yuki-kimoto authored on 2009-10-13
33
    
cleanup
yuki-kimoto authored on 2009-10-15
34
    # Callback to initialize model
35
    $callback->($class->model);
first commit
yuki-kimoto authored on 2009-10-13
36
}
37

            
cleanup
yuki-kimoto authored on 2009-10-15
38
# Clone
39
sub clone {
cleanup
yuki-kimoto authored on 2009-10-14
40
    my $self = shift;
cleanup
yuki-kimoto authored on 2009-10-15
41
    my $new = $self->Object::Simple::new;
42
    $new->connect_infos(%{$self->connect_infos || {}});
43
    $new->filters(%{$self->filters || {}});
cleanup
yuki-kimoto authored on 2009-10-14
44
    
cleanup
yuki-kimoto authored on 2009-10-15
45
    $new->global_bind_rules(@{$self->global_bind_rules || []});
46
    $new->global_fetch_rules(@{$self->global_fetch_rules || []});
cleanup
yuki-kimoto authored on 2009-10-14
47
    
cleanup
yuki-kimoto authored on 2009-10-15
48
    foreach my $method (qw/bind_rules fetch_rules/) {
49
        my $new_rules = [];
50
        foreach my $rule (@{$self->method}) {
51
            my $new_rule = {};
52
            foreach my $key ($rule) {
53
                if ($key eq 'filter') {
54
                    my $new_filters = [];
55
                    foreach my $filter (@{$rule->{$key} || []}) {
56
                        push @$new_filters, $filter
57
                    }
58
                    $new_rule->{$key} = $new_filters;
59
                }
60
                else {
61
                     $new_rule->{$key} = $rule->{$key};
62
                }
63
            }
64
            push @$new_rules, $new_rule;
65
        }
66
        $self->$method($new_rules);
cleanup
yuki-kimoto authored on 2009-10-14
67
    }
68
}
69

            
cleanup
yuki-kimoto authored on 2009-10-15
70
# Attribute
71
sub connect_info       : Attr { type => 'hash',  auto_build => sub { shift->connect_info({}) } }
72
sub global_bind_rules  : Attr { type => 'array', auto_build => sub { shift->global_bind_rules([]) } }
73
sub global_fetch_rules : Attr { type => 'array', auto_build => sub { shift->global_fetch_rules([]) } }
74
sub bind_rules         : Attr { type => 'hash',  auto_build => sub { shift->bind_rules({}) }
75
sub fetch_rules        : Attr { type => 'hash',  auto_build => sub { shift->fetch_rules({}) }
76

            
77
sub dbh          : Attr { auto_build => sub { shift->connect } }
78
sub sql_abstract : Attr { auto_build => sub { shift->sql_abstract(SQL::Abstract->new) }}
cleanup
yuki-kimoto authored on 2009-10-14
79

            
add some method
yuki-kimoto authored on 2009-10-14
80
sub connect {
81
    my $self = shift;
82
    my $connect_info = $self->connect_info;
83
    
84
    my $dbh = DBI->connect(
85
        $connect_info->{dsn},
86
        $connect_info->{user},
87
        $connect_info->{password},
88
        {
89
            RaiseError => 1,
90
            PrintError => 0,
91
            AutoCommit => 1,
92
            %{$connect_info->{options} || {} }
93
        }
94
    );
95
    
96
    $self->dbh($dbh);
97
}
first commit
yuki-kimoto authored on 2009-10-13
98

            
add some method
yuki-kimoto authored on 2009-10-14
99
sub reconnect {
100
    my $self = shift;
101
    $self->dbh(undef);
102
    $self->connect;
103
}
first commit
yuki-kimoto authored on 2009-10-13
104

            
add some method
yuki-kimoto authored on 2009-10-14
105
sub query {
106
    my ($self, $query, @binds) = @_;
107
    $self->{success} = 0;
108

            
109
    $self->_replace_omniholder(\$query, \@binds);
110

            
111
    my $st;
112
    my $sth;
113

            
114
    my $old = $old_statements{$self};
115

            
116
    if (my $i = (grep $old->[$_][0] eq $query, 0..$#$old)[0]) {
117
        $st = splice(@$old, $i, 1)->[1];
118
        $sth = $st->{sth};
119
    } else {
120
        eval { $sth = $self->{dbh}->prepare($query) } or do {
121
            if ($@) {
122
                $@ =~ s/ at \S+ line \d+\.\n\z//;
123
                Carp::croak($@);
124
            }
125
            $self->{reason} = "Prepare failed ($DBI::errstr)";
126
            return _dummy;
127
        };
128

            
129
        # $self is quoted on purpose, to pass along the stringified version,
130
        # and avoid increasing reference count.
131
        $st = bless {
132
            db    => "$self",
133
            sth   => $sth,
134
            query => $query
135
        }, 'DBIx::Simple::Statement';
136
        $statements{$self}{$st} = $st;
137
    }
first commit
yuki-kimoto authored on 2009-10-13
138

            
add some method
yuki-kimoto authored on 2009-10-14
139
    eval { $sth->execute(@binds) } or do {
140
        if ($@) {
141
            $@ =~ s/ at \S+ line \d+\.\n\z//;
142
            Carp::croak($@);
143
        }
first commit
yuki-kimoto authored on 2009-10-13
144

            
add some method
yuki-kimoto authored on 2009-10-14
145
        $self->{reason} = "Execute failed ($DBI::errstr)";
146
	return _dummy;
147
    };
148

            
149
    $self->{success} = 1;
150

            
151
    return bless { st => $st, lc_columns => $self->{lc_columns} }, $self->{result_class};
152
}
153

            
154
sub query {
155
    my ($self, $sql) = @_;
156
    my $sth = $self->dbh->prepare($sql);
157
    $sth->execute(@bind);
158
}
159

            
160
sub select {
161
    my ($table, $column_names, $where, $order) = @_;
first commit
yuki-kimoto authored on 2009-10-13
162
    
add some method
yuki-kimoto authored on 2009-10-14
163
    my ($stmt, @bind) = $self->sql_abstract->select($table, $column_names, $where, $order);
164
    my $sth = $self->dbh->prepare($stmt);
165
    $sth->execute(@bind);
166
}
167

            
168
sub insert {
169
    my ($self, $table, $values) = @_;
first commit
yuki-kimoto authored on 2009-10-13
170
    
add some method
yuki-kimoto authored on 2009-10-14
171
    my ($stmt, @bind) = $self->sql_abstract->insert($table, $values);
172
    my $sth = $self->dbh->prepare($stmt);
173
    $sth->execute(@bind);
174
}
175

            
176
sub update {
177
    my ($self, $values, $where) = @_;
178
    my ($stmt, @bind) = $self->sql_abstract->update($table, $values, $where);
179
    my $sth = $self->dbh->prepare($stmt);
180
    $sth->execute(@bind);
first commit
yuki-kimoto authored on 2009-10-13
181
}
182

            
add some method
yuki-kimoto authored on 2009-10-14
183
sub delete {
184
    my ($self, $where) = @_;
185
    my ($stmt, @bind) = $self->sql_abstract->delete($table, $where);
186
    my $sth = $self->dbh->prepare($stmt);
187
    $sth->execute(@bind);
188
}
189

            
190

            
first commit
yuki-kimoto authored on 2009-10-13
191

            
192
Object::Simple->build_class;
193

            
194
=head1 NAME
195

            
196
DBI::Custom - The great new DBI::Custom!
197

            
198
=head1 VERSION
199

            
200
Version 0.01
201

            
202
=cut
203

            
204
our $VERSION = '0.01';
205

            
206

            
207
=head1 SYNOPSIS
208

            
209
Quick summary of what the module does.
210

            
211
Perhaps a little code snippet.
212

            
213
    use DBI::Custom;
214

            
215
    my $foo = DBI::Custom->new();
216
    ...
217

            
218
=head1 EXPORT
219

            
220
A list of functions that can be exported.  You can delete this section
221
if you don't export anything, such as for a purely object-oriented module.
222

            
223
=head1 FUNCTIONS
224

            
225
=head2 function1
226

            
227
=cut
228

            
229
sub function1 {
230
}
231

            
232
=head2 function2
233

            
234
=cut
235

            
236
sub function2 {
237
}
238

            
239
=head1 AUTHOR
240

            
241
Yuki Kimoto, C<< <kimoto.yuki at gmail.com> >>
242

            
243
=head1 BUGS
244

            
245
Please report any bugs or feature requests to C<bug-dbi-custom at rt.cpan.org>, or through
246
the web interface at L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=DBI-Custom>.  I will be notified, and then you'll
247
automatically be notified of progress on your bug as I make changes.
248

            
249

            
250

            
251

            
252
=head1 SUPPORT
253

            
254
You can find documentation for this module with the perldoc command.
255

            
256
    perldoc DBI::Custom
257

            
258

            
259
You can also look for information at:
260

            
261
=over 4
262

            
263
=item * RT: CPAN's request tracker
264

            
265
L<http://rt.cpan.org/NoAuth/Bugs.html?Dist=DBI-Custom>
266

            
267
=item * AnnoCPAN: Annotated CPAN documentation
268

            
269
L<http://annocpan.org/dist/DBI-Custom>
270

            
271
=item * CPAN Ratings
272

            
273
L<http://cpanratings.perl.org/d/DBI-Custom>
274

            
275
=item * Search CPAN
276

            
277
L<http://search.cpan.org/dist/DBI-Custom/>
278

            
279
=back
280

            
281

            
282
=head1 ACKNOWLEDGEMENTS
283

            
284

            
285
=head1 COPYRIGHT & LICENSE
286

            
287
Copyright 2009 Yuki Kimoto, all rights reserved.
288

            
289
This program is free software; you can redistribute it and/or modify it
290
under the same terms as Perl itself.
291

            
292

            
293
=cut
294

            
295
1; # End of DBI::Custom