291 lines
7.7 KiB
Bash
Executable File
291 lines
7.7 KiB
Bash
Executable File
#!/bin/bash
|
|
|
|
# Email Server Maintenance Script
|
|
# Performs routine maintenance tasks
|
|
|
|
set -euo pipefail
|
|
|
|
# Colors
|
|
RED='\033[0;31m'
|
|
GREEN='\033[0;32m'
|
|
YELLOW='\033[1;33m'
|
|
BLUE='\033[0;34m'
|
|
NC='\033[0m'
|
|
|
|
log() {
|
|
echo "$(date '+%Y-%m-%d %H:%M:%S') - $1"
|
|
}
|
|
|
|
info() {
|
|
echo -e "${BLUE}INFO: $1${NC}"
|
|
log "INFO: $1"
|
|
}
|
|
|
|
success() {
|
|
echo -e "${GREEN}SUCCESS: $1${NC}"
|
|
log "SUCCESS: $1"
|
|
}
|
|
|
|
warning() {
|
|
echo -e "${YELLOW}WARNING: $1${NC}"
|
|
log "WARNING: $1"
|
|
}
|
|
|
|
error() {
|
|
echo -e "${RED}ERROR: $1${NC}" >&2
|
|
log "ERROR: $1"
|
|
}
|
|
|
|
# Update virus definitions
|
|
update_virus_definitions() {
|
|
info "Updating virus definitions..."
|
|
if freshclam; then
|
|
success "Virus definitions updated"
|
|
systemctl restart clamav-daemon
|
|
else
|
|
error "Failed to update virus definitions"
|
|
fi
|
|
}
|
|
|
|
# Update spam rules
|
|
update_spam_rules() {
|
|
info "Updating SpamAssassin rules..."
|
|
if sa-update; then
|
|
success "SpamAssassin rules updated"
|
|
systemctl restart spamassassin
|
|
else
|
|
warning "SpamAssassin update failed or no updates available"
|
|
fi
|
|
}
|
|
|
|
# Clean mail logs
|
|
clean_mail_logs() {
|
|
info "Cleaning old mail logs..."
|
|
|
|
# Rotate logs if they're getting large (>100MB)
|
|
if [[ -f "/var/log/mail.log" ]]; then
|
|
size=$(stat -f%z "/var/log/mail.log" 2>/dev/null || stat -c%s "/var/log/mail.log" 2>/dev/null || echo 0)
|
|
if [[ $size -gt 104857600 ]]; then # 100MB
|
|
logrotate -f /etc/logrotate.d/rsyslog
|
|
success "Mail logs rotated"
|
|
else
|
|
info "Mail logs are not large enough to rotate"
|
|
fi
|
|
fi
|
|
}
|
|
|
|
# Clean temporary files
|
|
clean_temp_files() {
|
|
info "Cleaning temporary files..."
|
|
|
|
# Clean Amavis temporary files
|
|
find /var/lib/amavis/tmp -type f -mtime +7 -delete 2>/dev/null || true
|
|
|
|
# Clean SpamAssassin temporary files
|
|
find /var/lib/spamassassin -name "*.tmp" -mtime +7 -delete 2>/dev/null || true
|
|
|
|
# Clean Postfix temporary files
|
|
find /var/spool/postfix -name "*" -type f -mtime +7 -path "*/tmp/*" -delete 2>/dev/null || true
|
|
|
|
success "Temporary files cleaned"
|
|
}
|
|
|
|
# Check disk space
|
|
check_disk_space() {
|
|
info "Checking disk space..."
|
|
|
|
# Check root filesystem
|
|
root_usage=$(df / | awk 'NR==2 {print $5}' | sed 's/%//')
|
|
if [[ $root_usage -gt 85 ]]; then
|
|
warning "Root filesystem is ${root_usage}% full"
|
|
else
|
|
info "Root filesystem usage: ${root_usage}%"
|
|
fi
|
|
|
|
# Check mail directory
|
|
if [[ -d "/var/mail/vhosts" ]]; then
|
|
mail_usage=$(df /var/mail/vhosts | awk 'NR==2 {print $5}' | sed 's/%//')
|
|
if [[ $mail_usage -gt 85 ]]; then
|
|
warning "Mail directory is ${mail_usage}% full"
|
|
else
|
|
info "Mail directory usage: ${mail_usage}%"
|
|
fi
|
|
fi
|
|
}
|
|
|
|
# Check certificate expiration
|
|
check_ssl_expiration() {
|
|
info "Checking SSL certificate expiration..."
|
|
|
|
cert_files=$(find /etc/letsencrypt/live -name "fullchain.pem" 2>/dev/null || true)
|
|
|
|
for cert_file in $cert_files; do
|
|
domain=$(basename $(dirname $cert_file))
|
|
expires=$(openssl x509 -in "$cert_file" -noout -enddate | cut -d= -f2)
|
|
expires_epoch=$(date -d "$expires" +%s)
|
|
current_epoch=$(date +%s)
|
|
days_left=$(( (expires_epoch - current_epoch) / 86400 ))
|
|
|
|
if [[ $days_left -lt 30 ]]; then
|
|
warning "SSL certificate for $domain expires in $days_left days"
|
|
else
|
|
info "SSL certificate for $domain expires in $days_left days"
|
|
fi
|
|
done
|
|
}
|
|
|
|
# Check service status
|
|
check_services() {
|
|
info "Checking service status..."
|
|
|
|
services=("postfix" "dovecot" "amavis" "spamassassin" "clamav-daemon" "opendkim" "apache2" "postgresql")
|
|
|
|
for service in "${services[@]}"; do
|
|
if systemctl is-active --quiet $service; then
|
|
success "$service is running"
|
|
else
|
|
error "$service is not running"
|
|
fi
|
|
done
|
|
}
|
|
|
|
# Test basic email functionality
|
|
test_email_basic() {
|
|
info "Testing basic email functionality..."
|
|
|
|
# Test SMTP port
|
|
if nc -z localhost 25; then
|
|
success "SMTP port 25 is accessible"
|
|
else
|
|
error "SMTP port 25 is not accessible"
|
|
fi
|
|
|
|
# Test submission port
|
|
if nc -z localhost 587; then
|
|
success "Submission port 587 is accessible"
|
|
else
|
|
error "Submission port 587 is not accessible"
|
|
fi
|
|
|
|
# Test IMAP port
|
|
if nc -z localhost 993; then
|
|
success "IMAPS port 993 is accessible"
|
|
else
|
|
error "IMAPS port 993 is not accessible"
|
|
fi
|
|
}
|
|
|
|
# Database maintenance
|
|
database_maintenance() {
|
|
info "Performing database maintenance..."
|
|
|
|
# Analyze and vacuum database
|
|
sudo -u postgres psql -d postfix -c "ANALYZE;" >/dev/null 2>&1
|
|
sudo -u postgres psql -d postfix -c "VACUUM;" >/dev/null 2>&1
|
|
|
|
success "Database maintenance completed"
|
|
}
|
|
|
|
# Check mail queue
|
|
check_mail_queue() {
|
|
info "Checking mail queue..."
|
|
|
|
queue_count=$(mailq | tail -1 | awk '{print $5}' || echo "0")
|
|
if [[ "$queue_count" == "empty" ]]; then
|
|
queue_count=0
|
|
fi
|
|
|
|
if [[ $queue_count -gt 10 ]]; then
|
|
warning "Mail queue has $queue_count messages"
|
|
echo "Run 'mailq' to see queued messages"
|
|
echo "Run 'postqueue -f' to flush the queue"
|
|
else
|
|
info "Mail queue has $queue_count messages"
|
|
fi
|
|
}
|
|
|
|
# Generate maintenance report
|
|
generate_report() {
|
|
info "Generating maintenance report..."
|
|
|
|
report_file="/var/log/email-maintenance-$(date +%Y%m%d).log"
|
|
|
|
{
|
|
echo "Email Server Maintenance Report - $(date)"
|
|
echo "============================================"
|
|
echo
|
|
echo "System Information:"
|
|
echo "- Hostname: $(hostname)"
|
|
echo "- Uptime: $(uptime | awk -F'up ' '{print $2}' | awk -F', load' '{print $1}')"
|
|
echo "- Load: $(uptime | awk -F'load average: ' '{print $2}')"
|
|
echo
|
|
echo "Disk Usage:"
|
|
df -h | grep -E "/$|/var"
|
|
echo
|
|
echo "Service Status:"
|
|
systemctl status postfix dovecot amavis --no-pager -l
|
|
echo
|
|
echo "Recent Mail Log Entries:"
|
|
tail -20 /var/log/mail.log | grep "$(date '+%b %d')"
|
|
} > "$report_file"
|
|
|
|
success "Maintenance report saved to $report_file"
|
|
}
|
|
|
|
# Main function
|
|
main() {
|
|
echo -e "${BLUE}Email Server Maintenance Script${NC}"
|
|
echo "==============================="
|
|
echo
|
|
|
|
# Check if running as root
|
|
if [[ $EUID -ne 0 ]]; then
|
|
error "This script must be run as root"
|
|
exit 1
|
|
fi
|
|
|
|
update_virus_definitions
|
|
update_spam_rules
|
|
clean_mail_logs
|
|
clean_temp_files
|
|
check_disk_space
|
|
check_ssl_expiration
|
|
check_services
|
|
test_email_basic
|
|
database_maintenance
|
|
check_mail_queue
|
|
generate_report
|
|
|
|
echo
|
|
success "Maintenance completed successfully!"
|
|
|
|
echo
|
|
echo -e "${YELLOW}Recommended actions:${NC}"
|
|
echo "1. Review the maintenance report in /var/log/"
|
|
echo "2. Monitor disk space regularly"
|
|
echo "3. Check for any service issues"
|
|
echo "4. Verify SSL certificate renewal is working"
|
|
}
|
|
|
|
# Show usage
|
|
if [[ "${1:-}" == "--help" || "${1:-}" == "-h" ]]; then
|
|
echo "Usage: $0"
|
|
echo
|
|
echo "This maintenance script performs:"
|
|
echo " - Updates virus definitions"
|
|
echo " - Updates SpamAssassin rules"
|
|
echo " - Cleans old logs and temporary files"
|
|
echo " - Checks disk space usage"
|
|
echo " - Verifies SSL certificate expiration"
|
|
echo " - Tests service status"
|
|
echo " - Performs database maintenance"
|
|
echo " - Checks mail queue status"
|
|
echo " - Generates maintenance report"
|
|
echo
|
|
echo "Run this script regularly (daily/weekly) via cron:"
|
|
echo "0 2 * * 0 /path/to/maintenance-email-server.sh"
|
|
exit 0
|
|
fi
|
|
|
|
main "$@"
|