Apache-EnvDir
view release on metacpan or search on metacpan
use Apache::Log ();
use Apache::Constants qw(OK DECLINED);
use Apache::ModuleConfig ();
use DynaLoader ();
use strict;
use warnings;
our $VERSION = '1.00';
sub MyLogger::log_error {
my $self = shift;
print STDERR shift, "\n";
}
if($ENV{MOD_PERL}) {
our @ISA = qw(DynaLoader);
__PACKAGE__->bootstrap($VERSION);
}
sub EnvDir ($$$;$) {
my($cfg, $parms, $dirname, $prefix) = @_;
$dirname = Apache->server_root_relative($dirname) unless $dirname =~ m|^/|;
$cfg->{EnvDir}{$dirname} = {};
return _loadenv($cfg->{EnvDir}{$dirname}, $dirname, $prefix, "MyLogger");
}
sub handler {
my $r = shift;
my $cfg = Apache::ModuleConfig->get($r) || return DECLINED;
my $envdircfg = $cfg->{EnvDir};
return DECLINED unless $envdircfg;
foreach my $dirname (keys %$envdircfg) {
my $dircfg = $envdircfg->{$dirname};
_loadenv($dircfg, $dirname, $dircfg->{prefix}, $r);
foreach my $file (keys %{$dircfg->{file}}) {
$r->subprocess_env(join("", $dircfg->{prefix}, $file),
$dircfg->{file}{$file}[1]);
}
}
return OK;
}
sub _loadenv {
my($dircfg, $dirname, $prefix, $r) = @_;
my $changeflag = 0;
local *DIR;
local *FILE;
local $/ = undef;
die "couldn't find directory called $dirname\n" unless (-d $dirname && -x _);
# First time through, this creates an anonymous hash.
# On subsequent runs, the hash is cleared if $dirname's
# mtime has changed. This is how you get Apache::EnvDir
# to notice that files have gone away.
$dircfg->{mtime} ||= 0;
%$dircfg = () if (stat(_))[9] > $dircfg->{mtime};
$prefix ||= "";
$dircfg->{prefix} = $prefix;
$dircfg->{mtime} = (stat(_))[9];
local *DIR;
opendir(DIR, $dirname) || die "couldn't open $dirname\n";
local *FILE;
foreach my $file (readdir DIR) {
my $path = join("/", $dirname, $file);
# Only do files.
next unless (-f $path && -r _);
# Skip files that havn't changed.
$dircfg->{file}{$file} ||= [0,""];
next unless (stat(_))[9] > $dircfg->{file}{$file}[0];
$changeflag++;
$dircfg->{file}{$file}[0] = (stat(_))[9];
if(open FILE, $path) {
$dircfg->{file}{$file}[1] = <FILE>;
$dircfg->{file}{$file}[1] =~ s/[\r\n]$//g;
close(FILE);
} else {
$r->log_error("couldn't open $path") if $r;
}
}
closedir(DIR);
return $changeflag;
}
1;
__END__
=head1 NAME
Apache::EnvDir - Dynamically set environment variables via a directory of files
=head1 SYNOPSIS
httpd.conf:
PerlModule Apache::EnvDir
PerlPostReadRequestHandler Apache::EnvDir
EnvDir /path/to/dir/of/files PREFIX
=head1 DESCRIPTION
Apache::EnvDir creates environment variables using a directory of files. The
environment is dynamic -- changes to the files are reflected immediately
within Apache -- which allows data to be passed into the Apache environment
without restarting the webserver.
The module should be installed as a PostReadRequest handler to allow its
changes to be seen by other modules such as mod_cgi and mod_include.
=head1 OPTIONS
Apart from installing the module, loading it into mod_perl, and registering
it as a handler, there is only one configuration option
=over 4
=item EnvDir
This directive takes either one or two arguments. The first argument is
always a directory path (either absolute or relative to ServerRoot). Any
files found in this directory will be turned into environment variables.
The filename (minus any directory information) will become the variable
name and the contents of the file become the value of the variable.
If EnvDir is called with two arguments, the second argument is used as a
variable name prefix and will be prepended to the filename when
constructing the environment variable name.
EnvDir /path/to/dir FOO_
( run in 2.501 seconds using v1.01-cache-2.11-cpan-98e64b0badf )