本文目录导读:

- 使用
fetchmail+procmail备份(Linux/Unix) - 使用 Python +
imaplib(跨平台方案) - 使用
curl+getmail(简单方案) - 设置定时任务(Cron)
- 使用 systemd 定时器
- 使用建议
使用 fetchmail + procmail 备份(Linux/Unix)
安装依赖
sudo apt-get install fetchmail procmail mailutils
备份脚本 backup_email.sh
#!/bin/bash
# 邮件备份脚本
# 支持 IMAP 和 POP3 协议
# 配置
BACKUP_DIR="/path/to/email_backups"
DATE=$(date +%Y%m%d_%H%M%S)
LOG_FILE="$BACKUP_DIR/backup_$DATE.log"
# 邮箱配置
EMAIL_USER="your_email@example.com"
EMAIL_PASS="your_password"
EMAIL_SERVER="imap.example.com"
EMAIL_PORT="993"
PROTOCOL="IMAP" # 或 POP3
SSL="--ssl"
# 创建备份目录
mkdir -p "$BACKUP_DIR"
cd "$BACKUP_DIR"
# 创建 fetchmail 配置
cat > .fetchmailrc << EOF
set daemon 0
set logfile "$LOG_FILE"
poll $EMAIL_SERVER
protocol $PROTOCOL
port $EMAIL_PORT
username "$EMAIL_USER"
password "$EMAIL_PASS"
$SSL
mda "/usr/bin/procmail -d %T"
EOF
chmod 600 .fetchmailrc
# 开始备份
echo "=== 开始备份邮件: $(date) ===" >> "$LOG_FILE"
fetchmail -f .fetchmailrc -v >> "$LOG_FILE" 2>&1
# 邮件格式转换(如果有新的 .eml 文件)
if ls *.eml 1> /dev/null 2>&1; then
mkdir -p "$BACKUP_DIR/mbox_$DATE"
for eml in *.eml; do
mv "$eml" "$BACKUP_DIR/mbox_$DATE/"
done
# 压缩备份
tar -czf "$BACKUP_DIR/email_backup_$DATE.tar.gz" "mbox_$DATE"
rm -rf "mbox_$DATE"
fi
# 清理旧配置
rm -f .fetchmailrc
echo "=== 备份完成: $(date) ===" >> "$LOG_FILE"
使用 Python + imaplib(跨平台方案)
安装依赖
pip install python-dotenv
备份脚本 email_backup.py
#!/usr/bin/env python3
"""
邮件备份脚本 - 支持导出为 .eml 和 .mbox 格式
"""
import imaplib
import email
import os
import json
import gzip
import logging
from datetime import datetime
from email.mime.multipart import MIMEMultipart
from email.utils import parsedate_to_datetime
from dotenv import load_dotenv
import getpass
# 加载环境变量
load_dotenv()
class EmailBackup:
def __init__(self, config=None):
self.config = config or self._load_config()
self.setup_logging()
def _load_config(self):
"""从环境变量或配置文件加载邮箱设置"""
if os.path.exists('config.json'):
with open('config.json', 'r') as f:
return json.load(f)
return {
'IMAP_SERVER': os.getenv('IMAP_SERVER', 'imap.example.com'),
'IMAP_PORT': int(os.getenv('IMAP_PORT', 993)),
'EMAIL': os.getenv('EMAIL'),
'PASSWORD': os.getenv('PASSWORD'),
'BACKUP_DIR': os.getenv('BACKUP_DIR', './email_backups'),
'FOLDERS': ['INBOX', 'Sent', 'Archive'],
'BACKUP_FORMAT': 'eml' # 或 'mbox'
}
def setup_logging(self):
"""配置日志"""
backup_dir = self.config['BACKUP_DIR']
os.makedirs(backup_dir, exist_ok=True)
log_file = os.path.join(backup_dir, f'backup_{datetime.now().strftime("%Y%m%d")}.log')
logging.basicConfig(
level=logging.INFO,
format='%(asctime)s - %(levelname)s - %(message)s',
handlers=[
logging.FileHandler(log_file),
logging.StreamHandler()
]
)
self.logger = logging.getLogger(__name__)
def connect(self):
"""连接到 IMAP 服务器"""
try:
self.logger.info(f"连接到 {self.config['IMAP_SERVER']}:{self.config['IMAP_PORT']}")
if self.config.get('SSL', True):
mail = imaplib.IMAP4_SSL(
self.config['IMAP_SERVER'],
self.config['IMAP_PORT']
)
else:
mail = imaplib.IMAP4(
self.config['IMAP_SERVER'],
self.config['IMAP_PORT']
)
email_addr = self.config['EMAIL'] or input("邮箱地址: ")
password = self.config['PASSWORD'] or getpass.getpass("密码: ")
mail.login(email_addr, password)
self.mail = mail
self.logger.info("连接成功")
except Exception as e:
self.logger.error(f"连接失败: {e}")
raise
def backup_folder(self, folder='INBOX'):
"""备份指定文件夹的邮件"""
try:
self.logger.info(f"备份文件夹: {folder}")
# 选择文件夹
status, messages = self.mail.select(folder)
if status != 'OK':
self.logger.warning(f"无法访问文件夹: {folder}")
return
# 获取所有邮件ID
status, message_ids = self.mail.search(None, 'ALL')
if status != 'OK':
self.logger.warning(f"没有找到邮件: {folder}")
return
message_ids = message_ids[0].split()
total = len(message_ids)
self.logger.info(f"找到 {total} 封邮件")
# 创建备份子目录
folder_dir = os.path.join(
self.config['BACKUP_DIR'],
folder.replace('/', '_'),
datetime.now().strftime("%Y%m%d")
)
os.makedirs(folder_dir, exist_ok=True)
# 备份每封邮件
for idx, msg_id in enumerate(message_ids, 1):
try:
self._backup_single_email(msg_id, folder_dir, idx)
if idx % 10 == 0:
self.logger.info(f"进度: {idx}/{total} ({idx*100/total:.1f}%)")
except Exception as e:
self.logger.error(f"备份邮件 {msg_id} 失败: {e}")
continue
self.logger.info(f"文件夹 {folder} 备份完成: {total} 封邮件")
except Exception as e:
self.logger.error(f"备份文件夹 {folder} 失败: {e}")
def _backup_single_email(self, msg_id, folder_dir, idx):
"""备份单封邮件"""
status, msg_data = self.mail.fetch(msg_id, '(RFC822)')
if status != 'OK':
raise Exception(f"获取邮件 {msg_id} 失败")
raw_email = msg_data[0][1]
email_message = email.message_from_bytes(raw_email)
# 获取邮件日期
date_str = email_message.get('Date', '')
try:
date = parsedate_to_datetime(date_str)
date_prefix = date.strftime("%Y%m")
except:
date_prefix = "nodate"
# 生成文件名
subject = email_message.get('Subject', 'no_subject')
# 清理文件名中的特殊字符
subject = "".join(c if c.isalnum() or c in (' ', '-', '_') else '_' for c in subject)[:50]
if self.config['BACKUP_FORMAT'] == 'eml':
# 保存为 .eml 文件
filename = f"{idx:05d}_{date_prefix}_{subject}.eml"
filepath = os.path.join(folder_dir, filename)
with open(filepath, 'wb') as f:
f.write(raw_email)
elif self.config['BACKUP_FORMAT'] == 'mbox':
# 添加到 mbox 文件
mbox_file = os.path.join(folder_dir, f"{date_prefix}_backup.mbox")
with open(mbox_file, 'ab') as f:
f.write(f"From {email_message.get('From', 'unknown')} {date_str}\n".encode())
f.write(raw_email)
f.write(b"\n\n")
self.logger.debug(f"备份邮件: {subject[:30]}")
def backup_all(self):
"""备份所有配置的文件夹"""
try:
self.connect()
for folder in self.config.get('FOLDERS', ['INBOX']):
self.backup_folder(folder)
# 压缩备份文件
self._compress_backup()
except Exception as e:
self.logger.error(f"备份过程出错: {e}")
finally:
try:
self.mail.logout()
except:
pass
def _compress_backup(self):
"""压缩备份文件夹"""
import shutil
import tarfile
backup_dir = self.config['BACKUP_DIR']
today = datetime.now().strftime("%Y%m%d")
archive_name = f"email_backup_{today}"
archive_path = os.path.join(backup_dir, archive_name)
# 创建 tar.gz 归档
with tarfile.open(f"{archive_path}.tar.gz", "w:gz") as tar:
tar.add(backup_dir, arcname=archive_name)
self.logger.info(f"备份已压缩: {archive_path}.tar.gz")
if __name__ == "__main__":
# 使用示例
backup = EmailBackup()
backup.backup_all()
# 也可以使用命令行参数
import sys
if len(sys.argv) > 1 and sys.argv[1] == '--incremental':
# 增量备份模式
backup.config['FOLDERS'] = ['INBOX']
backup.backup_all()
配置文件 config.json
{
"IMAP_SERVER": "imap.gmail.com",
"IMAP_PORT": 993,
"EMAIL": "your_email@gmail.com",
"PASSWORD": "your_app_password",
"BACKUP_DIR": "/path/to/email_backups",
"FOLDERS": ["INBOX", "[Gmail]/Sent Mail", "[Gmail]/All Mail"],
"BACKUP_FORMAT": "eml",
"SSL": true
}
环境变量文件 .env
IMAP_SERVER=imap.gmail.com IMAP_PORT=993 EMAIL=your_email@gmail.com PASSWORD=your_app_password BACKUP_DIR=./email_backups
使用 curl + getmail(简单方案)
安装
sudo apt-get install getmail4
配置文件 ~/.getmail/getmailrc
[retriever] type = SimpleIMAPSSLRetriever server = imap.gmail.com username = your_email@gmail.com password = your_password [destination] type = Maildir path = /path/to/backup/Maildir/ [options] verbose = 1 delete = false message_log = ~/.getmail/log
定时备份脚本 cron_backup.sh
#!/bin/bash # 备份路径 BACKUP_DIR="/path/to/email_backups" DATE=$(date +%Y%m%d) LOG_FILE="$BACKUP_DIR/backup_$DATE.log" mkdir -p "$BACKUP_DIR" echo "=== 邮件备份开始: $(date) ===" | tee -a "$LOG_FILE" # 执行 getmail 备份 getmail --rcfile=getmailrc -g "$BACKUP_DIR" | tee -a "$LOG_FILE" # 压缩备份 cd "$BACKUP_DIR" tar -czf "email_backup_$DATE.tar.gz" "$BACKUP_DIR"/* rm -rf "$BACKUP_DIR"/*/ echo "=== 备份完成: $(date) ===" | tee -a "$LOG_FILE" # 保留最近30天的备份 find "$BACKUP_DIR" -name "*.tar.gz" -mtime +30 -delete
设置定时任务(Cron)
添加到 crontab
# 编辑 crontab crontab -e # 添加以下内容(每天凌晨2点执行) 0 2 * * * /path/to/backup_email.sh # 或者使用 Python 版本 0 2 * * * /usr/bin/python3 /path/to/email_backup.py # 每周日凌晨3点执行完整备份 0 3 * * 0 /usr/bin/python3 /path/to/email_backup.py --full # 每天执行增量备份 0 2 * * * /usr/bin/python3 /path/to/email_backup.py --incremental
使用 systemd 定时器
Systemd 服务文件 /etc/systemd/system/email-backup.service
[Unit] Description=Email Backup Service After=network.target [Service] Type=oneshot ExecStart=/usr/bin/python3 /path/to/email_backup.py User=backup_user Group=backup_group [Install] WantedBy=multi-user.target
Systemd 定时器文件 /etc/systemd/system/email-backup.timer
[Unit] Description=Email Backup Timer Requires=email-backup.service [Timer] OnCalendar=daily OnCalendar=*-*-* 02:00:00 Persistent=true [Install] WantedBy=timers.target
启用定时器
sudo systemctl enable email-backup.timer sudo systemctl start email-backup.timer
使用建议
-
安全性:
- 使用应用专用密码而非主密码
- 配置文件设置权限 600
- 考虑加密备份文件
-
存储管理:
# 定期清理旧备份 find /path/to/backups -name "*.tar.gz" -mtime +90 -delete
-
备份验证:
# 验证备份完整性 tar -tzf backup.tar.gz > /dev/null && echo "备份有效"
-
日志监控:
# 检查备份状态 tail -f /var/log/email_backup.log
选择适合您需求的方案,根据邮箱服务商的要求调整配置即可,建议先在测试环境运行,确认无误后再设置为定时任务。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播