#!/usr/bin/perl ##--------------------------------------------------------------------------## ## File: ## $Id: filter-spool,v 1.11 2002/09/27 05:01:07 ehood Exp $ ## Description: ## Script to grab mail spool and filter mail to raw mbox archives. ##--------------------------------------------------------------------------## ## Copyright (C) 2002 Earl Hood ## ## This program is free software; you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation; either version 2 of the License, or ## (at your option) any later version. ## ## This program is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with this program; if not, write to the Free Software ## Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA ## 02111-1307, USA ##--------------------------------------------------------------------------## package MHArc::filter_spool; ##--------------------------------------------------------------------------## # BEGIN { die qq/CGI use FORBIDDEN!\n/ if (defined($ENV{'GATEWAY_INTERFACE'})); } my $Dir; BEGIN { $Dir = `dirname $0`; chomp $Dir; } use lib "$Dir/../lib"; # Add relative lib to search path # ##--------------------------------------------------------------------------## # use MHArc::Config; my $config = MHArc::Config->load("$Dir/../lib/config.sh"); # ##--------------------------------------------------------------------------## use Getopt::Long; use MHArc::Util qw( cmd run_prg usage ); my @_term_sigs = qw( ABRT ALRM BUS FPE HUP ILL INT IOT PIPE POLL PROF QUIT SEGV TERM TRAP USR1 USR2 VTALRM XCPU XFSZ ); my $Procmail = $config->{'PROCMAIL'} || 'procmail'; my $Lockfile = $config->{'LOCKFILE'} || 'lockfile'; my $Formail = $config->{'FORMAIL'} || 'formail'; my $TmpSpool = '.newmail'; my $TmpSpoolLock = $TmpSpool.'.lock'; MAIN: { # Make sure umask is set to make things readable by default umask 022; # Grap command-line options my %opt = ( ); my $clstatus = GetOptions(\%opt, 'verbose!', 'home=s', 'html-dir=s', 'is-spool!', 'log-dir=s', 'lock-timeout=i', 'mail=s', 'mbox-dir=s', 'procmailrc=s', 'procmailvars=s', 'help', 'man', ); usage(0) unless $clstatus; usage(1) if $opt{'help'}; usage(2) if $opt{'man'}; my $verbose = $opt{'verbose'}; if ($verbose) { $MHArc::Util::ECHO_CMDS = 1; } my $home = $opt{'home'} || $config->{'SW_ROOT'} || "$Dir/.."; my $html_dir = $opt{'html-dir'} || $config->{'HTML_DIR'} || join('/', $home, 'html'); my $log_dir = $opt{'log-dir'} || $config->{'LOG_DIR'} || join('/', $home, 'log'); my $mbox_dir = $opt{'mbox-dir'} || $config->{'MBOX_DIR'} || join('/', $home, 'mbox'); my $procmailrc = $opt{'procmailrc'} || $config->{'PROCMAILRC'} || join('/', $home, 'procmailrc.mharc'); my $procmailvars = $opt{'procmailvars'} || $config->{'PROCMAILVARS'} || ""; my $mail = $opt{'mail'} || $config->{'ORGMAIL'} || join('/', '/var/mail', $ENV{'LOGNAME'}); my $is_spool = $opt{'is-spool'} || $config->{'IS_MAIL_SPOOL'} || 1; my $lock_to = $opt{'lock-timeout'} || $config->{'ORGMAIL_LOCK_TIMEOUT'} || 3600; die qq/ERROR: "$home" not a directory/ if (! -d $home); die qq/ERROR: Unable to change directory to "$home": $!/ unless chdir($home); # Make sure certain directories exist cmd('mkdir', '-p', $log_dir, $mbox_dir, $html_dir); # Check that we have data to process my $have_spool = 1; if ((! -e $mail) || ((stat($mail))[7] == 0)) { $have_spool = 0; if (! -e $TmpSpool) { print qq/"$mail" does not exist or is zero bytes/ if $verbose; exit 1; } print qq/No new mail, but $TmpSpool exists\n/ if $verbose; } if (cmd("$Lockfile -r5 -l$lock_to $TmpSpoolLock 2>/dev/null") != 0) { print qq/Unable to obtain lock, exiting/ if $verbose; exit 1; } eval { local @SIG{@_term_sigs} = (\&clean_lock) x scalar(@_term_sigs); if ($have_spool) { if ($is_spool) { run_prg($Lockfile, "-l$lock_to", '-ml'); } else { run_prg($Lockfile, "-l$lock_to", "$mail.lock"); } if (cmd("/bin/cat '$mail' >>$TmpSpool") == 0) { cmd("/bin/cat /dev/null >'$mail'"); } if ($is_spool) { cmd($Lockfile, '-mu'); } else { unlink("$mail.lock") || warn qq/Warning: Unable to remove "$mail.lock": $!\n/; } } if (cmd("$Formail -s $Procmail $procmailrc $procmailvars <$TmpSpool") == 0) { unlink($TmpSpool) || warn qq/Warning: Unable to remove "$TmpSpool"\n/; } }; clean_lock(); if ($@) { die $@, "\n"; } } # End: MAIN ##---------------------------------------------------------------------------## sub clean_lock { unlink($TmpSpoolLock); } ##---------------------------------------------------------------------------## __END__ =head1 NAME filter-spool - Filter incoming mail into raw archives =head1 SYNOPSIS filter-spool filter-spool [options] =head1 DESCRIPTION This program is part of mharc and has the responsibility of filtering incoming mail into the raw message archives. This script is called by the L script before L is invoked. =head1 OPTIONS This program is generally called without any command-line options since it will read Cmharc-rootE/lib/config.sh> for all configurable options. However, the following command-line options are available: =over =item C<-help> Print out usage information. =item C<-home> I Root pathname of archiving software and data. If not specified, C variable in C is used, else the parent directory that contains this program is used. =item C<-html-dir> I Root pathname containing HTML archives. If not specified, C variable in C is used, else C/html> is used. B This program does not do any processing of the HTML archives. This option is used to insure that the HTML archive root directory exists for subsequent processing by other mharc scripts. =item C<-is-spool> Specifies that C<-mail> represents a mail spool file. If not specified, the value of the C variable in C is used, else C<-mail> is assumed to be a mail spool file. =item C<-lock-timeout> I The age of a lock before it is forceably removed. This is used to help deal with stale locks. If this option is not specified, C variable in C is used, else C<3600> is used. =item C<-log-dir> I Root pathname to place log files. If not specified, C variable in C is used, else C/log> is used. =item C<-mail> I Pathname to incoming mailbox file. If not specified, C variable in C is used, else C is used, where C<$LOGNAME> represents the value of the C environment variable. =item C<-man> Print out entire manpage. =item C<-mbox-dir> I Root pathname containing raw mailbox archives. If not specified, C variable in C is used, else C/mbox> is used. =item C<-procmailrc> I Pathname to procmailrc file to use when filtering mail. If not specified, C variable in C is used, else C/procmailrc.mharc> is used. =item C<-procmailvars> I Additional variables to pass into C. If not specified, C variable in C is used. =item C<-verbose> Print out status messages. =back =head1 EXIT VALUES If there was mail to process, and no errors occurred during processing, a zero exit status will be returned. Otherwise, a non-zero exit status will be returned. =head1 FILES =over =item Cmharc-rootE/lib/config.sh> Main configuration file for mharc. =back =head1 VERSION $Id: filter-spool,v 1.11 2002/09/27 05:01:07 ehood Exp $ =head1 AUTHOR Earl Hood, earl@earlhood.com This program is part of the mharc archiving system and comes with ABSOLUTELY NO WARRANTY and may be copied only under the terms of the GNU General Public License, which may be found in the mharc distribution. =cut