2020 lines
73 KiB
Perl
Executable File
2020 lines
73 KiB
Perl
Executable File
#!/usr/bin/perl -wT
|
|
|
|
#----------------------------------------------------------------------
|
|
# heading : Configuration
|
|
# description : E-mail Management
|
|
# navigation : 6000 6701
|
|
#
|
|
# Author: Stephen Noble support@dungog.net
|
|
#
|
|
#----------------------------------------------------------------------
|
|
|
|
package esmith;
|
|
|
|
use strict;
|
|
use CGI ':all';
|
|
use CGI::Carp qw(fatalsToBrowser);
|
|
|
|
use esmith::cgi;
|
|
use esmith::config;
|
|
use esmith::util;
|
|
use esmith::db;
|
|
|
|
use File::Find; #find user Maildir's
|
|
|
|
sub showInitial ($$); #front
|
|
sub showHelp ($);
|
|
|
|
sub showGroup ($$);
|
|
sub performGroup ($);
|
|
|
|
#global
|
|
sub showGlobalEnable ($$); #Global Settings
|
|
sub showEdit ($); #Add or modify a Global procmail rule
|
|
sub performSave ($); #save global rule
|
|
sub performDelete ($); #delete global rule
|
|
sub performGlobalSave ($); #save globally
|
|
sub performShowHide ($); #show hide _. pseudonyms
|
|
|
|
#individual
|
|
sub showEnableProc ($$$); #Single user setup
|
|
sub showAdvancedRuleEdit ($); #Add or modify a users procmail rule
|
|
sub performEnableProc ($); #save single user
|
|
sub performSaveRule ($); #save single user rule
|
|
sub performDeleteSingle ($); #delete single user rule
|
|
sub performDeletelog ($); #delete user procmail.log
|
|
sub performViewlog ($); #view .procmailrc or procmail.log
|
|
|
|
sub GetDisplayName ($); # of the mailfolder
|
|
|
|
BEGIN
|
|
{
|
|
# Clear PATH and related environment variables so that calls to
|
|
# external programs do not cause results to be tainted. See
|
|
# "perlsec" manual page for details.
|
|
|
|
$ENV {'PATH'} = '/usr/bin';
|
|
$ENV {'SHELL'} = '/bin/bash';
|
|
delete $ENV {'ENV'};
|
|
}
|
|
|
|
esmith::util::setRealToEffective ();
|
|
|
|
$CGI::POST_MAX=1024 * 100; # max 100K posts
|
|
$CGI::DISABLE_UPLOADS = 1; # no uploads
|
|
|
|
my %conf;
|
|
tie %conf, 'esmith::config';
|
|
|
|
my %accounts;
|
|
tie %accounts, 'esmith::config', '/home/e-smith/db/accounts';
|
|
|
|
my %domains;
|
|
tie %domains, 'esmith::config', '/home/e-smith/db/domains';
|
|
|
|
my %processmail;
|
|
tie %processmail, 'esmith::config', '/home/e-smith/db/processmail';
|
|
|
|
my %dungog;
|
|
tie %dungog, 'esmith::config', '/home/e-smith/db/dungog';
|
|
|
|
#-------------------------
|
|
# global variables
|
|
#-------------------------
|
|
|
|
my %Label = ('TO_' => 'e-mail address To:&Cc:',
|
|
'From' => 'e-mail address From:',
|
|
'Subject' => 'the subject',
|
|
'>' => 'size greater than',
|
|
'<' => 'size less than',
|
|
'headers' => 'e-mail headers');
|
|
|
|
my %Labels = ('sort' => 'sort to mail folder',
|
|
'forward' => 'forward email',
|
|
'delete' => 'delete email',
|
|
'inbox' => 'send to my inbox');
|
|
|
|
#-------------------------
|
|
# examine state parameter
|
|
#-------------------------
|
|
|
|
my $q = new CGI;
|
|
|
|
if (! grep (/^state$/, $q->param))
|
|
{
|
|
showInitial ($q, '');
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "help")
|
|
{
|
|
showHelp ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "showGroup")
|
|
{
|
|
showGroup ($q, '');
|
|
}
|
|
elsif ($q->param ('state') eq "performGroup")
|
|
{
|
|
performGroup ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "edit")
|
|
{
|
|
showEdit ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "save")
|
|
{
|
|
performSave ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "delete")
|
|
{
|
|
performDelete ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "deleteSingle")
|
|
{
|
|
performDeleteSingle ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "showhide")
|
|
{
|
|
performShowHide ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "globalSave")
|
|
{
|
|
performGlobalSave ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "enableProc")
|
|
{
|
|
showEnableProc ($q, '', '');
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "globalEnableProc")
|
|
{
|
|
showGlobalEnable ($q, '');
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "performEnableProc")
|
|
{
|
|
performEnableProc ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "advmodifyRule")
|
|
{
|
|
showAdvancedRuleEdit ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "saveRule")
|
|
{
|
|
performSaveRule ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "deletelog")
|
|
{
|
|
performDeletelog ($q);
|
|
}
|
|
|
|
elsif ($q->param ('state') eq "viewlog")
|
|
{
|
|
performViewlog ($q);
|
|
}
|
|
|
|
else
|
|
{
|
|
esmith::cgi::genStateError ($q, \%conf);
|
|
}
|
|
|
|
exit (0);
|
|
|
|
#-----------------------------------
|
|
# and display the appropriate form
|
|
#-----------------------------------
|
|
|
|
sub showInitial ($$)
|
|
{
|
|
my ($q, $msg) = @_;
|
|
|
|
if ($msg eq '')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Email Management.');
|
|
}
|
|
else
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Email Management.');
|
|
|
|
print $q->h4 ('Operation status report');
|
|
print $q->p ($msg);
|
|
print $q->hr;
|
|
}
|
|
|
|
unless (( -e "/etc/e-smith/web/functions/userpanel-vacation" ) &&
|
|
( -e "/etc/e-smith/web/functions/userpanel-mailsort" ))
|
|
{
|
|
print $q->p ('Extra functions are available, see https://wiki.koozali.org<br>
|
|
yum install smeserver-mailsorting smeserver-vacation');
|
|
}
|
|
|
|
|
|
#------------------------------------------------------------
|
|
# Global changes
|
|
#------------------------------------------------------------
|
|
|
|
print $q->h4 ('Global.');
|
|
|
|
my $FilterType = db_get_prop(\%conf, 'qmail', "FilterType") || '';
|
|
if ($FilterType eq 'maildrop')
|
|
{
|
|
print $q->p (esmith::cgi::genSmallRedCell ($q, 'Mail is being Sorted with Maildrop.'));
|
|
}
|
|
if ($FilterType eq 'procmail')
|
|
{
|
|
print $q->p (esmith::cgi::genSmallRedCell ($q, "Mail is being Sorted with Procmail.<p>"));
|
|
}
|
|
|
|
if ( -e "/usr/share/zarafa/VERSION" )
|
|
{
|
|
my $Gzar = db_get_prop(\%conf, 'zarafa-server', "GlobalForward") || '';
|
|
if ($Gzar eq 'enabled')
|
|
{ print $q->p (esmith::cgi::genSmallRedCell ($q, "Mail is being delivered globally to Zarafa.<p>")); }
|
|
else
|
|
{ print $q->p (esmith::cgi::genSmallRedCell ($q, "Mail is being selectivly delivered to Zarafa.<p>")); }
|
|
}
|
|
|
|
print $q->p ($q->td ($q->a ({href => $q->url (-absolute => 1) .
|
|
"?state=globalEnableProc"}, 'Modify'), " global mailfiltering rules and system settings.<p>"));
|
|
|
|
#------------------------------------------------------------
|
|
# accounts and user names
|
|
#------------------------------------------------------------
|
|
print $q->h4 ('Individual accounts.');
|
|
|
|
my @userAccounts = ();
|
|
foreach (sort keys %accounts)
|
|
{
|
|
push (@userAccounts, $_)
|
|
if (db_get_type(\%accounts, $_) eq "user");
|
|
}
|
|
|
|
my @Pseudonyms = ();
|
|
foreach (sort keys %accounts)
|
|
{
|
|
push (@Pseudonyms, $_)
|
|
if (db_get_type(\%accounts, $_) eq "pseudonym");
|
|
}
|
|
|
|
my $numAccts = @userAccounts +1;
|
|
if ($numAccts == 0)
|
|
{
|
|
print $q->h4 ('There are no user accounts in the system.');
|
|
}
|
|
else
|
|
{
|
|
print $q->p ('Review and modify a user\'s email delivery settings below.<br>
|
|
Details in the Help link below');
|
|
|
|
my $showPseudonym = db_get(\%processmail, 'showPseudonym') || 'no';
|
|
if ($showPseudonym eq 'yes')
|
|
{
|
|
print $q->Tr ($q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=showhide"},
|
|
'Hide'),
|
|
"the . and _ Pseudonyms.<p>"));
|
|
}
|
|
else
|
|
{
|
|
print $q->Tr ($q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=showhide&action=yes"},
|
|
'Show'),
|
|
"the . and _ Pseudonyms.<p> "));
|
|
}
|
|
|
|
print "<table border=1 cellspacing=1 cellpadding=4>";
|
|
|
|
print $q->Tr (esmith::cgi::genSmallCell ($q, $q->b ('Account')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('Name')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('Pseudonyms')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('delivery')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('forwarding')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('options')));
|
|
|
|
my $acct = '';
|
|
foreach $acct ('admin', @userAccounts)
|
|
{
|
|
my $EmailForward = db_get_prop(\%accounts, $acct, "EmailForward") || '';
|
|
my $ForwardAddress = db_get_prop(\%accounts, $acct, "ForwardAddress") || '';
|
|
my $fname = db_get_prop(\%accounts, $acct, "FirstName");
|
|
my $lname = db_get_prop(\%accounts, $acct, "LastName");
|
|
my $fullname = "$fname $lname";
|
|
my $userpath = ($acct eq 'admin')? "": "files/users/$acct";
|
|
|
|
#clean display
|
|
if ($EmailForward eq 'local')
|
|
{
|
|
$ForwardAddress = '';
|
|
}
|
|
|
|
#block external mail to this user
|
|
my $Visible ='';
|
|
if (defined(db_get_prop(\%accounts, $acct, "Visible")))
|
|
{
|
|
$Visible = db_get_prop(\%accounts, $acct, "Visible") || '';
|
|
if ($Visible ne 'internal') { $Visible = '';}
|
|
}
|
|
|
|
#mailfilter, bypass procmail/maildrop
|
|
my $MailFilter ='';
|
|
if (defined(db_get_prop(\%accounts, $acct, "MailFilter")))
|
|
{
|
|
$MailFilter = db_get_prop(\%accounts, $acct, "MailFilter") || '';
|
|
if ($MailFilter ne 'bypass') { $MailFilter = '';}
|
|
}
|
|
|
|
#vacation
|
|
my $vac ='';
|
|
if (defined(db_get_prop(\%accounts, $acct, "EmailVacation")))
|
|
{
|
|
$vac = db_get_prop(\%accounts, $acct, "EmailVacation") || '';
|
|
if ($vac eq 'yes') { $vac = 'vacation';}
|
|
if ($vac eq 'no') { $vac = '';}
|
|
}
|
|
|
|
#zarafa
|
|
my $zar ='';
|
|
my $Gzar = db_get_prop(\%conf, 'zarafa-server', "GlobalForward") || '';
|
|
if ($Gzar ne 'enabled')
|
|
{
|
|
if (defined(db_get_prop(\%accounts, $acct, "zarafa")))
|
|
{
|
|
$zar = db_get_prop(\%accounts, $acct, "zarafa") || '';
|
|
if ($zar eq 'enabled') { $zar = 'zarafa';}
|
|
if ($zar eq 'disabled') { $zar = '';}
|
|
}
|
|
}
|
|
|
|
my $tmda ='';
|
|
if ( -e "/etc/e-smith/templates/etc/crontab/25tmda-daily")
|
|
{
|
|
if (defined(db_get_prop(\%accounts, $acct, "tmda")))
|
|
{
|
|
$tmda = db_get_prop(\%accounts, $acct, "tmda") || '';
|
|
if ($tmda eq "on")
|
|
{
|
|
if (-e "/home/e-smith/$userpath/.tmda/config")
|
|
{
|
|
$tmda = 'tmda';
|
|
}
|
|
elsif (-e "/home/e-smith/$userpath/TMDA_restore.tgz")
|
|
{
|
|
$tmda = 'tmda!';
|
|
}
|
|
else
|
|
{
|
|
$tmda = 'tmda-';
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (-e "/home/e-smith/$userpath/.tmda/config")
|
|
{
|
|
$tmda = 'tmda*';
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (-e "/home/e-smith/$userpath/.tmda/config")
|
|
{
|
|
$tmda = 'tmda*';
|
|
}
|
|
}
|
|
if ($tmda eq 'off') { $tmda = '';}
|
|
}
|
|
|
|
#options
|
|
my $options = "$vac $Visible $MailFilter $tmda $zar";
|
|
|
|
#Pseudonyms
|
|
my @nyms = ();
|
|
foreach (@Pseudonyms)
|
|
{
|
|
my $Account = db_get_prop(\%accounts, $_, "Account");
|
|
if ($acct eq $Account)
|
|
{
|
|
if ($showPseudonym eq 'yes')
|
|
{
|
|
push (@nyms, $_);
|
|
push (@nyms, '<br>');
|
|
}
|
|
else
|
|
{
|
|
#lowercase
|
|
$fname =~ s/([^\W0-9_])/\l$1/g;
|
|
$lname =~ s/([^\W0-9_])/\l$1/g;
|
|
|
|
if ($_ ne $fname.".".$lname)
|
|
{
|
|
if ($_ ne $fname."_".$lname)
|
|
{
|
|
push (@nyms, $_);
|
|
push (@nyms, '<br>');
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if ($acct eq 'admin')
|
|
{
|
|
$ForwardAddress = db_get_prop(\%accounts, 'admin', 'ForwardAddress') || '';
|
|
if ($ForwardAddress ne '')
|
|
{
|
|
$EmailForward = 'forward' || '';
|
|
}
|
|
}
|
|
|
|
print $q->Tr ( esmith::cgi::genSmallCell ($q, $q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=enableProc&acct=" . $acct}, $acct)),
|
|
esmith::cgi::genSmallCell ($q, $fullname),
|
|
esmith::cgi::genSmallCell ($q, "@nyms"),
|
|
esmith::cgi::genSmallCell ($q, $EmailForward),
|
|
esmith::cgi::genSmallCell ($q, $ForwardAddress),
|
|
esmith::cgi::genSmallCell ($q, $options));
|
|
}#end of users
|
|
|
|
print '</table>';
|
|
|
|
}#end >0 users
|
|
|
|
#------------------------------------------------------------
|
|
# domains
|
|
#------------------------------------------------------------
|
|
|
|
|
|
if ( -e "/etc/e-smith/web/functions/dungog-domains")
|
|
{
|
|
my @domain = ();
|
|
foreach (sort keys %domains)
|
|
{
|
|
push (@domain, $_) if (db_get_type(\%domains, $_) eq "domain");
|
|
}
|
|
|
|
print $q->h4 ('Domains.');
|
|
|
|
print $q->p ('Modify with dungog-domain <a href="smeserver-domains">here</a>');
|
|
|
|
print "<table border=1 cellspacing=1 cellpadding=4>";
|
|
|
|
print $q->Tr (esmith::cgi::genSmallCell ($q, $q->b ('Domain')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('Description')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('Delegated to')));
|
|
|
|
foreach ( sort @domain)
|
|
{
|
|
my $Description = db_get_prop(\%domains, $_, "Description") || '';
|
|
my $MailServer = db_get_prop(\%domains, $_, "MailServer") || '';
|
|
|
|
print $q->Tr (esmith::cgi::genSmallCell ($q, $_),
|
|
esmith::cgi::genSmallCell ($q, $Description),
|
|
esmith::cgi::genSmallCell ($q, $MailServer));
|
|
}
|
|
print '</table>';
|
|
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# groups
|
|
#------------------------------------------------------------
|
|
|
|
my @groups = ();
|
|
foreach (sort keys %accounts)
|
|
{
|
|
push (@groups, $_) if (db_get_type(\%accounts, $_) eq "group");
|
|
}
|
|
|
|
print $q->h4 ('Groups.');
|
|
|
|
my $numgroups = @groups;
|
|
if ($numgroups == 0)
|
|
{
|
|
print $q->h4 ('There are no groups in the system.');
|
|
}
|
|
else
|
|
{
|
|
print $q->p ('Modify group email delivery');
|
|
|
|
print "<table border=1 cellspacing=1 cellpadding=4>";
|
|
|
|
print $q->Tr (esmith::cgi::genSmallCell ($q, $q->b ('Group')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('Description')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('Visible')));
|
|
|
|
foreach ( sort @groups)
|
|
{
|
|
my $Description = db_get_prop(\%accounts, $_, "Description") || '';
|
|
my $Visible = db_get_prop(\%accounts, $_, "Visible") || 'external';
|
|
|
|
print $q->Tr (esmith::cgi::genSmallCell ($q, $q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=showGroup&group=" . $_}, $_)),
|
|
esmith::cgi::genSmallCell ($q, $Description),
|
|
esmith::cgi::genSmallCell ($q, $Visible));
|
|
}
|
|
|
|
print '</table>';
|
|
}
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print '</FONT>';
|
|
print '</DIV>';
|
|
print $q->end_html;
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# show modify or create global rule
|
|
#------------------------------------------------------------
|
|
|
|
sub showEdit ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $pmRule = $q->param ('acct');
|
|
my $oldpmRule = "$pmRule";
|
|
|
|
if ($pmRule eq 'new')
|
|
{
|
|
my $random = int(rand(999999));
|
|
$pmRule = $random;
|
|
}
|
|
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Add or modify a Global procmail rule.');
|
|
|
|
print $q->startform (-method => 'POST',
|
|
-action => $q->url (-absolute => 1));
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4},
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ('Select the part of the email to be tested. The criterion
|
|
could be part of an email address, header or subject, or the email size.
|
|
The second test is optional.')),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "First Test",
|
|
$q->popup_menu (-name => 'basis',
|
|
-values => ['Subject','TO_','From','headers','<','>'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "basis") || '' ,
|
|
-labels => \%Label)),
|
|
|
|
esmith::cgi::genNameValueRow ($q,"First Criterion",
|
|
"criterion",
|
|
db_get_prop(\%processmail, $pmRule, "criterion") || '',),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Second Test",
|
|
$q->popup_menu (-name => 'basis2',
|
|
-values => ['','Subject','TO_','From','headers'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "basis2") || '' ,
|
|
-labels => \%Label)),
|
|
|
|
esmith::cgi::genNameValueRow ($q,"Second Criterion",
|
|
"criterion2",
|
|
db_get_prop(\%processmail, $pmRule, "criterion2") || '',),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ('What you are going to do with the message.')),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Action",
|
|
$q->popup_menu (-name => 'action',
|
|
-values => ['sort','forward','delete'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "action") || '' ,
|
|
-labels => \%Labels)),
|
|
|
|
esmith::cgi::genNameValueRow ($q,"Folder or address",
|
|
"deliver",
|
|
db_get_prop(\%processmail, $pmRule, "deliver") || ''),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->b ('Optional copy')),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ("Keep a copy of the email, sort it, or send it to somewhere else.")),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Copy",
|
|
$q->popup_menu (-name => 'copy',
|
|
-values => ['no','yes'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "copy") || '' )),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Action of copy",
|
|
$q->popup_menu (-name => 'action2',
|
|
-values => ['','inbox','sort','forward'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "action2") || '',
|
|
-labels => \%Labels)),
|
|
|
|
esmith::cgi::genNameValueRow ($q, "Folder or address",
|
|
"deliver2",
|
|
db_get_prop(\%processmail, $pmRule, "deliver2") || ''),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->b ('Priority')),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ("Change the order ".
|
|
"in which global rules are evaluated by altering this value. ".
|
|
"Low numbers go first and values must be unique or you ".
|
|
"overwrite the other rule with that value.")),
|
|
|
|
esmith::cgi::genNameValueRow ($q, "Order of rule execution",
|
|
"pmRule",
|
|
"$pmRule",));
|
|
|
|
print $q->p (esmith::cgi::genButtonRow ($q,
|
|
$q->submit (-name => 'action',
|
|
-value => 'Save')));
|
|
|
|
print $q->hidden (-name => 'state', -override => 1, -default => 'save');
|
|
print $q->hidden (-name => 'pmRule', -override => 1, -default => $pmRule);
|
|
print $q->hidden (-name => 'oldpmRule', -override => 1, -default => $oldpmRule);
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "dungog.net/wiki",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print '</FONT>';
|
|
print '</DIV>';
|
|
print $q->end_html;
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# show qmail settings
|
|
#------------------------------------------------------------
|
|
|
|
sub showGroup ($$)
|
|
{
|
|
my ($q) = @_;
|
|
my $group = $q->param ('group');
|
|
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, 'Group mail Settings');
|
|
|
|
print $q->startform (-method => 'POST',
|
|
-action => $q->url (-absolute => 1));
|
|
|
|
print $q->h4 ("Group Mail settings - $group");
|
|
|
|
print $q->p ("Disable external reciept of mail, ie. for the address $group, not the members of the group");
|
|
|
|
my $Visible = db_get_prop(\%accounts, $group, "Visible") || '';
|
|
print $q->p ("Group Email Delivery:",
|
|
$q->popup_menu (-name => 'Visible',
|
|
-values => ['external', 'internal'],
|
|
-default => $Visible));
|
|
|
|
print $q->p (esmith::cgi::genButtonRow ($q,
|
|
$q->submit (-name => 'action',
|
|
-value => 'Save')));
|
|
|
|
print $q->hidden (-name => 'state', -override => 1, -default => 'performGroup');
|
|
print $q->hidden (-name => 'group', -override => 1, -default => $group);
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print '</FONT>';
|
|
print '</DIV>';
|
|
print $q->end_html;
|
|
}
|
|
|
|
sub performGroup ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $group = $q->param ('group');
|
|
my $Visible = $q->param ('Visible');
|
|
|
|
if ($Visible eq 'internal')
|
|
{
|
|
db_set_prop(\%accounts, $group, "Visible", 'internal');
|
|
}else{
|
|
db_delete_prop(\%accounts, $group, "Visible");
|
|
}
|
|
|
|
system ("/sbin/e-smith/signal-event", "email-update") == 0
|
|
or die ("Error occurred while globally updating.\n");
|
|
|
|
showInitial ($q, "settings saved.");
|
|
}
|
|
#------------------------------------------------------------
|
|
# show global update form
|
|
#------------------------------------------------------------
|
|
|
|
sub showGlobalEnable ($$)
|
|
{
|
|
my ($q) = @_;
|
|
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, 'Global Settings');
|
|
|
|
print $q->startform (-method => 'POST',
|
|
-action => $q->url (-absolute => 1));
|
|
|
|
print $q->h4 ('Zarafa');
|
|
|
|
# test if zarafa is installed
|
|
if ( -e "/usr/share/zarafa/VERSION" )
|
|
{
|
|
print $q->p ('Zarafa is an exchange replacment, see contribs.org/zarafa');
|
|
|
|
my $GlobalForward = db_get_prop(\%conf, 'zarafa-server', "GlobalForward") || 'disabled';
|
|
print $q->p ("Zarafa Global delivery",
|
|
$q->popup_menu (-name => 'GlobalForward',
|
|
-values => ['disabled','enabled'],
|
|
-default => $GlobalForward));
|
|
}
|
|
|
|
print $q->h4 ('Email Sorting');
|
|
|
|
# test if Mailfilter is installed
|
|
if ( -e "/etc/e-smith/web/functions/userpanel-mailsort" )
|
|
{
|
|
print $q->p ('Make a system wide change, enable procmail or maildrop,
|
|
Note, procmail and maildrop will deliver mail according to
|
|
the local, forward or both settings after any sorting');
|
|
|
|
my $FilterType = db_get_prop(\%conf, 'qmail', "FilterType") || '';
|
|
print $q->p ("Global Email Delivery",
|
|
$q->popup_menu (-name => 'FilterType',
|
|
-values => ['default', 'procmail', 'maildrop'],
|
|
-default => $FilterType));
|
|
|
|
print $q->h4 ('Global mail rules');
|
|
|
|
print $q->p ("Any rules you create will be placed before the users rules. ");
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4});
|
|
|
|
my @pmRules = ();
|
|
foreach (sort keys %processmail)
|
|
{
|
|
push (@pmRules, $_)
|
|
if (db_get_type(\%processmail, $_) eq "pmGlobalRule");
|
|
}
|
|
|
|
#hide table if you have no rules
|
|
my $pmRules = @pmRules || 'no rules';
|
|
if ($pmRules eq 'no rules')
|
|
{
|
|
print $q->p ($q->a ({href => $q->url (-absolute => 1) . "?state=edit&acct=new"},
|
|
'Click here'),
|
|
'to define your first Global procmail rule.');
|
|
}
|
|
else
|
|
{
|
|
print $q->p ($q->a ({href => $q->url (-absolute => 1) . "?state=edit&acct=new"},
|
|
'Click here'),
|
|
"to add another procmail rule. You currently have $pmRules rules.");
|
|
|
|
print "<table border=1 cellspacing=1 cellpadding=4>";
|
|
|
|
#header
|
|
print $q->Tr (esmith::cgi::genSmallCell ($q, $q->b ('basis')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('criterion')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('basis2')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('criterion2')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('destination')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('copy')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('copy to')),
|
|
$q->td (' '),
|
|
$q->td (' '));
|
|
|
|
#held in /home/e-smith/db/processmail
|
|
my $pmRule;
|
|
foreach $pmRule (sort {$a <=> $b} @pmRules)
|
|
{
|
|
my $basis = db_get_prop(\%processmail, $pmRule, "basis") || '';
|
|
my $criterion = db_get_prop(\%processmail, $pmRule, "criterion") || '';
|
|
my $basis2 = db_get_prop(\%processmail, $pmRule, "basis2") || '';
|
|
my $criterion2 = db_get_prop(\%processmail, $pmRule, "criterion2") || '';
|
|
my $action = db_get_prop(\%processmail, $pmRule, "action") || '';
|
|
my $deliver = db_get_prop(\%processmail, $pmRule, "deliver") || '';
|
|
my $copy = db_get_prop(\%processmail, $pmRule, "copy") || '';
|
|
my $deliver2 = db_get_prop(\%processmail, $pmRule, "deliver2") || '';
|
|
my $action2 = db_get_prop(\%processmail, $pmRule, "action2") || '';
|
|
|
|
if ($copy eq 'yes' && $action2 eq 'inbox')
|
|
{
|
|
$copy = 'yes*';
|
|
}
|
|
|
|
foreach ($basis, $basis2)
|
|
{
|
|
if ($_ eq 'TO_')
|
|
{
|
|
$_ = 'To';
|
|
}
|
|
|
|
if ($_ eq '>')
|
|
{
|
|
$_ = 'greater than';
|
|
}
|
|
|
|
if ($_ eq '<')
|
|
{
|
|
$_ = 'less than';
|
|
}
|
|
}
|
|
|
|
if ($action eq 'delete')
|
|
{
|
|
print $q->Tr ( #esmith::cgi::genSmallCell ($q, $pmRule),
|
|
esmith::cgi::genSmallCell ($q, $basis),
|
|
esmith::cgi::genSmallCell ($q, $criterion),
|
|
esmith::cgi::genSmallCell ($q, $basis2),
|
|
esmith::cgi::genSmallCell ($q, $criterion2),
|
|
esmith::cgi::genSmallRedCell ($q, 'deleted'),
|
|
esmith::cgi::genSmallCell ($q, $copy),
|
|
esmith::cgi::genSmallCell ($q, $deliver2),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=edit&acct="
|
|
. $pmRule}, 'Modify...')),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=delete&acct="
|
|
. $pmRule}, 'Remove...')));
|
|
}
|
|
else
|
|
{
|
|
print $q->Tr ( #esmith::cgi::genSmallCell ($q, $pmRule),
|
|
esmith::cgi::genSmallCell ($q, $basis),
|
|
esmith::cgi::genSmallCell ($q, $criterion),
|
|
esmith::cgi::genSmallCell ($q, $basis2),
|
|
esmith::cgi::genSmallCell ($q, $criterion2),
|
|
esmith::cgi::genSmallCell ($q, $deliver),
|
|
esmith::cgi::genSmallCell ($q, $copy),
|
|
esmith::cgi::genSmallCell ($q, $deliver2),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=edit&acct="
|
|
. $pmRule}, 'Modify...')),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=delete&acct="
|
|
. $pmRule}, 'Remove...')));
|
|
}
|
|
}
|
|
}
|
|
|
|
print '</table>';
|
|
}
|
|
else
|
|
{
|
|
print $q->p ('Maildrop and procmail can be enabled more easily with smesmerver-mailfiltering
|
|
see https://wiki.koozali.org, yum install smesmerver-mailfiltering');
|
|
}
|
|
|
|
print $q->h4 ('Email/qmail settings');
|
|
|
|
print $q->p ('Enable archiving of email to and from the server to the user maillog [which must exist],<br>
|
|
cc adds a header for legal reasons, bcc does not');
|
|
|
|
print $q->p ("qpsmtpd Log Level:",
|
|
$q->popup_menu (-name => 'LogLevel',
|
|
-values => ['6', '8'],
|
|
-default => db_get_prop(\%conf, 'qpsmtpd', "LogLevel")));
|
|
|
|
print $q->p ("Double Bounces:",
|
|
$q->popup_menu (-name => 'DoubleBounceTo',
|
|
-values => ['postmaster','devnull'],
|
|
-default => db_get_prop(\%conf, 'qmail', "DoubleBounceTo")));
|
|
|
|
print $q->p ("Archive Email:",
|
|
$q->popup_menu (-name => 'BccMode',
|
|
-values => ['off', 'cc', 'bcc'],
|
|
-default => db_get_prop(\%conf, 'qpsmtpd', "BccMode")));
|
|
|
|
print $q->p ("RBL Blacklist:",
|
|
$q->popup_menu (-name => 'DNSBL',
|
|
-values => ['disabled', 'enabled'],
|
|
-default => db_get_prop(\%conf, 'qpsmtpd', "DNSBL")));
|
|
|
|
print $q->p (esmith::cgi::genNameValueRow ($q,
|
|
"RBL Blacklists",
|
|
"RBLList",
|
|
db_get_prop(\%conf, 'qpsmtpd', "RBLList")));
|
|
|
|
print $q->p ("SBL Blacklist:",
|
|
$q->popup_menu (-name => 'RHSBL',
|
|
-values => ['disabled', 'enabled'],
|
|
-default => db_get_prop(\%conf, 'qpsmtpd', "RHSBL")));
|
|
|
|
print $q->p (esmith::cgi::genNameValueRow ($q,
|
|
"SBL Blacklists",
|
|
"SBLList",
|
|
db_get_prop(\%conf, 'qpsmtpd', "SBLList")));
|
|
|
|
print $q->p (esmith::cgi::genNameValueRow ($q,
|
|
"Max size for attachment, in bytes",
|
|
"MaxMessageSize",
|
|
db_get_prop(\%conf, 'qmail', "MaxMessageSize")));
|
|
|
|
print $q->p (esmith::cgi::genNameValueRow ($q,
|
|
"Max size that is virus scanned, in bytes",
|
|
"MaxScannerSize",
|
|
db_get_prop(\%conf, 'qpsmtpd', "MaxScannerSize")));
|
|
|
|
print $q->p (esmith::cgi::genButtonRow ($q,
|
|
$q->submit (-name => 'action',
|
|
-value => 'Save')));
|
|
|
|
print $q->hidden (-name => 'state',
|
|
-override => 1,
|
|
-default => 'globalSave');
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print '</FONT>';
|
|
print '</DIV>';
|
|
print $q->end_html;
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# save procmail rule to database
|
|
#------------------------------------------------------------
|
|
|
|
sub performSave ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $oldpmRule = $q->param ('oldpmRule') || '';
|
|
my $pmRule = $q->param ('pmRule') || '';
|
|
my $basis = $q->param ('basis') || '';
|
|
my $criterion = $q->param ('criterion') || '';
|
|
my $basis2 = $q->param ('basis2') || '';
|
|
my $criterion2 = $q->param ('criterion2') || '';
|
|
my $deliver = $q->param ('deliver') || '';
|
|
my $deliver2 = $q->param ('deliver2') || '';
|
|
my $copy = $q->param ('copy') || '';
|
|
my $action = $q->param ('action') || '';
|
|
my $action2 = $q->param ('action2') || '';
|
|
my $changes = $q->param ('changes') || '';
|
|
|
|
if ($deliver eq '' && $action eq 'forward')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: in destination.");
|
|
esmith::cgi::genResult ($q, "Error: You failed to enter a destination address");
|
|
return;
|
|
}
|
|
|
|
if ($deliver2 eq '' && $copy eq 'yes' && $action2 eq 'forward')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: in destination.");
|
|
esmith::cgi::genResult ($q, "Error: You failed to enter a destination address for your copy");
|
|
return;
|
|
}
|
|
|
|
if ($criterion eq '')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: in criterion.");
|
|
esmith::cgi::genResult ($q, "Error: you failed to enter a criterion value");
|
|
return;
|
|
}
|
|
|
|
if ($action ne 'delete' && $deliver eq '' )
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: in destination.");
|
|
esmith::cgi::genResult ($q, "Error: you failed to enter a destination value");
|
|
return;
|
|
}
|
|
|
|
if ($copy eq 'no')
|
|
{
|
|
$deliver2 = '';
|
|
$action2 = '';
|
|
}
|
|
|
|
db_delete(\%processmail, $oldpmRule);
|
|
db_set(\%processmail, $pmRule, 'pmGlobalRule');
|
|
db_set_prop(\%processmail, $pmRule, "basis", $basis);
|
|
db_set_prop(\%processmail, $pmRule, "criterion", $criterion);
|
|
db_set_prop(\%processmail, $pmRule, "basis2", $basis2);
|
|
db_set_prop(\%processmail, $pmRule, "criterion2", $criterion2);
|
|
db_set_prop(\%processmail, $pmRule, "deliver", $deliver);
|
|
db_set_prop(\%processmail, $pmRule, "deliver2", $deliver2);
|
|
db_set_prop(\%processmail, $pmRule, "action", $action);
|
|
db_set_prop(\%processmail, $pmRule, "action2", $action2);
|
|
db_set_prop(\%processmail, $pmRule, "copy", $copy);
|
|
|
|
system ("/sbin/e-smith/signal-event", "mailsorting-conf") == 0
|
|
or die ("Error occurred while globally updating mailfiltering.\n");
|
|
|
|
showGlobalEnable ($q, "Rules altered.");
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# delete rule
|
|
#------------------------------------------------------------
|
|
|
|
sub performDelete ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $acct = $q->param ('acct');
|
|
|
|
db_delete(\%processmail, "$acct");
|
|
|
|
system ("/sbin/e-smith/signal-event", "mailsorting-conf") == 0
|
|
or die ("Error occurred while globally updating mailfiltering.\n");
|
|
|
|
showGlobalEnable ($q, "Removed rule.");
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# show or hide pseudonyms
|
|
#------------------------------------------------------------
|
|
|
|
sub performShowHide ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $action = $q->param ('action');
|
|
|
|
if ($action eq 'yes')
|
|
{ db_set(\%processmail, 'showPseudonym', 'yes'); }
|
|
else
|
|
{ db_delete(\%processmail, "showPseudonym"); }
|
|
|
|
showInitial ($q, "");
|
|
}
|
|
|
|
|
|
#------------------------------------------------------------
|
|
# global update of all users .procmailrc/.qmail/.mailfilter files
|
|
#------------------------------------------------------------
|
|
|
|
sub performGlobalSave ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $FilterType = $q->param ('FilterType') || 'default';
|
|
my $GlobalForward = $q->param ('GlobalForward') || '';
|
|
|
|
if (($FilterType eq 'procmail') || ($FilterType eq 'maildrop'))
|
|
{ db_set_prop(\%conf, 'qmail', 'FilterType', $FilterType); }
|
|
else
|
|
{ db_delete_prop(\%conf, 'qmail', 'FilterType'); }
|
|
|
|
if ($GlobalForward eq 'enabled')
|
|
{ db_set_prop(\%conf, 'zarafa-server', 'GlobalForward', 'enabled'); }
|
|
else
|
|
{ db_delete_prop(\%conf, 'zarafa-server', 'GlobalForward'); }
|
|
|
|
my $BccMode = $q->param ('BccMode') || '';
|
|
my $DNSBL = $q->param ('DNSBL') || '';
|
|
my $RHSBL = $q->param ('RHSBL') || '';
|
|
my $DoubleBounceTo = $q->param ('DoubleBounceTo') || '';
|
|
my $LogLevel = $q->param ('LogLevel') || '';
|
|
my $RBLList = $q->param ('RBLList') || '';
|
|
my $SBLList = $q->param ('SBLList') || '';
|
|
my $MaxScannerSize = $q->param ('MaxScannerSize') || '';
|
|
my $MaxMessageSize = $q->param ('MaxMessageSize') || '';
|
|
|
|
if ($BccMode eq 'cc' || $BccMode eq 'bcc')
|
|
{ db_set_prop(\%conf, 'qpsmtpd', 'Bcc', 'enabled');
|
|
db_set_prop(\%conf, 'qpsmtpd', 'BccMode', $BccMode); }
|
|
else
|
|
{ db_set_prop(\%conf, 'qpsmtpd', 'Bcc', 'disabled');
|
|
db_set_prop(\%conf, 'qpsmtpd', 'BccMode', $BccMode); }
|
|
|
|
if ($DoubleBounceTo eq 'devnull')
|
|
{ db_set_prop(\%conf, 'qmail', 'DoubleBounceTo', $DoubleBounceTo); }
|
|
else
|
|
{ db_delete_prop(\%conf, 'qmail', 'DoubleBounceTo'); }
|
|
|
|
db_set_prop(\%conf, 'qmail', 'MaxMessageSize', $MaxMessageSize);
|
|
db_set_prop(\%conf, 'qpsmtpd', 'MaxScannerSize', $MaxScannerSize);
|
|
db_set_prop(\%conf, 'qpsmtpd', 'DNSBL', $DNSBL);
|
|
db_set_prop(\%conf, 'qpsmtpd', 'RHSBL', $RHSBL);
|
|
db_set_prop(\%conf, 'qpsmtpd', 'LogLevel', $LogLevel);
|
|
db_set_prop(\%conf, 'qpsmtpd', 'RBLList', $RBLList);
|
|
db_set_prop(\%conf, 'qpsmtpd', 'SBLList', $SBLList);
|
|
|
|
#system ("/sbin/e-smith/signal-event", "mailsorting-conf") == 0
|
|
system ("/sbin/e-smith/signal-event", "email-update") == 0
|
|
or die ("Error occurred while signal-event email save.\n");
|
|
|
|
showInitial ($q, 'Setttings saved');
|
|
}
|
|
|
|
#------ SINGLE USER--------------------------------------
|
|
|
|
sub showEnableProc ($$$)
|
|
{
|
|
my ($q, $msg, $acctName) = @_;
|
|
my $FilterType = db_get_prop(\%conf, 'qmail', "FilterType") || '';
|
|
|
|
if ($msg eq '')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Single user setup');
|
|
}
|
|
else
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Single user setup');
|
|
|
|
print $q->h4 ('Operation status report');
|
|
print $q->p ($msg);
|
|
print $q->hr;
|
|
}
|
|
|
|
print $q->startform
|
|
(-method => 'POST', -action => $q->url (-absolute => 1));
|
|
|
|
#get username from param, acctName is from deleteSingle
|
|
my $acct = '';
|
|
if ($acctName eq '')
|
|
{
|
|
$acct = $q->param ('acct');
|
|
}
|
|
else
|
|
{
|
|
$acct = $acctName;
|
|
}
|
|
|
|
if (db_get_type(\%accounts, $acct) eq "user" || $acct eq "admin")
|
|
{
|
|
my $name = db_get_prop(\%accounts, $acct, 'FirstName') . ' ' . db_get_prop(\%accounts, $acct, 'LastName');
|
|
my $userpath = ($acct eq 'admin')? "": "files/users/$acct";
|
|
|
|
print $q->p ('Email delivery for the user account "'
|
|
. $acct
|
|
. '" (user name "' . $name . '").');
|
|
|
|
print $q->h4 ("Email Delivery");
|
|
print $q->p ($q->a ({href => $q->url (-absolute => 1) . "?state=viewlog&file=.qmail&acct=$acct"},
|
|
'View'),
|
|
".qmail");
|
|
|
|
my %emailLabels = ('local' => 'Deliver email locally',
|
|
'forward' => 'Forward to address below',
|
|
'both' => 'Both deliver locally and forward');
|
|
|
|
my %visLabels = ('internal' => 'Internally visible only',
|
|
'external' => 'Unrestricted');
|
|
|
|
print $q->p (esmith::cgi::genWidgetRow ($q, "Email Delivery",
|
|
$q->popup_menu (-name => 'emailForward',
|
|
-values => ['local', 'forward', 'both'],
|
|
-default => db_get_prop(\%accounts, $acct, "EmailForward") || 'local',
|
|
-labels => \%emailLabels )));
|
|
|
|
|
|
my $forwardAddress = db_get_prop(\%accounts, $acct, 'ForwardAddress') || '';
|
|
print $q->p (esmith::cgi::genNameValueRow ($q,
|
|
"Forwarding address",
|
|
"forwardAddress",
|
|
$forwardAddress));
|
|
|
|
my $Visible = db_get_prop(\%accounts, $acct, "Visible") || '';
|
|
print $q->p (esmith::cgi::genWidgetRow ($q, "Visible ",
|
|
$q->popup_menu (-name => 'Visible',
|
|
-values => ['external', 'internal'],
|
|
-default => $Visible,
|
|
-labels => \%visLabels )));
|
|
|
|
|
|
########### test if zarafa is installed ####################
|
|
if ( -e "/usr/share/zarafa/VERSION" )
|
|
{
|
|
my %zarLabels = ('enabled' => 'Enabled',
|
|
'disabled' => 'Disabled',
|
|
'Genabled' => 'Zarafa is Globally enabled');
|
|
|
|
my $zar = db_get_prop(\%accounts, $acct, "zarafa") || '';
|
|
my $Gzar = db_get_prop(\%conf, 'zarafa-server', "GlobalForward") || '';
|
|
if ($Gzar eq 'enabled')
|
|
{ $zar = 'Genabled'; }
|
|
print $q->p (esmith::cgi::genWidgetRow ($q, "Deliver to Zarafa",
|
|
$q->popup_menu (-name => 'zarafa',
|
|
-values => ['enabled', 'disabled', 'Genabled'],
|
|
-default => $zar,
|
|
-labels => \%zarLabels )));
|
|
}
|
|
|
|
############# tmda ####################
|
|
# test if tmda is installed
|
|
if ( -e "/etc/e-smith/templates/etc/crontab/25tmda-daily")
|
|
{
|
|
my $tmda = defined(db_get_prop(\%accounts, $acct, "tmda")) ?
|
|
db_get_prop(\%accounts, $acct, "tmda") : '';
|
|
|
|
my $status = '';
|
|
unless (-e "/home/e-smith/$userpath/.tmda/config")
|
|
{
|
|
$status = 'NOT';
|
|
}
|
|
|
|
print $q->h4 ('TMDA settings');
|
|
|
|
print $q->p ('Enabling TMDA is a two stage process,<br>
|
|
Each user enables and configures TMDA at domainname/tmda<br>'.
|
|
"$acct has $status enabled tmda at /tmda<p>".
|
|
|
|
'Then set TMDA as enabled in the SME Accounts database<br>
|
|
this sets the users .qmail file up the SME way.<br>
|
|
the user can also do this himself at /user > tmda settings');
|
|
|
|
print $q->p ("TMDA Delivery:",
|
|
$q->popup_menu (-name => 'tmda',
|
|
-values => ['off', 'on'],
|
|
-default => $tmda));
|
|
}
|
|
|
|
############# Mailfilter ####################
|
|
# test if Mailfilter is installed
|
|
print $q->h4 ('Mailsorting rules');
|
|
if ( -e "/etc/e-smith/web/functions/userpanel-mailsort" )
|
|
{
|
|
my %filterLabels = ('on' => "Adopt system default: $FilterType",
|
|
'bypass' => "Bypass $FilterType");
|
|
|
|
my $MailFilter = db_get_prop(\%accounts, $acct, "MailFilter") || 'on';
|
|
print $q->p (esmith::cgi::genWidgetRow ($q, "Mailfilter",
|
|
$q->popup_menu (-name => 'MailFilter',
|
|
-values => ['on', 'bypass'],
|
|
-default => $MailFilter,
|
|
-labels => \%filterLabels )));
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4});
|
|
|
|
#hide table if you have no rules
|
|
my @pmRules = ();
|
|
foreach (sort keys %processmail)
|
|
{
|
|
push (@pmRules, $_)
|
|
if (db_get_type(\%processmail, $_) eq "$acct");
|
|
}
|
|
|
|
my $pmRules = @pmRules || 'no rules';
|
|
if ($pmRules eq 'no rules')
|
|
{
|
|
print $q->p ($q->a ({href => $q->url (-absolute => 1) . "?state=advmodifyRule&acct=new&acctName=$acct"},
|
|
'Click here'),
|
|
'to define the first procmail rule.');
|
|
}
|
|
else
|
|
{
|
|
print $q->p ($q->a ({href => $q->url (-absolute => 1) . "?state=advmodifyRule&acct=new&acctName=$acct"},
|
|
'Click here'),
|
|
"to add another rule. You currently have $pmRules rules.");
|
|
|
|
print $q->p ;
|
|
|
|
print "<table border=1 cellspacing=1 cellpadding=4>";
|
|
|
|
#header
|
|
print $q->Tr ( #esmith::cgi::genSmallCell ($q, $q->b ('priority')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('basis')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('criterion')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('2nd basis')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('2nd criterion')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('destination')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('copy')),
|
|
esmith::cgi::genSmallCell ($q, $q->b ('copy to')),
|
|
$q->td (' '),
|
|
$q->td (' '));
|
|
|
|
my $pmRule;
|
|
foreach $pmRule (sort @pmRules)
|
|
{
|
|
my $basis = db_get_prop(\%processmail, $pmRule, "basis") || '';
|
|
my $criterion = db_get_prop(\%processmail, $pmRule, "criterion") || '';
|
|
my $basis2 = db_get_prop(\%processmail, $pmRule, "basis2") || '';
|
|
my $criterion2 = db_get_prop(\%processmail, $pmRule, "criterion2") || '';
|
|
my $action = db_get_prop(\%processmail, $pmRule, "action") || '';
|
|
my $deliver = db_get_prop(\%processmail, $pmRule, "deliver") || '';
|
|
my $copy = db_get_prop(\%processmail, $pmRule, "copy") || '';
|
|
my $deliver2 = db_get_prop(\%processmail, $pmRule, "deliver2") || '';
|
|
my $action2 = db_get_prop(\%processmail, $pmRule, "action2") || '';
|
|
|
|
foreach ($basis, $basis2)
|
|
{
|
|
if ($_ eq 'TO_')
|
|
{
|
|
$_ = 'Recipient';
|
|
}
|
|
|
|
if ($_ eq 'From')
|
|
{
|
|
$_ = 'Sender';
|
|
}
|
|
|
|
if ($_ eq '>')
|
|
{
|
|
$_ = 'greater than';
|
|
}
|
|
|
|
if ($_ eq '<')
|
|
{
|
|
$_ = 'less than';
|
|
}
|
|
}
|
|
|
|
if ($action eq 'delete')
|
|
{
|
|
print $q->Tr ( #esmith::cgi::genSmallCell ($q, $pmRule),
|
|
esmith::cgi::genSmallCell ($q, $basis),
|
|
esmith::cgi::genSmallCell ($q, $criterion),
|
|
esmith::cgi::genSmallCell ($q, $basis2),
|
|
esmith::cgi::genSmallCell ($q, $criterion2),
|
|
esmith::cgi::genSmallRedCell ($q, 'deleted'),
|
|
esmith::cgi::genSmallCell ($q, $copy),
|
|
esmith::cgi::genSmallCell ($q, $deliver2),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=advmodifyRule&acctName=$acct&acct="
|
|
. $pmRule}, 'Modify...')),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=deleteSingle&acctName=$acct&acct="
|
|
. $pmRule}, 'Remove...')));
|
|
}
|
|
else
|
|
{
|
|
print $q->Tr ( #esmith::cgi::genSmallCell ($q, $pmRule),
|
|
esmith::cgi::genSmallCell ($q, $basis),
|
|
esmith::cgi::genSmallCell ($q, $criterion),
|
|
esmith::cgi::genSmallCell ($q, $basis2),
|
|
esmith::cgi::genSmallCell ($q, $criterion2),
|
|
esmith::cgi::genSmallCell ($q, $deliver),
|
|
esmith::cgi::genSmallCell ($q, $copy),
|
|
esmith::cgi::genSmallCell ($q, $deliver2),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=advmodifyRule&acctName=$acct&acct="
|
|
. $pmRule}, 'Modify...')),
|
|
esmith::cgi::genSmallCell ($q,
|
|
$q->a ({href => $q->url (-absolute => 1)
|
|
. "?state=deleteSingle&acctName=$acct&acct="
|
|
. $pmRule}, 'Remove...')));
|
|
}
|
|
}
|
|
}
|
|
|
|
print '</table>';
|
|
print $q->table ({border => 0, cellspacing => 1, cellpadding => 4});
|
|
|
|
#mailfilter files
|
|
print $q->Tr ($q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=viewlog&file=.procmailrc&acct=$acct"},
|
|
'View'),
|
|
".procmailrc"),
|
|
|
|
$q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=viewlog&file=.mailfilter&acct=$acct"},
|
|
'View'),
|
|
".mailfilter [maildrop]"));
|
|
|
|
print $q->Tr ($q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=viewlog&file=procmail.log&acct=$acct"},
|
|
'View'),
|
|
"procmail.log"),
|
|
|
|
$q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=viewlog&file=mailfilter.log&acct=$acct"},
|
|
'View'),
|
|
"mailfilter.log"));
|
|
|
|
print $q->Tr ($q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=deletelog&file=procmail.log&acct=$acct"},
|
|
'Delete'),
|
|
'procmail.log'),
|
|
|
|
$q->td ($q->a ({href => $q->url (-absolute => 1) . "?state=deletelog&file=mailfilter.log&acct=$acct"},
|
|
'Delete'),
|
|
'mailfilter.log'));
|
|
|
|
print '</table>';
|
|
}
|
|
else
|
|
{
|
|
print $q->p ('Maildrop and procmail can be enabled more easily with smesmerver-mailfiltering
|
|
see https://wiki.koozali.org, yum install smesmerver-mailfiltering');
|
|
}
|
|
|
|
############# Vacation ####################
|
|
print $q->h4 ('Vacation message');
|
|
if ( -e "/etc/e-smith/web/functions/userpanel-vacation" )
|
|
{
|
|
my $enableVacation = db_get_prop(\%accounts, $acct, "EmailVacation");
|
|
if (defined ($enableVacation) && $enableVacation eq 'yes')
|
|
{
|
|
$enableVacation = 'yes';
|
|
}
|
|
else
|
|
{
|
|
$enableVacation = 'no';
|
|
}
|
|
|
|
my $fullname = db_get_prop(\%accounts, $acct, 'FirstName') . " " . db_get_prop(\%accounts, $acct, 'LastName');
|
|
my $vacationText = "From: \"$fullname\" \<$acct\@$conf{'DomainName'}\>\n".
|
|
"Subject: away from my email\n\n".
|
|
"I will not be reading my mail for a while. Your mail regarding\n\n".
|
|
" \"\$SUBJECT\"\n\n".
|
|
"will be read when I return.\n\n";
|
|
|
|
if ( -e "/home/e-smith/$userpath/.vacation.msg" )
|
|
{
|
|
open (VACATION, "</home/e-smith/$userpath/.vacation.msg")
|
|
or die "Error: Could not open file: /home/e-smith/$userpath/.vacation.msg\n";
|
|
my @vacationTemp = <VACATION>;
|
|
$vacationText = join ("", @vacationTemp);
|
|
|
|
close VACATION;
|
|
}
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4},
|
|
esmith::cgi::genTextRow ($q,
|
|
"Enter a vacation message here. You can use the keyword \"\$SUBJECT\" ".
|
|
"anywhere in the text to be replaced with the subject line ".
|
|
"from the email that activated the auto-reply. ".
|
|
"All text up-to the first blank line will be part of the reply ".
|
|
"email's header so ensure to leave at leave one blank line ".
|
|
"before you start your reply message."),
|
|
esmith::cgi::genTextRow($q,
|
|
$q->textarea (-name => 'vacationText',
|
|
-override => 1,
|
|
-default => "$vacationText",
|
|
-rows => 10,
|
|
-columns => 64)),
|
|
|
|
$q->Tr (esmith::cgi::genCell ($q, "Enable Vacation Messages:"),
|
|
esmith::cgi::genCell ($q, $q->popup_menu (-name => 'enableVacation',
|
|
-values => ['yes', 'no'],
|
|
-default => "$enableVacation"))));
|
|
|
|
print '</table>';
|
|
}
|
|
else
|
|
{
|
|
print $q->p ('Vacation can be enabled more easily with smesmerver-vacation
|
|
see https://wiki.koozali.org, yum install smesmerver-vacation');
|
|
}
|
|
|
|
print $q->submit (-name => 'action', -value => 'Save');
|
|
print $q->hidden (-name => 'acctNAME', -override => 1, -default => $acct);
|
|
|
|
print $q->hidden (-name => 'state',
|
|
-override => 1,
|
|
-default => 'performEnableProc');
|
|
|
|
}
|
|
else
|
|
{
|
|
print $q->p (esmith::cgi::genTextRow ($q, "Admin can't modify any settings here."));
|
|
print $q->p ('<a href="emailsettings">configure</a> the admin settings in the E-mail panel');
|
|
}
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print '</FONT>';
|
|
print '</DIV>';
|
|
print $q->end_html;
|
|
return;
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# advanced form to modify or create rule
|
|
#------------------------------------------------------------
|
|
|
|
sub showAdvancedRuleEdit ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $acctName2 = $q->param ('acctName');
|
|
my $pmRule = $q->param ('acct');
|
|
my $oldpmRule = "$pmRule";
|
|
|
|
if ($pmRule eq 'new')
|
|
{
|
|
my $random = int(rand(999999));
|
|
$pmRule = $acctName2.$random;
|
|
}
|
|
|
|
#clear deliver field if using sort as we use the existing mbox list *nolonger
|
|
my $del = db_get_prop(\%processmail, $pmRule, "deliver") || '';
|
|
my $del2 = db_get_prop(\%processmail, $pmRule, "deliver2") || '';
|
|
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Add or modify a users mail rule.');
|
|
|
|
print $q->startform (-method => 'POST',
|
|
-action => $q->url (-absolute => 1));
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4},
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ('Select the part of the email to be tested. The criterion
|
|
could be part of an email address, header, subject, or the email size.
|
|
The second test is optional.')),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "First Test",
|
|
$q->popup_menu (-name => 'basis',
|
|
-values => ['Subject','TO_','From','headers','<','>'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "basis") || '' ,
|
|
-labels => \%Label)),
|
|
|
|
esmith::cgi::genNameValueRow ($q,"First Criterion",
|
|
"criterion",
|
|
db_get_prop(\%processmail, $pmRule, "criterion") || '',),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Second Test",
|
|
$q->popup_menu (-name => 'basis2',
|
|
-values => ['','Subject','TO_','From','headers'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "basis2") || '' ,
|
|
-labels => \%Label)),
|
|
|
|
esmith::cgi::genNameValueRow ($q,"Second Criterion",
|
|
"criterion2",
|
|
db_get_prop(\%processmail, $pmRule, "criterion2") || '',),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ("What you are going to do with your message.")),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Action",
|
|
$q->popup_menu (-name => 'action',
|
|
-values => ['sort','forward','delete'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "action") || '' ,
|
|
-labels => \%Labels)),
|
|
|
|
esmith::cgi::genNameValueRow ($q,"Folder or address",
|
|
"deliver",
|
|
$del,),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->b ('Optional copy')),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ("Keep a copy of the email, sort it, or send it to somewhere else.")),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Copy",
|
|
$q->popup_menu (-name => 'copy',
|
|
-values => ['no','yes'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "copy") || '' )),
|
|
|
|
esmith::cgi::genWidgetRow ($q, "Action of copy",
|
|
$q->popup_menu (-name => 'action2',
|
|
-values => ['','inbox','sort','forward'],
|
|
-default => db_get_prop(\%processmail, $pmRule, "action2") || '',
|
|
-labels => \%Labels)),
|
|
|
|
esmith::cgi::genNameValueRow ($q, "Folder or address",
|
|
"deliver2",
|
|
$del2,),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->b ('Priority')),
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ("Change the order ".
|
|
"in which rules are evaluated by altering this value. ".
|
|
"Priority is determined by ascii value, and must be unique or you ".
|
|
"overwrite the other rule with that value. ".
|
|
"eg user101 goes first, then user5 then user99. because 1<5<9 ")),
|
|
|
|
esmith::cgi::genNameValueRow ($q,
|
|
"Order of rule execution",
|
|
"pmRule",
|
|
"$pmRule",));
|
|
|
|
print $q->p (esmith::cgi::genButtonRow ($q,
|
|
$q->submit (-name => 'action',
|
|
-value => 'Save')));
|
|
|
|
print $q->hidden (-name => 'state', -override => 1, -default => 'saveRule');
|
|
print $q->hidden (-name => 'pmRule', -override => 1, -default => $pmRule);
|
|
print $q->hidden (-name => 'oldpmRule', -override => 1, -default => $oldpmRule);
|
|
print $q->hidden (-name => 'acctName', -override => 1, -default => $acctName2);
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print '</FONT>';
|
|
print '</DIV>';
|
|
print $q->end_html;
|
|
return;
|
|
}
|
|
|
|
|
|
#----------PERFORM single user-------------------------------
|
|
|
|
sub performEnableProc ($)
|
|
{
|
|
my $acct = $q->param ('acctNAME');
|
|
my $loglevel = $q->param ('loglevel') || 'some';
|
|
my $emailForward = $q->param ('emailForward');
|
|
my $forwardAddress = $q->param ('forwardAddress');
|
|
my $Visible = $q->param ('Visible') || '';
|
|
my $MailFilter = $q->param ('MailFilter') || '';
|
|
my $tmda = $q->param ('tmda') || '';
|
|
my $zarafa = $q->param ('zarafa') || '';
|
|
|
|
if ($acct =~ /^([a-z][\-a-z0-9]*)$/)
|
|
{
|
|
$acct = $1;
|
|
}
|
|
|
|
my $userpath = ($acct eq 'admin')? "": "files/users/$acct";
|
|
|
|
if ($Visible eq 'internal')
|
|
{ db_set_prop(\%accounts, $acct, 'Visible', $Visible); }
|
|
else
|
|
{ db_delete_prop(\%accounts, $acct, 'Visible'); }
|
|
|
|
if ($MailFilter eq 'bypass')
|
|
{ db_set_prop(\%accounts, $acct, 'MailFilter', $MailFilter); }
|
|
else
|
|
{ db_delete_prop(\%accounts, $acct, 'MailFilter'); }
|
|
|
|
if ($zarafa eq 'enabled')
|
|
{ db_set_prop(\%accounts, $acct, 'zarafa', 'enabled'); }
|
|
elsif ($zarafa eq 'disabled')
|
|
{ db_delete_prop(\%accounts, $acct, 'zarafa'); }
|
|
|
|
if ($forwardAddress eq '') #blank
|
|
{
|
|
if (($emailForward eq 'forward') || ($emailForward eq 'both'))
|
|
{
|
|
showInitial ($q,
|
|
"Error: missing characters in email forwarding address: " .
|
|
"\"$forwardAddress\". Did not modify account.");
|
|
return;
|
|
}
|
|
}
|
|
elsif ($forwardAddress =~ /\s+/) #whitespace
|
|
{
|
|
showInitial ($q,
|
|
"Error: whitespace characters in email forwarding address: " .
|
|
"\"$forwardAddress\". Did not modify account.");
|
|
return;
|
|
}
|
|
elsif ($forwardAddress =~ /!^[a-zA-Z][a-zA-Z0-9\._\-\@]*$/) #not valid
|
|
{
|
|
showInitial ($q,
|
|
"Error: invalid characters in email forwarding address: " .
|
|
"\"$forwardAddress\". Did not modify account.");
|
|
return;
|
|
}
|
|
|
|
|
|
#in smeserver-vacation
|
|
if ( -e "/etc/e-smith/web/functions/userpanel-vacation" )
|
|
{
|
|
my $enableVacation = $q->param ('enableVacation');
|
|
|
|
my $vacationText = $q->param ('vacationText');
|
|
if ($vacationText eq '' && $enableVacation eq 'yes')
|
|
{
|
|
showEnableProc ($q, "Error: no vacation message was specified. $acct.", $acct);
|
|
return;
|
|
}
|
|
|
|
open (VACATION, ">/home/e-smith/$userpath/.vacation.msg")
|
|
or die ("Error opening vacation message file '/home/e-smith/files/$acct/.vacation.msg': $!\n");
|
|
|
|
print VACATION "$vacationText";
|
|
close VACATION;
|
|
|
|
db_set_prop(\%accounts, $acct, 'EmailVacation', "$enableVacation");
|
|
db_set_prop(\%accounts, $acct, 'EmailForward', $emailForward);
|
|
db_set_prop(\%accounts, $acct, 'ForwardAddress', $forwardAddress);
|
|
}
|
|
|
|
#in smeserver-mailfiltering
|
|
if ( -e "/etc/e-smith/web/functions/userpanel-mailsort" )
|
|
{
|
|
unless (exists $processmail {$acct})
|
|
{
|
|
db_set(\%processmail, $acct, 'settings');
|
|
}
|
|
db_set_prop(\%processmail, $acct, 'loglevel', $loglevel);
|
|
|
|
}
|
|
|
|
# in dungog-tmda-cgi
|
|
if ( -e "/etc/e-smith/web/functions/userpanel-tmda")
|
|
{
|
|
db_set_prop(\%accounts, $acct, 'tmda', $tmda);
|
|
}
|
|
|
|
system ("/sbin/e-smith/signal-event", "email-update", $acct) == 0
|
|
or die ("Error occurred email-update.\n");
|
|
|
|
showInitial ($q, "Settings altered for account $acct.");
|
|
#showEnableProc ($q, "Settings altered for account $acct.", $acct);
|
|
}
|
|
|
|
#------------------------------------------------------------
|
|
# save the rule for $user to the database
|
|
#------------------------------------------------------------
|
|
|
|
sub performSaveRule ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $acctName = $q->param ('acctName') || '';
|
|
my $oldpmRule = $q->param ('oldpmRule') || '';
|
|
my $pmRule = $q->param ('pmRule') || '';
|
|
my $basis = $q->param ('basis') || '';
|
|
my $criterion = $q->param ('criterion') || '';
|
|
my $basis2 = $q->param ('basis2') || '';
|
|
my $criterion2 = $q->param ('criterion2') || '';
|
|
my $deliver = $q->param ('deliver') || '';
|
|
my $deliver2 = $q->param ('deliver2') || '';
|
|
my $copy = $q->param ('copy') || '';
|
|
my $action = $q->param ('action') || '';
|
|
my $action2 = $q->param ('action2') || '';
|
|
my $id = $q->param ('id') || '';
|
|
|
|
if ($acctName =~ /^([a-z][\.\-a-z0-9]*)$/)
|
|
{
|
|
$acctName = $1;
|
|
}
|
|
|
|
if ($deliver eq '' && $action eq 'forward')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: in destination.");
|
|
esmith::cgi::genResult ($q, "Error: You failed to enter a destination address");
|
|
return;
|
|
}
|
|
|
|
if ($deliver2 eq '' && $copy eq 'yes' && $action2 eq 'forward')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: in destination.");
|
|
esmith::cgi::genResult ($q, "Error: You failed to enter a destination address for your copy");
|
|
return;
|
|
}
|
|
|
|
if ($criterion eq '')
|
|
{
|
|
esmith::cgi::genHeaderNonCacheable ($q, \%conf, "Error: you failed to enter a criterion value.");
|
|
esmith::cgi::genResult ($q, "Error: you failed to enter a criterion value.");
|
|
return;
|
|
}
|
|
|
|
if ($copy eq 'no')
|
|
{
|
|
$deliver2 = '';
|
|
$action2 = '';
|
|
}
|
|
|
|
db_delete(\%processmail, $oldpmRule);
|
|
db_set(\%processmail, $pmRule, $acctName);
|
|
db_set_prop(\%processmail, $pmRule, "basis", $basis);
|
|
db_set_prop(\%processmail, $pmRule, "criterion", $criterion);
|
|
db_set_prop(\%processmail, $pmRule, "basis2", $basis2);
|
|
db_set_prop(\%processmail, $pmRule, "criterion2", $criterion2);
|
|
db_set_prop(\%processmail, $pmRule, "deliver", $deliver);
|
|
db_set_prop(\%processmail, $pmRule, "deliver2", $deliver2);
|
|
db_set_prop(\%processmail, $pmRule, "action", $action);
|
|
db_set_prop(\%processmail, $pmRule, "action2", $action2);
|
|
db_set_prop(\%processmail, $pmRule, "copy", $copy);
|
|
|
|
system ("/sbin/e-smith/signal-event", "mailsorting-conf", "$acctName") == 0
|
|
or die ("Error occurred while modifying user.\n");
|
|
|
|
showEnableProc ($q, "Rule saved for $acctName.",$acctName);
|
|
|
|
return;
|
|
}
|
|
|
|
|
|
#------------------------------------------------------------
|
|
# delete single rule
|
|
#------------------------------------------------------------
|
|
|
|
sub performDeleteSingle ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $acct = $q->param ('acct'); #the rule number
|
|
my $acctName = $q->param ('acctName'); #the user
|
|
|
|
if ($acct =~ /^([a-z][\-a-z0-9]*)$/)
|
|
{
|
|
$acct = $1;
|
|
}
|
|
if ($acctName =~ /^([a-z][\-a-z0-9]*)$/)
|
|
{
|
|
$acctName = $1;
|
|
}
|
|
|
|
db_delete(\%processmail, "$acct");
|
|
|
|
system ("/sbin/e-smith/signal-event", "mailsorting-conf", "$acctName") == 0
|
|
or die ("Error occurred while modifying user.\n");
|
|
|
|
showEnableProc ($q, "Successfully removed rule.", $acctName);
|
|
|
|
}
|
|
|
|
sub performDeletelog ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $acct = $q->param ('acct');
|
|
my $file = $q->param ('file');
|
|
|
|
if ($acct =~ /^([a-z][\-a-z0-9]*)$/)
|
|
{
|
|
$acct = $1;
|
|
}
|
|
|
|
my $userpath = ($acct eq 'admin')? "": "files/users/$acct";
|
|
|
|
if (-f "/home/e-smith/$userpath/$file")
|
|
{
|
|
system("/bin/rm -f /home/e-smith/$userpath/procmail.log");
|
|
}
|
|
|
|
if (-f "/home/e-smith/$userpath/$file")
|
|
{
|
|
system("/bin/rm -f /home/e-smith/$userpath/mailfilter.log");
|
|
}
|
|
|
|
showEnableProc ($q, "Deleted log file.", $acct);
|
|
}
|
|
|
|
|
|
sub performViewlog ($)
|
|
{
|
|
my ($q) = @_;
|
|
my $acct = $q->param ('acct');
|
|
my $file = $q->param ('file');
|
|
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, "$acct $file");
|
|
|
|
print $q->startform (-method => 'POST',
|
|
-action => $q->url (-absolute => 1));
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4});
|
|
|
|
my $userpath = ($acct eq 'admin')? "": "files/users/$acct";
|
|
|
|
if ( -e "/home/e-smith/$userpath/$file" )
|
|
{
|
|
open (INF,"/home/e-smith/$userpath/$file")
|
|
or die ("can't open $file to read: $1. ");
|
|
|
|
while (<INF>)
|
|
{
|
|
print "$_<br>\n";
|
|
}
|
|
close INF;
|
|
}
|
|
|
|
if ( -e "$file" )
|
|
{
|
|
open (INF,"$file")
|
|
or die ("can't open $file to read: $1. ");
|
|
|
|
while (<INF>)
|
|
{
|
|
print "$_<br>\n";
|
|
}
|
|
close INF;
|
|
}
|
|
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . "?state=help"}, 'Email help'), " ..."));
|
|
print $q->end_html;
|
|
return;
|
|
|
|
}
|
|
|
|
sub GetDisplayName ($)
|
|
{
|
|
my $s = shift;
|
|
return $s;
|
|
}
|
|
|
|
sub showHelp ($)
|
|
{
|
|
my ($q) = @_;
|
|
|
|
esmith::cgi::genHeaderNonCacheable
|
|
($q, \%conf, 'Email Help');
|
|
|
|
print $q->startform (-method => 'POST',
|
|
-action => $q->url (-absolute => 1));
|
|
|
|
print $q->table ({border => 0, cellspacing => 0, cellpadding => 4},
|
|
|
|
esmith::cgi::genTextRow ($q, $q->p ('<pre>
|
|
* <a href="#global">Global rules</a>
|
|
* <a href="#individ">Individual accounts</a>
|
|
* <a href="#options">Delivery options</a>
|
|
* <a href="#rules">Mail Rules</a>
|
|
|
|
<a name="global"><h3>Global rules</h3></a>
|
|
If smeserver-mailsorting is installed you can enable all mail
|
|
to be directed through either procmail or maildrop.
|
|
|
|
Default leaves the system in the original state
|
|
When procmail or maildrop is enabled mail can be sorted according to
|
|
any rules created, if unsorted the mail is delivered according to the
|
|
standard email setting of the user ie local, forward or both.
|
|
|
|
Maildrop includes a rule to match content in the body of the email
|
|
for email smaller the 5000 bytes it compares the list of words
|
|
or regular expressions you create in the file /opt/wordfilter
|
|
|
|
<a name="individ"><h3>Individual accounts</h3></a>
|
|
The Individual accounts table of users provides an overview.
|
|
The Account name provies a link to individual settings.
|
|
Name shows the users real name.
|
|
Pseudomnys give additional email addresses that go to the account
|
|
Delivery is either
|
|
local - mail stays on server
|
|
forward - mail is forwarded to another address
|
|
both - keeps a copy and forwards the mail
|
|
The Forwarding address is show only if forwarding is enabled
|
|
|
|
<a name="options"><h3>Delivery options</h3></a>
|
|
Values in the options column may include:
|
|
internal, users can only recieve local mail
|
|
|
|
The following options require additional software.
|
|
|
|
bypass, exclude this user for global mailfiltering ie. procmail/maildrop
|
|
vacation, a vacation message reply is sent
|
|
tmda, challenge and response email system
|
|
zarafa, deliver to zarafa
|
|
|
|
<b>smeserver-mailsorting</b>
|
|
Provides configuration files to create mail rules
|
|
that are processed by either procmail or maildrop
|
|
|
|
<b>smeserver-vacation</b>
|
|
Provides for a vacation message to be sent,
|
|
for example the user is out of the office
|
|
|
|
<b>dungog-tmda-cgi</b>
|
|
tmda.net
|
|
A combination of challenge and responce, and tagged email address that reduces spam
|
|
|
|
Note. tmda needs two values set
|
|
|
|
> tmda : the sme setting is enabled and the user has enabled tmda at /tmda
|
|
> tmda* : the sme setting is NOT enabled but the user has enabled tmda at /tmda
|
|
> tmda- : the sme setting is enabled but the user never enabled tmda at /tmda
|
|
> tmda! : the user has disabled tmda at /tmda but not the sme setting
|
|
|
|
tmda
|
|
tmda is correctly configured
|
|
|
|
tmda*
|
|
tmda will work but without vacation, forwarding or procmail,
|
|
until .qmail file is recreated, then mail does not get sent to tmda.
|
|
|
|
tmda-
|
|
tmda setting is ignored
|
|
|
|
tmda!
|
|
/tmda was enabled but now is not, its likely mail will be lost
|
|
.qmail is sending mail to tmda, see the cron job below for a fix
|
|
|
|
To enable TMDA
|
|
1. enable and configure at /tmda
|
|
2. make SME aware of the change here
|
|
|
|
To disable TMDA
|
|
1. Tell SME we are no longer going to use TMDA
|
|
- once you have done that here SME has disabled tmda
|
|
[optional but recommended]
|
|
2. disable at /tmda to release pending mail
|
|
3. Tell SME again, to confirm current settings are restored
|
|
|
|
To Check users who may disable /tmda but not the SME setting
|
|
enable the cron job *Fix incorrect TMDA settings*
|
|
which is visible if you have dungog-cron
|
|
|
|
Admin can change the default domain for new tmda users
|
|
db dungog set tmdaDomain domain.net
|
|
expand-template /usr/lib/python2.3/site-packages/tmda-cgi/skel/install/.tmda/config
|
|
|
|
If you have procmail enabled the daily *TMDA pending summary*
|
|
will be deleted automatically if it is empty
|
|
|
|
<a name="rules"><h3>Mail Rules</h3></a>
|
|
Rules to match email then perform an action
|
|
|
|
Match against the emails size, To, From, or other headers
|
|
You can combine two elements before you call it a match
|
|
it may be helpful to view the headers of your emails to check if things
|
|
are not matching as expected,
|
|
to get an idea of the size of emails check the log file
|
|
|
|
when matched you can
|
|
sort to an existing mail folder
|
|
forward to another email address
|
|
or delete it
|
|
|
|
links are available to review the rules file,
|
|
you can review the log file to check which rules are matched
|
|
the log file is rotated weekly and kept for two weeks but you can delete it
|
|
if for example you are checking current activity and have a lot of information
|
|
|
|
')));
|
|
|
|
print $q->p ('<a href="viewlogfiles?filename=qmail/current&matchPattern=&highlightPattern=">Review</a> qmail/current or
|
|
<a href="viewlogfiles?filename=qpsmtpd/current&matchPattern=&highlightPattern=">Review</a> qpsmtpd/current in the View log files panel.');
|
|
|
|
print $q->endform;
|
|
print $q->p ($q->hr, $q->font ({size => "-1"}, "https://wiki.koozali.org",
|
|
$q->a ({href => $q->url (-absolute => 1) . ""}, 'Return to main'), " ..."));
|
|
print $q->end_html;
|
|
return;
|
|
}
|
|
|