in reply to mod_perl and multiple installations of the same code

Are these four sites running on the same box?

You have to re-jigger your modules so they don't have to know which host they are working for, or make SiteConfig smart enough to load the right things based on which host it's dealing with. SiteConfig might hold a hash of several configs and through an appropriate interface, return the values for the right host.

This is a basic mod_perl trap: you can't rely on Perl to clean up dependencies because it doesn't stop running. The design things you could ignore previously, perhaps setting global variables in a module and use-ing it, don't work anymore. We can't guess any more than that without knowing something about SiteConfig.pm

This problem is solvable, though, without copying the libraries a bunch of times. It might take a little work, but that work is better than making the situation even worse. :)

  • Comment on Re: mod_perl and multiple installations of the same code

Replies are listed 'Best First'.
Re^2: mod_perl and multiple installations of the same code
by saberworks (Curate) on Mar 16, 2005 at 19:07 UTC
    SiteConfig.pm is very simple. Here is an example:
    package SiteConfig; use strict; use Exporter; our $c; @SiteConfig::ISA = qw(Exporter); @SiteConfig::EXPORT_OK = qw($c); $c->{dbname} = 'somedb'; $c->{dbserver} = 'somehost'; $c->{dbuser} = 'someuser'; $c->{dbpass} = 'somepass'; $c->{site_name} = 'Some Plain Text Name'; $c->{domain} = 'some-domain.com'; #... and a bunch more ...
    Then the other various modules say stuff like: use SiteConfig qw($c); So what would need to happen is that SiteConfig would have to export a "$c" that is appropriate for the current request (based on some way to determine which of four domains it's serving). That doesn't even seem possible (to export something different at run-time when it's loaded when mod_perl starts). I think we'd have to change the interface from Exporter to a function or method call (in every one of our modules). There is also one "quick access" method inside SiteConfig.pm that allows you to grab any value w/out importing $c:
    sub param { return $c->{(shift)}; }
    That one seems like it would be easy to modify to return the appropriate value, if only I knew some reliable way to determine from which domain the request was coming.
      So what would need to happen is that SiteConfig would have to export a "$c" that is appropriate for the current request (based on some way to determine which of four domains it's serving). That doesn't even seem possible (to export something different at run-time when it's loaded when mod_perl starts).
      Tied variables allow you to have things that appear to be variables but are in fact subroutines.
      package SiteConfig; use strict; use base 'Exporter'; tie our $c, 'SiteConfig'; our @EXPORT_OK = qw($c); sub FETCH {{ dbname => 'somedb', dbserver => 'somehost', dbuser => 'someuser', dbpass => 'somepass', site_name => 'Some Plain Text Name', domain => 'some-domain.com', #... and a bunch more ... }}
        This is great. I'm going to try a combination of this and the Apache::Request host checking mentioned above by cowboy. Thanks!
      Running under mod_perl, you should be able to get an Apache::Request object easily, using something like this:
      # $c = { 'foo.com' => { dbname => 'foo', dbuser => 'foo', }, 'bar.com' => { dbname => 'bar', dbuser => 'bar', } }; sub param { my $param = shift; # get a request instance my $r = Apache::Request->instance(); # get the hostname my $host = $r->hostname(); return $c->{$host}->{$param}; }
      This obviously doesn't take into account 'www.foo.com' and 'foo.com' if they're the same thing, but a little munging of $host before using it, should allow you to find the right one, or worst case, fall back to a default.