前言:为什么 Linux 服务器安全加固是每个技术人的必修课
2026 年,全球每天都有超过 30,000 个网站遭到入侵,其中绝大多数是运行在 Linux 系统上的服务器。无论是你自托管的 NAS、公司的生产环境,还是个人博客的 VPS,一旦安全防护不到位,后果可能是数据泄露、服务中断,甚至被植入挖矿程序成为僵尸网络的一部分。
很多技术人有一个误区:「Linux 本身就很安全,不需要额外配置。」事实恰恰相反——Linux 的默认配置往往是最薄弱的环节。一个全新安装的 Ubuntu Server,如果直接使用默认设置暴露在公网上,平均不到 4 小时就会被自动化扫描工具发现并尝试入侵。
本文将从零开始,带你完成一台 Linux 服务器的完整安全加固。无论你是运维新手还是有经验的开发者,这份指南都能帮你建立一道坚固的安全防线。全文涵盖 10 个核心加固步骤,每一步都配有可执行的具体命令和配置说明。
第一步:系统更新与包管理安全
安全加固的第一步不是装防火墙,而是确保系统本身是最新的。大量安全漏洞之所以能被利用,正是因为管理员没有及时更新系统补丁。
1.1 启用自动安全更新
Ubuntu/Debian 系统可以使用 unattended-upgrades 实现自动安全更新:
# 安装自动更新工具
sudo apt update
sudo apt install -y unattended-upgrades
# 启用自动安全更新
sudo dpkg-reconfigure -plow unattended-upgrades
# 查看配置
cat /etc/apt/apt.conf.d/50unattended-upgrades
确保配置文件中的 Unattended-Upgrade::Allowed-Origins 包含 ${distro_id}:${distro_codename}-security,这样才能自动拉取安全补丁。
1.2 配置更新日志监控
自动更新虽然方便,但你仍然需要知道系统更新了哪些内容。配置日志通知:
# 编辑配置文件,开启邮件通知
sudo nano /etc/apt/apt.conf.d/50unattended-upgrades
# 添加以下行(替换为你的邮箱)
Unattended-Upgrade::Mail "admin@example.com";
Unattended-Upgrade::MailReport "on-change";
最佳实践:对于生产环境,建议每周手动执行一次完整更新,并在更新前检查变更日志:
# 查看待更新的包列表
apt list --upgradable
# 查看安全更新详情
apt changelog <package-name>
# 执行完整更新
sudo apt update && sudo apt upgrade -y
第二步:用户权限与 SSH 安全
SSH 是 Linux 服务器最常用的远程管理方式,也是攻击者最主要的入侵入口。据统计,暴露在公网的服务器每天会收到数千次 SSH 暴力破解尝试。
2.1 禁用 root 直接登录
永远不要让 root 用户直接通过 SSH 登录。创建一个普通用户,通过 sudo 提权:
# 创建新用户
sudo adduser admin
sudo usermod -aG sudo admin
# 切换到新用户测试登录
su - admin
# 确认新用户可以 sudo 后再禁用 root SSH 登录
sudo nano /etc/ssh/sshd_config
# 修改以下配置
PermitRootLogin no
MaxAuthTries 3
LoginGraceTime 30
2.2 使用 SSH 密钥认证,禁用密码登录
密码认证是暴力破解的主要目标。切换到 SSH 密钥认证后,暴力破解的成功率几乎降为零:
# 在本地机器生成密钥(如果还没有)
ssh-keygen -t ed25519 -C "your-email@example.com"
# 将公钥复制到服务器
ssh-copy-id admin@your-server-ip
# 在服务器上禁用密码认证
sudo nano /etc/ssh/sshd_config
# 修改以下配置
PasswordAuthentication no
PubkeyAuthentication yes
AuthenticationMethods publickey
PermitEmptyPasswords no
为什么选择 Ed25519:相比传统的 RSA,Ed25519 密钥更短(256 位 vs 2048/4096 位)、速度更快、安全性更高。它是目前推荐的 SSH 密钥算法。
2.3 修改 SSH 默认端口
虽然这不是真正的安全措施(属于安全通过模糊性),但修改默认端口可以过滤掉 90% 以上的自动化扫描:
# 编辑 SSH 配置
sudo nano /etc/ssh/sshd_config
# 修改端口(选择一个 1024-65535 之间的端口)
Port 2222
# 重启 SSH 服务
sudo systemctl restart sshd
# 验证新端口可以登录(重要!先开一个备用终端测试)
ssh -p 2222 admin@your-server-ip
⚠️ 警告:修改端口前,务必保持当前 SSH 连接不关闭,先开一个新终端测试新端口是否能正常登录。否则一旦配置错误,你可能被锁在服务器外面。
2.4 配置 SSH 访问控制
限制哪些用户和 IP 地址可以访问 SSH:
# 只允许特定用户登录
AllowUsers admin deployer
# 只允许特定组登录
AllowGroups sshusers
# 限制来源 IP(在 sshd_config 中)
# 或使用防火墙规则(见第四步)
第三步:配置防火墙(UFW / iptables)
防火墙是服务器安全的第一道防线。Linux 提供了多种防火墙方案,Ubuntu/Debian 推荐使用 UFW(Uncomplicated Firewall),它是对 iptables 的简化封装。
3.1 安装并配置 UFW
# 安装 UFW
sudo apt install -y ufw
# 默认策略:拒绝所有入站,允许所有出站
sudo ufw default deny incoming
sudo ufw default allow outgoing
# 只开放必要的端口
sudo ufw allow 2222/tcp # SSH(你修改后的端口)
sudo ufw allow 80/tcp # HTTP
sudo ufw allow 443/tcp # HTTPS
# 如果需要特定 IP 访问某个端口
sudo ufw allow from 203.0.113.0/24 to any port 3306
# 启用防火墙
sudo ufw enable
# 查看状态和规则
sudo ufw status verbose
3.2 高级:限制 SSH 连接频率
即使使用密钥认证,也应该限制 SSH 连接频率,防止暴力尝试耗尽系统资源:
# 限制 SSH 每分钟最多 3 个新连接
sudo ufw limit 2222/tcp
# 或者使用 iptables 直接配置
sudo iptables -A INPUT -p tcp --dport 2222 -m state --state NEW -m recent --set
sudo iptables -A INPUT -p tcp --dport 2222 -m state --state NEW -m recent --update --seconds 60 --hitcount 4 -j DROP
第四步:入侵检测与防护(Fail2Ban)
Fail2Ban 是一个自动化的入侵防护工具,它会监控日志文件,自动封禁多次尝试失败的 IP 地址。这是防御暴力破解的利器。
4.1 安装 Fail2Ban
# 安装
sudo apt install -y fail2ban
# 创建本地配置(不要直接修改 jail.conf)
sudo cp /etc/fail2ban/jail.conf /etc/fail2ban/jail.local
sudo nano /etc/fail2ban/jail.local
4.2 配置关键防护规则
# jail.local 配置示例
[DEFAULT]
# 封禁时间(秒):1 小时
bantime = 3600
# 检测时间窗口:10 分钟
findtime = 600
# 最大尝试次数:3 次
maxretry = 3
# 使用 UFW 作为封禁动作
banaction = ufw
[sshd]
enabled = true
port = 2222
filter = sshd
logpath = /var/log/auth.log
maxretry = 3
bantime = 86400
[nginx-http-auth]
enabled = true
filter = nginx-http-auth
port = http,https
logpath = /var/log/nginx/error.log
maxretry = 5
[recidive]
# 对反复被封禁的 IP 进行长期封禁
enabled = true
filter = recidive
logpath = /var/log/fail2ban.log
bantime = 604800
findtime = 86400
maxretry = 3
4.3 管理 Fail2Ban
# 启动并设置开机自启
sudo systemctl enable fail2ban
sudo systemctl start fail2ban
# 查看状态
sudo fail2ban-client status
# 查看特定 jail 的状态
sudo fail2ban-client status sshd
# 手动封禁/解封 IP
sudo fail2ban-client set sshd banip 10.0.0.0
sudo fail2ban-client set sshd unbanip 10.0.0.0
# 查看被封禁的 IP 列表
sudo fail2ban-client get sshd banip
第五步:文件系统安全加固
Linux 的文件权限系统是安全的基础。错误的权限配置可能导致敏感文件被未授权访问。
5.1 关键文件权限检查
# 检查关键文件权限
ls -la /etc/passwd # 应为 644
ls -la /etc/shadow # 应为 640(root:shadow)
ls -la /etc/gshadow # 应为 640
ls -la /etc/group # 应为 644
# 查找系统中所有 SUID 文件(可能被利用提权)
find / -perm -4000 -type f 2>/dev/null
# 查找系统中所有 SGID 文件
find / -perm -2000 -type f 2>/dev/null
# 查找世界可写文件
find / -perm -0002 -type f 2>/dev/null
# 查找没有属主的文件
find / -nouser -o -nogroup 2>/dev/null
5.2 配置 /tmp 安全挂载
/tmp 目录是攻击者常用的临时文件存放位置。通过特殊挂载选项可以限制其使用:
# 编辑 fstab
sudo nano /etc/fstab
# 添加以下行(如果没有单独的 /tmp 分区)
tmpfs /tmp tmpfs defaults,noexec,nosuid,size=1G 0 0
# 重新挂载
sudo mount -o remount /tmp
参数说明:
noexec:禁止在 /tmp 中执行任何程序nosuid:忽略 SUID/SGID 位size=1G:限制 /tmp 最大使用 1GB 内存
5.3 启用文件系统审计
# 安装 auditd
sudo apt install -y auditd
# 配置关键文件监控
sudo auditctl -w /etc/passwd -p wa -k identity
sudo auditctl -w /etc/shadow -p wa -k identity
sudo auditctl -w /etc/sudoers -p wa -k sudoers
sudo auditctl -w /etc/ssh/sshd_config -p wa -k sshd
# 查看审计日志
sudo aureport -f
sudo ausearch -k identity
第六步:网络层安全加固
除了防火墙,Linux 内核还提供了丰富的网络参数可以调整,以增强服务器的网络安全性。
6.1 配置 sysctl 网络参数
# 创建 sysctl 配置文件
sudo nano /etc/sysctl.d/99-security.conf
# 添加以下配置
# === IP 转发(除非你是路由器,否则禁用)===
net.ipv4.ip_forward = 0
net.ipv6.conf.all.forwarding = 0
# === ICMP 安全 ===
# 忽略 ICMP 广播(防止 Smurf 攻击)
net.ipv4.icmp_echo_ignore_broadcasts = 1
# 忽略错误的 ICMP 响应
net.ipv4.icmp_ignore_bogus_error_responses = 1
# === TCP 安全 ===
# 启用 SYN Cookie(防御 SYN Flood 攻击)
net.ipv4.tcp_syncookies = 1
# 禁用 IP 源路由
net.ipv4.conf.all.accept_source_route = 0
net.ipv6.conf.all.accept_source_route = 0
# 禁用 ICMP 重定向
net.ipv4.conf.all.accept_redirects = 0
net.ipv4.conf.all.send_redirects = 0
net.ipv6.conf.all.accept_redirects = 0
# 启用反向路径过滤
net.ipv4.conf.all.rp_filter = 1
# 禁用 IP 转发日志中的 martian 包
net.ipv4.conf.all.log_martians = 1
# === 连接跟踪 ===
# 增加最大连接数
net.netfilter.nf_conntrack_max = 1000000
# 缩短 TCP 连接超时
net.netfilter.nf_conntrack_tcp_timeout_established = 3600
# 应用配置
sudo sysctl -p /etc/sysctl.d/99-security.conf
6.2 禁用不必要的网络协议
如果你的服务器不需要 IPv6,建议直接禁用:
# 在 sysctl 配置中添加
sudo nano /etc/sysctl.d/99-security.conf
# 添加
net.ipv6.conf.all.disable_ipv6 = 1
net.ipv6.conf.default.disable_ipv6 = 1
# 应用
sudo sysctl -p /etc/sysctl.d/99-security.conf
第七步:Web 服务安全加固
如果你的服务器上运行着 Web 服务(Nginx/Apache),以下是必须的安全配置。
7.1 Nginx 安全配置
# /etc/nginx/nginx.conf 安全配置
server_tokens off; # 隐藏 Nginx 版本号
# 限制请求大小
client_max_body_size 10m;
# 安全头部
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-XSS-Protection "1; mode=block" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline';" always;
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
# 限制 HTTP 方法
if ($request_method !~ ^(GET|HEAD|POST)$) {
return 405;
}
# 禁止访问隐藏文件
location ~ /\. {
deny all;
access_log off;
log_not_found off;
}
7.2 SSL/TLS 配置
使用 Let’s Encrypt 免费获取 SSL 证书,并配置强加密:
# 安装 Certbot
sudo apt install -y certbot python3-certbot-nginx
# 获取证书
sudo certbot --nginx -d your-domain.com
# 配置自动续期
sudo certbot renew --dry-run
# 查看续期定时器
systemctl list-timers | grep certbot
第八步:日志管理与监控
没有日志的安全系统就像没有监控的仓库。完善的日志管理是安全事件响应的基础。
8.1 配置集中式日志
# 确保 rsyslog 正常运行
sudo systemctl enable rsyslog
sudo systemctl start rsyslog
# 配置日志轮转(防止日志占满磁盘)
sudo nano /etc/logrotate.conf
# 关键配置
daily
rotate 30
compress
delaycompress
missingok
notifempty
create 0640 root adm
8.2 配置关键日志监控
# 实时监控 SSH 登录尝试
sudo tail -f /var/log/auth.log | grep -i "failed\|invalid"
# 监控 sudo 使用
sudo tail -f /var/log/auth.log | grep sudo
# 监控内核日志
sudo dmesg -w
# 配置 logwatch(每日安全摘要邮件)
sudo apt install -y logwatch
# 默认每天凌晨运行,发送安全摘要
8.3 日志备份策略
# 创建日志备份脚本
sudo nano /usr/local/bin/backup-logs.sh
#!/bin/bash
BACKUP_DIR="/var/log/backups"
DATE=$(date +%Y%m%d)
mkdir -p $BACKUP_DIR
tar czf $BACKUP_DIR/logs-$DATE.tar.gz \
/var/log/auth.log \
/var/log/syslog \
/var/log/kern.log \
/var/log/fail2ban.log \
--remove-files
# 只保留最近 7 天的备份
find $BACKUP_DIR -name "logs-*.tar.gz" -mtime +7 -delete
# 设置定时任务
sudo crontab -e
# 每天凌晨 3 点备份日志
0 3 * * * /usr/local/bin/backup-logs.sh
第九步:安全扫描与漏洞检测
定期运行安全扫描工具,主动发现潜在的安全问题。
9.1 安装 Lynis 安全审计工具
# 安装 Lynis
sudo apt install -y lynis
# 运行安全审计
sudo lynis audit system
# 查看审计报告
sudo cat /var/log/lynis-report.dat
# 查看安全建议
sudo cat /var/log/lynis-report.dat | grep "suggestion"
Lynis 会对系统进行 200+ 项安全检查,并给出详细的评分和建议。建议每周运行一次。
9.2 安装 chkrootkit 和 rkhunter
# 安装 rootkit 检测工具
sudo apt install -y chkrootkit rkhunter
# 运行 chkrootkit
sudo chkrootkit
# 更新 rkhunter 数据库
sudo rkhunter --update
# 运行 rkhunter 检查
sudo rkhunter --check --skip-keypress
# 配置 rkhunter 每日自动检查
sudo nano /etc/default/rkhunter
# 设置 CRON_DAILY_RUN="yes"
9.3 端口扫描自查
# 查看当前开放的端口
sudo ss -tlnp
# 或使用 netstat
sudo netstat -tlnp
# 使用 nmap 自查(从外部机器)
nmap -sS -sV -O your-server-ip
# 检查 UDP 端口
nmap -sU your-server-ip
第十步:自动化安全维护脚本
将上述安全配置整合为自动化脚本,定期执行安全检查:
#!/bin/bash
# /usr/local/bin/security-check.sh
# 每周安全自查脚本
LOGFILE="/var/log/security-check-$(date +%Y%m%d).log"
echo "=== 安全自查报告 - $(date) ===" | tee $LOGFILE
echo "" | tee -a $LOGFILE
# 1. 检查系统更新
echo "--- 待更新的安全补丁 ---" | tee -a $LOGFILE
apt list --upgradable 2>/dev/null | grep -i security | tee -a $LOGFILE
# 2. 检查失败的 SSH 登录
echo "" | tee -a $LOGFILE
echo "--- 最近 24 小时 SSH 失败登录 ---" | tee -a $LOGFILE
grep "Failed password" /var/log/auth.log | \
awk '{print $(NF-3)}' | sort | uniq -c | sort -rn | \
head -20 | tee -a $LOGFILE
# 3. 检查异常进程
echo "" | tee -a $LOGFILE
echo "--- CPU 占用前 10 的进程 ---" | tee -a $LOGFILE
ps aux --sort=-%cpu | head -11 | tee -a $LOGFILE
# 4. 检查磁盘使用
echo "" | tee -a $LOGFILE
echo "--- 磁盘使用情况 ---" | tee -a $LOGFILE
df -h | tee -a $LOGFILE
# 5. 检查开放端口
echo "" | tee -a $LOGFILE
echo "--- 开放端口 ---" | tee -a $LOGFILE
ss -tlnp | tee -a $LOGFILE
# 6. 检查 Fail2Ban 状态
echo "" | tee -a $LOGFILE
echo "--- Fail2Ban 状态 ---" | tee -a $LOGFILE
fail2ban-client status | tee -a $LOGFILE
# 7. 检查 SUID 文件变化
echo "" | tee -a $LOGFILE
echo "--- SUID 文件 ---" | tee -a $LOGFILE
find / -perm -4000 -type f 2>/dev/null | tee -a $LOGFILE
echo "" | tee -a $LOGFILE
echo "=== 自查完成 ===" | tee -a $LOGFILE
将脚本加入 cron:
# 每周日凌晨 4 点执行安全自查
sudo crontab -e
0 4 * * 0 /usr/local/bin/security-check.sh
安全加固检查清单
完成所有步骤后,对照以下清单确认每一项都已落实:
| 检查项 | 状态 | 验证命令 |
|---|---|---|
| 系统已更新至最新 | ☐ | apt list --upgradable |
| 自动安全更新已启用 | ☐ | systemctl status unattended-upgrades |
| root SSH 登录已禁用 | ☐ | grep PermitRootLogin /etc/ssh/sshd_config |
| SSH 密钥认证已启用 | ☐ | grep PasswordAuthentication /etc/ssh/sshd_config |
| SSH 默认端口已修改 | ☐ | grep "^Port" /etc/ssh/sshd_config |
| 防火墙已配置并启用 | ☐ | sudo ufw status |
| Fail2Ban 已安装并运行 | ☐ | sudo fail2ban-client status |
| 关键文件权限正确 | ☐ | ls -la /etc/shadow |
| sysctl 网络参数已优化 | ☐ | sysctl net.ipv4.tcp_syncookies |
| Web 服务安全头部已配置 | ☐ | curl -I https://your-domain.com |
| SSL/TLS 证书已配置 | ☐ | openssl s_client -connect your-domain.com:443 |
| 日志监控已配置 | ☐ | systemctl status rsyslog |
| 安全扫描工具已安装 | ☐ | lynis --version |
| 自动化安全脚本已设置 | ☐ | crontab -l | grep security-check |
总结:安全是一个持续的过程
服务器安全加固不是一次性的工作,而是一个持续的过程。完成上述 10 个步骤后,你的 Linux 服务器已经具备了相当高的安全水平。但要记住以下几点:
第一,保持更新。安全补丁的发布速度永远快于攻击者的利用速度,及时更新是最有效的防御手段。
第二,监控日志。再好的安全配置也无法做到 100% 无漏洞。完善的日志监控能让你在第一时间发现异常,将损失降到最低。
第三,定期审计。每周运行一次安全自查脚本,每月运行一次 Lynis 全面审计,每季度进行一次完整的渗透测试(可以使用 nikto、nmap 等工具)。
第四,最小权限原则。每个服务、每个用户只授予其完成任务所需的最小权限。这是安全设计的核心原则,适用于任何规模的系统。
第五,备份与恢复。再完善的安全防护也不能替代备份。确保你有可靠的备份策略,并定期测试恢复流程。
安全不是一堵墙,而是一套体系。从系统层、网络层、应用层到管理层,每一层都需要精心设计和持续维护。希望这份指南能帮助你建立起自己的安全防线。
作者:虾米 | 发布于 2026 年 5 月 6 日
虾米生活分享

评论前必须登录!
注册