5月28日 00:54

SSH 配置文件有哪些常用选项?如何通过配置文件简化连接管理?

SSH 配置文件(~/.ssh/config 和 /etc/ssh/sshd_config)是管理和简化远程连接的核心工具。掌握常用选项后,可以将冗长的命令行参数转化为可复用的配置块,实现连接复用、跳板代理和端口转发等高级功能,大幅提升日常运维效率。

客户端配置文件(~/.ssh/config)

配置文件位置与优先级

SSH 客户端从三个来源读取配置,优先级从高到低:

  1. 命令行参数:如 ssh -p 2222 user@host,优先级最高
  2. 用户配置文件~/.ssh/config(最常用,日常管理的核心)
  3. 全局配置文件/etc/ssh/ssh_config(系统管理员设置默认值)

三个来源的配置合并后生效,命令行参数覆盖用户配置,用户配置覆盖全局配置。注意:用户配置文件权限必须为 600,否则 SSH 会拒绝读取。

基本连接配置

bash
# ~/.ssh/config # 最基本的主机配置 Host server1 HostName 192.168.1.100 User admin Port 2222 IdentityFile ~/.ssh/id_ed25519 # 使用别名简化连接 Host prod HostName prod.example.com User deploy IdentityFile ~/.ssh/prod_key

配置完成后,ssh prod 等价于 ssh -i ~/.ssh/prod_key deploy@prod.example.com,无需记忆每台服务器的连接参数。

通配符与批量配置

Host 指令支持通配符 *?,可以对一组主机应用相同配置:

bash
# 对所有 example.com 主机使用相同用户和密钥 Host *.example.com User webadmin IdentityFile ~/.ssh/web_key # 对所有连接启用连接保持 Host * ServerAliveInterval 60 ServerAliveCountMax 3

关键细节:SSH 按配置文件中的顺序逐段匹配 Host,第一个匹配段中出现的选项生效,不会与后续段合并。因此通配符配置应放在文件末尾,避免被提前匹配覆盖。

连接复用(ControlMaster)

连接复用是 SSH 最实用的性能优化手段。首次连接建立 master 连接并创建 socket 文件,后续到同一主机的连接直接复用该通道,跳过认证和握手过程:

bash
Host * ControlMaster auto ControlPath ~/.ssh/sockets/%r@%h-%p ControlPersist 600

各参数含义:

参数说明
ControlMaster auto自动创建新连接或复用已有 master 连接
ControlPathsocket 文件路径,%r 远程用户名、%h 主机名、%p 端口
ControlPersist 600最后一个会话关闭后,master 连接保持 600 秒

使用前需创建 socket 目录:mkdir -p ~/.ssh/sockets。管理命令:ssh -O exit hostname 关闭复用连接,ssh -O check hostname 查看复用状态。

跳板机配置

ProxyJump(推荐,OpenSSH 7.3+)

bash
Host jump HostName jump.example.com User jumper IdentityFile ~/.ssh/jump_key Host internal HostName 10.0.0.50 User root ProxyJump jump

ProxyJump 语法简洁,支持多跳串联:ProxyJump jump1,jump2。命令行等价写法:ssh -J jump internal

ProxyCommand(兼容旧版本)

bash
Host internal HostName 10.0.0.50 User root ProxyCommand ssh -W %h:%p jump.example.com

核心区别:ProxyJump 是 ProxyCommand 的高层封装,底层都是通过跳板机建立到目标的 TCP 通道。两者互斥,不能同时配置。OpenSSH 7.3 以下只能用 ProxyCommand。

端口转发配置

SSH 支持三种端口转发,都可以写入配置文件持久化:

bash
# 本地端口转发:将远程 Redis 映射到本地 Host db-tunnel HostName db.example.com User admin LocalForward 16379 127.0.0.1:6379 # 远程端口转发:将本地服务暴露到远程 Host expose-local HostName remote.example.com User admin RemoteForward 8080 127.0.0.1:3000 # 动态端口转发:SOCKS5 代理 Host socks-proxy HostName tunnel.example.com User admin DynamicForward 1080

三种转发的区别:

类型配置项数据流方向典型场景
本地转发LocalForward本地 → 远程内网访问远程数据库
远程转发RemoteForward远程 → 本地将本地服务暴露给远程
动态转发DynamicForward本地 → 任意(SOCKS5)通过 SSH 安全代理上网

Include 指令与配置拆分

OpenSSH 7.3+ 支持 Include 指令,可将配置按项目或环境拆分为多个文件:

bash
# ~/.ssh/config Include ~/.ssh/config.d/* # ~/.ssh/config.d/work Host prod-* User deploy IdentityFile ~/.ssh/work_key # ~/.ssh/config.d/personal Host github HostName github.com User git IdentityFile ~/.ssh/personal_key

这种方式便于按项目或环境管理配置,也方便脚本自动化生成。Include 可以出现在配置文件的任何位置,被包含的文件内容在该位置展开。

Token 替换

配置文件中的部分选项支持 Token 动态替换:

Token含义常见用途
%h远程主机名ControlPath、ProxyCommand
%p远程端口号ControlPath、ProxyCommand
%r远程用户名ControlPath
%d本地用户家目录IdentityFile 路径
%u本地用户名日志路径

其他常用选项

选项默认值说明
IdentitiesOnly yesno只使用配置的密钥,防止 ssh-agent 干扰
Compression yesno启用压缩,低带宽环境有效
StrictHostKeyCheckingask主机密钥验证策略:ask/yes/no
ForwardAgent yesno转发认证代理,用于跳板机链式认证
ConnectTimeout 10连接超时秒数
ServerAliveInterval 600客户端心跳间隔,防止连接被防火墙断开

服务器端配置文件(/etc/ssh/sshd_config)

认证与安全加固

bash
# /etc/ssh/sshd_config # 认证方式 PasswordAuthentication no # 禁用密码认证,只允许密钥登录 PubkeyAuthentication yes # 启用公钥认证 PermitRootLogin prohibit-password # 允许 root 但禁止密码登录 MaxAuthTries 3 # 限制单次连接认证尝试次数 # 访问控制(白名单优先) AllowUsers admin deploy # 只允许这些用户登录 AllowGroups ssh-users # 只允许这些组登录 DenyUsers test guest # 拒绝这些用户登录

PermitRootLogin prohibit-passwordno 更灵活:允许 root 通过密钥登录但禁止密码,适合需要 root 权限的自动化脚本。

连接与性能

bash
MaxStartups 10:30:100 # 未认证连接速率限制:10个开始拒绝30%,100个全部拒绝 LoginGraceTime 60 # 认证超时时间(秒) ClientAliveInterval 300 # 服务器端心跳间隔(秒) ClientAliveCountMax 2 # 心跳无响应次数上限

功能开关

bash
X11Forwarding no # 禁用 X11 转发 AllowTcpForwarding yes # 允许 TCP 转发 GatewayPorts no # 禁止远程转发绑定非本地地址 PermitTunnel no # 禁用 tun 设备

Match 条件块

sshd_config 支持 Match 指令,按条件应用不同配置,实现精细化访问控制:

bash
# 内网允许密码认证 Match Address 192.168.1.0/24 PasswordAuthentication yes # 特定用户允许端口转发 Match User deploy AllowTcpForwarding yes GatewayPorts clientspecified # 特定组禁用端口转发 Match Group restricted AllowTcpForwarding no

Match 支持的条件:User、Group、Host、Address,可组合使用。

常见面试追问

ProxyJump 和 ProxyCommand 有什么区别?

ProxyJump 是 ProxyCommand 的高层封装(OpenSSH 7.3+),语法更简洁。底层原理相同:都是通过跳板机建立到目标主机的 TCP 通道。ProxyJump 支持逗号分隔的多跳串联(ProxyJump j1,j2),而 ProxyCommand 实现多跳需要嵌套。两者互斥,不能同时配置。

ControlPath 中 %r %h %p 分别代表什么?

%r 是远程用户名,%h 是远程主机名,%p 是远程端口号。这三个 Token 组合可以确保到不同主机的连接使用不同的 socket 文件,避免复用冲突。

StrictHostKeyChecking 三个值有什么区别?

ask(默认)首次连接时提示确认主机指纹;yes 只允许 known_hosts 中已有的主机连接,未知主机直接拒绝;no 自动接受新主机密钥存入 known_hosts。生产环境建议 askyesno 存在中间人攻击风险。

ClientAliveInterval 和 ServerAliveInterval 有什么区别?

两者都是心跳机制,但发起方和用途不同。ServerAliveInterval 由客户端定期发心跳给服务器,防止客户端侧连接被防火墙或 NAT 设备断开。ClientAliveInterval 由服务器定期发心跳给客户端,用于检测客户端是否存活并主动断开僵死连接。

标签:SSH