Ubuntu服务器默认的SSH配置在公网环境下并不安全,尤其是允许密码登录和root直接登录这两项,几乎等于把大门敞开。安全加固的核心思路是:关闭不必要的登录通道、限制来源、强制密钥认证、记录异常行为。下面直接进入具体配置和操作方法。

先备份SSH配置文件

任何修改系统关键服务配置的操作,第一步都应该是备份。SSH服务的配置文件位于/etc/ssh/sshd_config,用下面命令备份:

sudo cp /etc/ssh/sshd_config /etc/ssh/sshd_config.bak.$(date +%F)

这样一旦配置错误导致无法登录,还可以通过服务器控制台或救援模式恢复。

禁止root账户直接SSH登录

root账户权限过大,一旦被暴力破解或撞库成功,攻击者就能完全控制服务器。正确做法是创建一个普通用户,赋予sudo权限,然后禁止root通过SSH登录。先创建用户并设置密码:

sudo adduser adminuser
sudo usermod -aG sudo adminuser

然后编辑sshd_config,找到PermitRootLogin这一行,修改为:

PermitRootLogin no

如果该行被注释,取消注释并改为no。保存后不要立即重启SSH服务,先确认新用户能正常sudo,否则可能把自己锁在服务器外。

禁用密码登录,强制使用密钥认证

密码登录是SSH暴力破解的主要目标。密钥认证使用非对称加密,安全性远高于密码。在本地电脑生成密钥对(如果还没有):

ssh-keygen -t ed25519 -C "your_email@example.com"

将公钥上传到服务器:

ssh-copy-id adminuser@服务器IP

测试密钥登录成功后,再修改sshd_config:

PasswordAuthentication no
PubkeyAuthentication yes
ChallengeResponseAuthentication no
UsePAM no

注意UsePAM设为no可以进一步减少密码认证的依赖,但某些系统可能依赖PAM做其他认证,建议先测试密钥登录完全正常后再修改。

修改默认SSH端口

默认22端口是扫描器重点攻击目标。修改为高位端口能减少大量自动化攻击噪音。在sshd_config中找到Port 22,改为一个不常用的端口,例如:

Port 2299

修改后需要同步更新防火墙规则。如果使用ufw:

sudo ufw allow 2299/tcp
sudo ufw delete allow 22/tcp

如果使用云服务商的安全组,也要在控制台放行新端口并关闭22端口。修改端口不是安全手段,但能显著降低日志中的无效扫描记录,让真正的攻击更容易被发现。

限制允许登录的用户和组

即使系统中有多个用户,也不应该让所有用户都能SSH登录。使用AllowUsers或AllowGroups明确指定允许登录的账户。在sshd_config末尾添加:

AllowUsers adminuser

或者使用组控制:

AllowGroups sshusers

然后将需要登录的用户加入sshusers组。这种方式比逐个用户指定更易维护。同时可以使用DenyUsers和DenyGroups显式拒绝特定账户。

配置空闲超时和登录尝试限制

SSH连接长时间空闲不关闭,容易被利用。在sshd_config中设置:

ClientAliveInterval 300
ClientAliveCountMax 2

这表示每300秒发送一次心跳包,如果连续2次无响应则断开连接,空闲超时约10分钟。登录尝试次数限制需要配合PAM或fail2ban实现,但SSH本身可以设置最大认证尝试次数:

MaxAuthTries 3

超过3次认证失败直接断开,能有效减缓在线爆破速度。

禁用不安全的SSH协议版本和弱加密算法

SSH协议版本1存在严重安全缺陷,必须禁用。在sshd_config中确认:

Protocol 2

同时限制加密算法,只允许强加密和强MAC:

Ciphers aes256-gcm@openssh.com,chacha20-poly1305@openssh.com,aes256-ctr
MACs hmac-sha2-512-etm@openssh.com,hmac-sha2-256-etm@openssh.com,hmac-sha2-512,hmac-sha2-256
KexAlgorithms curve25519-sha256,curve25519-sha256@libssh.org,diffie-hellman-group16-sha512,diffie-hellman-group18-sha512

这些算法列表在OpenSSH 7.6及以上版本都支持。配置后需要重启SSH服务并测试连接,确保客户端也支持这些算法。

使用TCP Wrappers或防火墙限制来源IP

如果服务器只面向固定IP地址管理,最有效的安全措施是直接限制来源。使用ufw限制SSH端口只允许特定IP访问:

sudo ufw allow from 203.0.113.5 to any port 2299 proto tcp
sudo ufw deny 2299/tcp

这样即使SSH配置存在漏洞,攻击者也无法从其他IP建立连接。对于没有固定IP的情况,可以考虑使用跳板机或至少限制到所属运营商的IP段。

启用SSH日志详细记录

默认SSH日志级别为INFO,建议调整为VERBOSE以记录更详细的认证信息。在sshd_config中设置:

LogLevel VERBOSE

同时确认rsyslog配置中auth日志被记录。Ubuntu默认将SSH日志写入/var/log/auth.log。定期检查该文件,关注大量失败尝试、异常登录时间和陌生IP。

安装并配置fail2ban自动封禁

fail2ban监控日志中的失败认证记录,自动将攻击源IP加入防火墙黑名单。安装:

sudo apt update
sudo apt install fail2ban

创建本地配置文件:

sudo cp /etc/fail2ban/jail.conf /etc/fail2ban/jail.local

在jail.local中找到[sshd]部分,设置:

[sshd]
enabled = true
port = 2299
maxretry = 3
bantime = 3600
findtime = 600

这表示10分钟内失败3次就封禁1小时。重启fail2ban服务:

sudo systemctl restart fail2ban

查看封禁状态:

sudo fail2ban-client status sshd

fail2ban是动态防御,能应对分布式低速爆破,比单纯依赖SSH自身限制更有效。

定期更新系统和OpenSSH

Ubuntu和OpenSSH会定期发布安全补丁。保持系统更新是基础安全措施:

sudo apt update
sudo apt upgrade

对于生产服务器,建议配置自动安全更新:

sudo apt install unattended-upgrades
sudo dpkg-reconfigure --priority=low unattended-upgrades

自动更新只安装安全补丁,不升级大版本,风险可控。

配置完成后验证和测试

每次修改sshd_config后,先检查配置语法:

sudo sshd -t

没有输出表示配置正确。然后重启SSH服务:

sudo systemctl restart sshd

重启后不要关闭当前连接,新开一个终端测试登录。确认新配置生效且能正常登录后,再关闭旧连接。如果服务器有控制台访问,建议在控制台保留一个会话,防止配置错误导致完全无法连接。

独到见解:安全加固不是一次性任务

很多管理员做完上述配置后就认为SSH安全了,实际上安全是一个持续过程。建议每季度检查一次auth.log中的异常记录,每月检查fail2ban封禁列表,关注是否有大量来自特定网段的攻击。另外,如果服务器有多个管理员,应该为每个人分配独立的SSH密钥,而不是共享一个密钥。密钥丢失或人员离职时,及时从authorized_keys中删除对应公钥。对于高安全要求的服务器,可以考虑使用SSH证书认证替代传统公钥认证,实现密钥的集中管理和过期机制。这些措施配合上述基础加固,才能让Ubuntu服务器的SSH服务在公网环境中保持足够的安全性。