File Coverage

blib/lib/Apache/BabyConnect.pm
Criterion Covered Total %
statement 8 12 66.6
branch 3 6 50.0
condition 2 6 33.3
subroutine 4 4 100.0
pod n/a
total 17 28 60.7


line stmt bran cond sub pod time code
1             package Apache::BabyConnect;
2              
3             our @ISA = qw();
4             our $VERSION = '0.93';
5              
6 1     1   44637 use strict;
  1         2  
  1         118  
7              
8             die "
9             Apache::BabyConnect cannot start without setting the environment
10             variable BABYCONNECT. You may have forgotten to set BABYCONNECT
11             environment variable prior to loading the Apache::BabyConnect
12             module.
13             In the /etc/httpd/conf.d/perl.conf you need to setup the environment
14             variable before loading the Apache::BabyConnect module. For instance,
15             if you have loaded the Apache::BabyConnect from a startup script
16             using the PerlRequire directive, you can setup the BABYCONNECT
17             environment variable simply by using the directive PerlSetEnv prior
18             to loading the startup script:
19              
20             PerlSetEnv BABYCONNECT /opt/DBI-BabyConnect-$VERSION/configuration
21             PerlRequire /opt/DBI-BabyConnect-$VERSION/startupscripts/babystartup.pl
22             Alias /perl /var/www/perl
23            
24             SetHandler perl-script
25             PerlResponseHandler ModPerl::Registry
26             PerlOptions +ParseHeaders
27             Options +ExecCGI
28            
29              
30             " unless $ENV{BABYCONNECT};
31 1 50 33     289 use constant MP2 => (exists $ENV{MOD_PERL_API_VERSION} &&
32 1     1   6 $ENV{MOD_PERL_API_VERSION} == 2) ? 1 : 0;
  1         2  
33              
34             BEGIN {
35 1 50   1   25 if (MP2) {
36             require mod_perl2;
37             require Apache2::Module;
38             require Apache2::ServerUtil;
39             }
40 0 50 33     0 elsif (defined $modperl::VERSION && $modperl::VERSION > 1 &&
41             $modperl::VERSION < 1.99) {
42 0         0 require Apache;
43             }
44             }
45              
46             ########################################################################################
47             # DBI::BabyConnect needs to be called with caching and persistence enabled
48 1     1   692 use DBI::BabyConnect(1,1);
  0            
  0            
49              
50             use Carp ();
51              
52             $Apache::BabyConnect::VERSION = '1.00';
53              
54             $Apache::BabyConnect::DEBUG = 3;
55              
56             my @ChildConnect; # connections to be established with each httpd child
57             my $parent_pid;
58              
59             ########################################################################################
60             ########################################################################################
61             sub debug {
62             print STDERR "$_[1]\n" if $Apache::BabyConnect::DEBUG >= $_[0];
63             }
64              
65             ########################################################################################
66             ########################################################################################
67             # connect_on_init is called in the script babystartup.pl to provide a PerlChildInitHandler
68             # that will be hooked to a DBI::BabyConnect instance.
69             #
70             # The connect_on_init will request a DBI::BabyConnect instance to manage a DBI connection whose
71             # parameters are being described with the database descriptor. Each child
72             # is hooked to such an instance, and the instance is being persisted during the
73             # life time of the child.
74             # Because all childs are being started with the same database descriptor, therefore
75             # they can access the database concurrently. You should be careful on how to use
76             # the connection. Refer to Apache::BabyConnect documentation, and the script testbaby.pl
77             # to understand how the pool of connections work.
78             # You can request new connection from any Perl script, and the connection will be cached
79             # only if the database descriptor cannot be found within the child (httpd child) own
80             # DBI::BabyConnect instance cache.
81             # The caching of connection per each httpd child (or its hooked instance DBI::BabyConnect instance)
82             # is maintained within the DBI::BabyConnect itself, and each entry in the cache is
83             # identified with the concatenation of the child kernel process ID and the database descriptor.
84             #
85             sub connect_on_init {
86             if (MP2) {
87             if (!@ChildConnect) {
88             my $s = Apache2::ServerUtil->server;
89             debug(1, "\n***!!!!!!!!! $$ connect_on_init / MP2 Apache2::ServerUtil->server NOT ChildConnect === @ChildConnect\n\n");
90             $s-> push_handlers(PerlChildInitHandler => \&childinit);
91             }
92             }
93             else {
94             Carp::carp("Apache.pm was not loaded\n")
95             and return unless $INC{'Apache.pm'};
96              
97             if (!@ChildConnect and Apache->can('push_handlers')) {
98             Apache->push_handlers(PerlChildInitHandler => \&childinit);
99             }
100             }
101              
102             debug(1, "\n*** connect_on_init / store connections === $$ @_\n\n");
103              
104             # store connections
105             $parent_pid = $$;
106             push @ChildConnect, [@_];
107             #foreach (@ChildConnect) { print STDERR "************** Childconnect: @$_\n"; #}
108             }
109              
110             ########################################################################################
111             ########################################################################################
112             # The PerlChildInitHandler creates all connections during server startup.
113             # Note: this handler runs in every child server, but not in the main server.
114             sub childinit {
115             my $prefix = " $$ Apache::BabyConnect ";
116             debug(2, "$prefix PerlChildInitHandler");
117              
118             while (@ChildConnect) {
119             for my $aref (@ChildConnect) {
120             debug(2, "\n\n************** Childconnect: @$aref");
121             my @da = @$aref;
122             shift @da;
123             my %da;
124             while (my($l,$r)=splice @da, 0, 2) {
125             $da{$l} = $r;
126             }
127             my ($arg_iconf,$arg_errlog,$arg_tralog,$arg_tralev) =
128             @{ %da } { qw(DESCRIPTOR ERROR_FILE TRACE_FILE TRACE_LEVEL) };
129             $arg_errlog ||= "";
130             $arg_tralog ||= "";
131             $arg_tralev ||= "";
132             #my $arg_iconf = ${@$aref}[1];
133             #my $arg_errlog = ${@$aref}[2] || "";
134             #my $arg_tralog = ${@$aref}[3] || "";
135             #my $arg_tralev = ${@$aref}[4] || "";
136             debug(2, " Child / ${@$aref}[0] requesting an instance of Apache::BabyConnect($arg_iconf) ");
137             debug(2, " HookError($arg_errlog)");
138             debug(2, " HookTracing($arg_tralog) with TraceLevel=$arg_tralev) ");
139             my $cnn = DBI::BabyConnect->new($arg_iconf);
140             # this redirection seems to work, but the need need debugging because it is altering the args!!!!!!!!
141             length($arg_errlog) > 2 && $cnn ->HookError(">>$arg_errlog");
142             #${@$aref}[2] && $cnn ->HookError(">>$arg_errlog");
143             $arg_tralev ||= 1; # if trace level not specified then assume 1
144             length($arg_tralog) > 2 && $cnn ->HookTracing(">>$arg_tralog",$arg_tralev);
145             #${@$aref}[3] && $cnn ->HookTracing(">>$arg_tralog",$arg_tralev);
146             }
147             shift @ChildConnect;
148             # fudge this for now, need debugging!!!!!!!!
149             last if @ChildConnect == 1;
150             }
151              
152             1;
153             }
154              
155             ########################################################################################
156             ########################################################################################
157             # The cleanup phase from within mod_perl will execute some code immediately after the
158             # request has been served (the client went away) and before the request object is destroyed.
159             #
160             # The PerlCleanupHandler does nothing since Apache::BabyConnect relies on DBI::BabyConnect
161             # to handle all DBI functions such as rollback when AutoCommit is off
162             sub cleanup {
163              
164             1;
165             }
166              
167             ########################################################################################
168             ########################################################################################
169             # ref: http://perl.apache.org/docs/2.0/api/Apache2/ServerUtil.html
170              
171             sub get_child_init_handlers {
172             my $s = Apache2::ServerUtil->server;
173             my $handlers_list = $s-> get_handlers('PerlChildInitHandler');
174             #a list of references to the handler subroutines
175             return $handlers_list;
176             }
177              
178             sub get_child_exit_handlers {
179             my $s = Apache2::ServerUtil->server;
180             my $handlers_list = $s-> get_handlers('PerlChildExitHandler') || [];
181             return $handlers_list;
182             }
183              
184             sub parent_pid {
185             return $parent_pid;
186             }
187              
188             sub cpids {
189             my @a = split(/\n/,`ps --ppid $parent_pid`);
190             my @cpid;
191             foreach (@a) {
192             if ($_ =~ m/^(\d+)/) {
193             push(@cpid,$1);
194             }
195             }
196             return @cpid;
197             }
198             ########################################################################################
199             ########################################################################################
200              
201             if (MP2) {
202             if (Apache2::Module::loaded('Apache2::Status')) {
203             Apache2::Status->menu_item(
204             'BabyConnect' => 'BabyConnet for DBI connections',
205             );
206             }
207             }
208             else {
209             if ($INC{'Apache.pm'} # is Apache loaded?
210             and Apache->can('module') # really loaded?
211             and Apache->module('Apache::Status')) { # and has an Apache::Status?
212             Apache::Status->menu_item(
213             'BabyConnect' => 'BabyConnect for DBI connections',
214             );
215             }
216             }
217              
218             1;
219              
220             __END__