Reputation: 3728
I'm hosting multiple instances of the same web app in different versions using the same instance of HTTPd and one VHOST
per instance/version of web app currently. I would like to use mod_perl's PostConfigRequire
to implement a handler pre-loading all those instances during server startup instead of relying on mod_perl's registry-facilities per request, as is done currently. The latter breaks in case of too many concurrent requests and according to some tests, that problem doesn't occur anymore in case things get pre-loaded.
Because of the different versions of my web app, I need to use PerlOptions +Parent
to provide each VHOST
with its individual Perl interpreter pool. Additionally I can easily configure PerlPostConfigRequire
per VHOST
, but pre-loading needs to take into account which VHOST
that handler is currently executed in. Within that handler I need to only load those files associated with some concrete VHOST
.
The problem is that I'm having trouble how to find the VHOST
currently executing that handler. In that past I have implemented something similar per request by looking at the currently requested URL and comparing that to VHOST
configs, but I don't have a request now. Apache2::ServerUtil->server()
is not providing my VHOST
, but it's available at all e.g. using Apache2::Directive::conftree()->lookup('VirtualHost')
. Only that I don't know which one is the one containing PerlPostConfigRequire
currently executed. I'm pretty sure that PerlPostConfigRequire
really gets executed per VHOST
, because I get debugging output scaling with the number of VHOST
s configured as well.
Any ideas? Thanks!
Upvotes: 1
Views: 97
Reputation: 3728
The only thing which came into my mind is using environment variables per VHOST like in the following example. PerlSetVar
doesn'T work because it's per request only and not available during startup of the web server.
PerlSetEnv SOME_ID "0c8c1236-86de-4483-9d4b-999e2cfd17c1"
PerlPostConfigRequire "Some.pm"
Each VHOST gets it's own ID and that environment variable seems to be uniquely available during execution of the configured package:
[Mon Aug 05 20:50:32.181559 2019] [:warn] [pid 17736:tid 704] [...]: 0c8c1236-86de-4483-9d4b-999e2cfd17c1: 1
[Mon Aug 05 20:50:32.836195 2019] [:warn] [pid 17736:tid 704] [...]: 9dc691d6-794a-4095-852e-e596cabf43d5: 1
[Mon Aug 05 20:50:34.180453 2019] [:warn] [pid 17736:tid 704] [...]: 0c8c1236-86de-4483-9d4b-999e2cfd17c1: 2
[Mon Aug 05 20:50:34.830098 2019] [:warn] [pid 17736:tid 704] [...]: 9dc691d6-794a-4095-852e-e596cabf43d5: 2
The logging code:
my $server = Apache2::ServerUtil->server();
$server->warn(__PACKAGE__ . ": $ENV{'SOME_ID'}: " . Apache2::ServerUtil::restart_count());
With that in mind, one can get all VHOSTs and search for the ID they define. It's important to note that lookup
is not of much help here, it doesn't seem to support searching for PerlSetEnv
directly, but one needs to implement that on hash refs returned for the VHOSTs manually:
my $confTree = Apache2::Directive::conftree();
my @vhosts = $confTree->lookup('VirtualHost');
Each result is a hash ref containing keys and values like the following:
$VAR1 = {\n 'PerlSetEnv' => 'AMS_MOD_PERL_PRE_LOADING_ID "9dc691d6-794a-4095-852e-e596cabf43d5"',\n[...]
'PerlSetEnv' => [\n '"AMS_MOD_PERL_PRE_LOADING_ID" "9dc691d6-794a-4095-852e-e596cabf43d5"',\n '"murks" "test"'\n ],
The structure of the hash ref depends on the actual config, so it might contain additional child hash refs I guess. Any better ideas welcome...
Upvotes: 0