File Coverage

lib/Object/Wrapper/Fork/DBI.pm
Criterion Covered Total %
statement 36 69 52.1
branch 0 22 0.0
condition n/a
subroutine 12 18 66.6
pod n/a
total 48 109 44.0


line stmt bran cond sub pod time code
1             ########################################################################
2             # housekeeping
3             ########################################################################
4              
5             package Object::Wrapper::Fork::DBI;
6              
7 1     1   1241 use 5.8.0;
  1         4  
  1         51  
8 1     1   6 use strict;
  1         1  
  1         42  
9 1     1   935 use parent qw( Object::Wrapper::Fork );
  1         359  
  1         7  
10              
11 1     1   36 use Carp;
  1         2  
  1         69  
12              
13             eval { require DBI };
14              
15 1     1   1177 use if ! $DBI::VERSION, 'Object::Wrapper::Fork::DBI_stubs';
  1         10  
  1         5  
16              
17             ########################################################################
18             # package variables & sanity checks
19             ########################################################################
20              
21             our $VERSION = 0.03;
22              
23             ########################################################################
24             # utility subs
25             ########################################################################
26              
27             ########################################################################
28             # public interface
29             ########################################################################
30              
31             sub connect
32             {
33             # discard the object/class: this is a factory.
34              
35 0     0     shift;
36              
37 0 0         my $dbh = DBI->connect( @_ )
38             or croak 'Fail connect: ' . $DBI::errstr;
39              
40 0           Object::Wrapper::Fork::dbh->new( $dbh )
41             }
42              
43             sub connect_cached
44             {
45 0     0     shift;
46              
47 0 0         my $dbh = DBI->connect_cached( @_ )
48             or croak 'Fail connect_cached: ' . $DBI::errstr;
49              
50 0           Object::Wrapper::Fork::dbh->new( $dbh )
51             }
52              
53             ########################################################################
54             # handlers for database and statement handles
55             #
56             # both inherit AUTOLOAD from Fork (i.e., they check the pid).
57             ########################################################################
58              
59             package Object::Wrapper::Fork::dbh;
60              
61 1     1   12 use 5.8.0;
  1         563  
  1         46  
62 1     1   5 use strict;
  1         2  
  1         35  
63 1     1   4 use parent qw( Object::Wrapper::Fork );
  1         2  
  1         5  
64              
65 1     1   59 use Carp qw( croak confess );
  1         2  
  1         415  
66              
67             sub prepare
68             {
69 0     0     my $franger = shift;
70              
71 0           my ( $dbh, $pid ) = @$franger;
72              
73 0 0         $pid == $$
74 0           or confess "Bogus prepare: @{ $franger } crosses fork.";
75              
76 0 0         my $sth = $dbh->prepare( @_ )
77             or croak 'Failed prepare: ' . $dbh->errstr;
78              
79 0           Object::Wrapper::Fork::sth->new( $sth )
80             }
81              
82             sub prepare_cached
83             {
84 0     0     my $franger = shift;
85              
86 0           my ( $dbh, $pid ) = @$franger;
87              
88 0 0         $pid == $$
89 0           or confess "Bogus prepare_cached: @{ $franger } crosses fork.";
90              
91 0 0         my $sth = $dbh->prepare_cached( @_ )
92             or croak 'Failed prepare_cached: ' . $dbh->errstr;
93              
94 0           Object::Wrapper::Fork::sth->new( $sth )
95             }
96              
97             sub cleanup
98             {
99 0     0     my ( $dbh, $pid ) = @_;
100              
101             my $struct
102             = do
103 0           {
104 0           my $drh = $dbh->{ Driver };
105              
106             $drh
107             ? $drh->{ CachedKids }
108 0 0         : ''
109             };
110              
111             my @kidz
112 0 0         = $struct
113             ? values %$struct
114             : ()
115             ;
116              
117 0 0         if( $$ != $pid )
118             {
119             # handle crossed a fork: turn off side
120             # effects of destruction.
121              
122             $_->{ InactiveDestroy } = 1
123 0           for
124             (
125             $dbh,
126             @kidz
127             );
128             }
129             else
130             {
131 0           $_->finish for @kidz;
132              
133 0           $dbh->disconnect;
134             }
135              
136             # at this point the DBI object has been
137             # prepared to go out of scope politely.
138              
139             return
140 0           }
141              
142             ########################################################################
143             # cleanup handler for statement handles
144              
145             package Object::Wrapper::Fork::sth;
146              
147 1     1   10 use 5.8.0;
  1         4  
  1         36  
148 1     1   5 use strict;
  1         1  
  1         35  
149 1     1   5 use parent qw( Object::Wrapper::Fork );
  1         1  
  1         4  
150              
151             sub cleanup
152             {
153 0     0     my ( $sth, $pid ) = @_;
154              
155 0 0         if( $$ ~~ $pid )
156             {
157             # same process: finalize the handle and disconnect.
158             # caller deals with clones.
159              
160             $sth->{ Active }
161 0 0         and $sth->finish;
162             }
163             else
164             {
165 0           $sth->{ InactiveDestroy } = 1;
166             }
167              
168             # at this point the DBI object has been
169             # prepared to go out of scope politely.
170              
171             return
172 0           }
173              
174              
175             # keep require happy
176              
177             1
178              
179             __END__