Linux 服务器防护:SSH、UFW、firewalld 与安全更新

保护 Linux 服务器,需要同时限制账号、管理权限和开放端口,及时维护安全更新,并保留可用的恢复通道。调整远程访问策略时,先保留当前会话和控制台,再逐项修改并测试新连接,确认后才关闭原会话。

修改规则前先验证SSH 登录与密钥认证,并准备虚拟机控制台恢复(英语)。参考环境为常规 Ubuntu 26.04 LTS 或 Rocky Linux 9 系列虚拟机;容器、WSL 和其他版本的服务及软件包可能不同,先记录本机版本。

变更前清点暴露面和恢复路径

id
getent group sudo
getent group wheel
sudo ss -lntup
systemctl --failed

id 查看当前身份与组,getent 查询系统组数据库。Ubuntu 常见 sudo 组、Rocky Linux 常见 wheel 组用于委派管理权限,但真正授权取决于 sudoers 等实际策略。某个组不存在时查询可能返回非零,不能据此推断整个服务器配置失败,也不能只凭组名判定权限。

ss -lntup 查看 TCP/UDP 监听及进程信息,systemctl 列出失败单元。把端口逐一对应到实际服务和用途,检查依赖后再停用不需要的服务。云安全组和主机防火墙是两个独立层次,主机允许不代表云入口也允许。

亲自确认虚拟机或云串行控制台能够打开,不能只有一个未验证的“控制台入口”。变更前记录防火墙、SSH 与账号状态并备份配置。现有连接仍存活,可能只是既有连接被允许,不代表新登录能成功。

先验证密钥登录,再调整 SSH 策略

用普通管理员账号打开新会话,确认密钥登录和 sudo 都可用。限制密码认证前,检查 Include 文件、Match 段和云初始化配置;反复追加同名选项不一定改变实际生效值。先找到服务端 sshd 的真实路径,再按本机安装调整示例:

sudo /usr/sbin/sshd -t
sudo /usr/sbin/sshd -T | grep -E "^(port|permitrootlogin|passwordauthentication|pubkeyauthentication) "

sshd -t 检查配置有效性与密钥状态,-T 输出生效配置。若存在 Match 条件,还需用 -C 指定相关用户、源地址等连接上下文。grep 只是筛选输出,不证明前面的 sshd 已通过检查;应先单独确认验证成功,再读取筛选结果。

通过检查后才用本机准确的服务名 reload,并从另一个终端测试新登录。若失败,在保留的会话或控制台恢复备份,再次验证。不要在尚无替代访问方式时先关闭原会话或停用唯一认证方式。

Ubuntu UFW:先允许实际管理入口

下方仅适用于SSH 确实监听 TCP 22 端口的实验服务器;自定义端口应将示例中的 22 一致替换。修改前确认安装和管理方式,避免在同一台主机上不加区分地混用不同防火墙管理工具。先读取状态,预览规则,添加所需允许项,再启用:

sudo ufw status verbose
sudo ufw --dry-run allow 22/tcp
sudo ufw allow 22/tcp
sudo ufw enable
sudo ufw status numbered

--dry-run 显示将生成的规则,不实际应用。这里的允许项对所有来源开放 22/tcp,只是实验条件,不是互联网服务器的最终访问策略。若需限制到管理来源,先核对 NAT 或 VPN 出口地址,避免把正确管理员挡在外面。

保留原会话,从新终端验证登录;再添加并验证更窄的来源规则,之后才移除宽规则,并再次测试。删除前重新读取 numbered 列表和原始记录,只删除目标规则;编号可能随删除而变化,不要依赖旧编号连续操作。不要通过清空全部规则来撤销一次实验。

Rocky Linux firewalld:区分 zone 与持久化

sudo firewall-cmd --state
sudo firewall-cmd --get-active-zones
sudo firewall-cmd --get-default-zone

zone 是一组适用于接口或来源的规则。先查实际管理流量使用的接口和活动 zone,不能默认它就是 default zone。将下方 REPLACE_WITH_ACTIVE_ZONE 替换为已确认的名称;--info-service=ssh 用于核对 ssh 服务定义中的端口是否与本机一致。

zone=REPLACE_WITH_ACTIVE_ZONE
sudo firewall-cmd --info-service=ssh
sudo firewall-cmd --zone="$zone" --add-service=ssh
sudo firewall-cmd --zone="$zone" --list-all
sudo firewall-cmd --permanent --zone="$zone" --add-service=ssh
sudo firewall-cmd --permanent --zone="$zone" --list-all

先只应用 runtime 规则并查看结果,暂停执行后续命令,并测试新的管理连接;确认访问正常,再把同一条预期规则写入 permanent,并核对保存结果。runtime 是当前运行状态,permanent 是持久配置;reload 可能丢弃未保存的 runtime 修改。反过来,直接把全部 runtime 保存为 permanent,也可能将临时放行一起长期保留。

撤销时只删除本次新增、原先不存在的允许项,并分别检查 runtime 和 permanent。尚未验证替代访问路径时,不要删除当前管理连接所依赖的规则。此示例允许 ssh 服务的范围仍由 zone 等条件决定,不自动等于仅允许某个管理来源。

维护更新,同时保留 SELinux 防护

下方第一组用于 Ubuntu。apt update 刷新软件包索引,随后列出可升级项;这不是已经安装了安全更新的证明:

sudo apt update
apt list --upgradable

第二组用于 Rocky Linux,查询可用更新并读取 SELinux 状态:

sudo dnf check-update
getenforce

dnf check-update 发现可用更新时可返回 100,不应与普通执行错误混淆。实际安装前检查备份、维护窗口、服务影响和是否需要重启。升级后不仅核对版本,还要测试实际服务响应,并在需要重启时验证重启后的运行状态。

SELinux 通过文件标签与进程策略控制访问,与防火墙的网络过滤不同。Web 服务读不到文件时,先查普通权限、标签和审计日志,不要直接关闭 SELinux。自定义目录可能需要用 semanage fcontext 定义持久标签规则,再用 restorecon 应用;应按服务和路径选择正确类型,不能给无关目录批量套用标签。

官方参考资料