Linux 下使用 SSH 免密登录的不同姿势
一、背景概述
ssh
这个命令算作是学习 Linux 时最基础的命令之一了。之前使用 ssh 时,都是通过用户名 + 密码的形式进行登录的。之前写 TransFile-Shell 小工具[[1]](https://gitee.com/lwx19960428...,曾经通过服务端配置客户端公钥的方式进行免密登录,这两天给朋友解决问题时,接触到 Jenkins 执行远程脚本的功能,涉及到了 SSH-Agent 做代理请求的功能,现在把几种方式都作为笔记写下来。
二、SSH 介绍
根据百度百科介绍:SSH 是建立在应用层基础上的安全协议。SSH 是目前较可靠,专为远程登录会话和其他网络服务提供安全性的协议。利用 SSH 协议可以有效防止远程管理过程中的信息泄露问题[[2]](https://baike.baidu.com/item/...。
从客户端来看,SSH 有两种形式的安全验证方式:
- 基于口令(密码)的验证方式
- 基于密钥的验证方式
口令验证因无法保证正在连接的服务器就是真正想要的服务器,所以可能存在服务端被冒充(中间人攻击)的方式。而密钥验证则是依赖客户端服务端之间的公私钥加解密方式,故不存在中间人攻击(中间人没有任何一端的私钥),但同时整个过程需要相对较长的时间。
具体的 ssh 相关资料可参照后续的参考链接进行了解。
三、实验环境
进行下述实验步骤前,请确认服务器已开启 SSH 服务,且相关端口的网络策略已经开通。
角色 | 主机名 | IP 地址 | 系统 |
---|---|---|---|
客户机 A | local-vmware-01 | 192.168.36.129 | CentOS 7.4 |
客户机 B | local-vmware-03 | 192.168.36.133 | CentOS 7.4 |
服务机 | local-vmware-02 | 192.168.36.132 | Ubuntu 18.04 LTS |
四、服务端配置公钥信任来实现免密登录
未配置公私钥对时,客户机 A 通过 SSH 登陆时,登陆提示需要密码。
ssh dcos@192.168.36.132
为了免密,一路回车,生成 SSH 要用的公私钥对,此步骤在客户机 A 执行。根据提示,生成出来的公私钥文件位于 ~/.ssh
目录下,其中 id_rsa
为私钥,id_rsa.pub
为公钥。
ssh-keygen -t rsa
将客户机 A 的公钥内容复制出来,粘贴至服务机的 ~/.ssh/authorized_keys
文件中。
# local-vmware-01 上执行 cat ~/.ssh/id_rsa.pub # local-vmware-02 上执行 # 如果不存在 ~/.ssh 此目录,则需要先行手动创建,创建完注意同时赋权 700 mkdir ~/.ssh && chmod 700 ~/.ssh # 文件不存在,则 Vim 将自动创建该文件;如已存在,注意与之前记录间增加换行 vi ~/.ssh/authorized_keys # 同时,此文件需要赋权 600 权限,不允许其他用户修改 chmod 600 ~/.ssh/authorized_keys
再次通过 SSH 登录,不再需要密码即可重新登录,使用 scp
命令等也是一样,不再需要输入密码。至此,通过添加客户机公钥信任来实现免密登录已经完成。
五、客户端通过私钥身份信息实现登录
上述方式可以很方便的通过公私钥的配置进行 SSH 的免密登录,但当我们无法拿到客户机的公钥时,就需要通过 ssh-agent
进行代理登录。
什么都不做配置,在客户机 B 上通过 SSH 访问,提示需要输入密码。
因为客户机 A 已配置好了公钥信任,接下来我们将在客户机 B 上通过 ssh-agent 的形式来进行代理登录。
将客户机 A 的 id_rsa
私钥文件上传到客户机 B 中,同时设置其权限为 600,以上传到家目录为例。
# local-vmware-03 上执行 chmod 600 ~/id_rsa
(一)通过 ssh-agent 形式进行代理登录
通过如下命令启动 ssh-agent 服务、增加身份密钥、登录认证等步骤,可不用密码登陆服务机。
# 启动ssh-agent服务 ssh-agent # 启动ssh-agent bash服务 ssh-agent bash --login -i # 增加私钥文件 ssh-add ~/id_rsa # 重新SSH进行登录,不再需要输入密码 ssh dcos@192.168.36.132
(二)通过 ssh -i 形式进行代理登录
之前的 ssh 命令登录相当于是增加了默认的 -i ~/.ssh/id_rsa
参数,当一台 Linux 机器生成了多个 ssh 密钥时,就需要通过 -i 参数的形式来指定使用哪个私钥文件参与到 ssh 连接的过程。同理,这种形式则是相当于自定义了 id_rsa 文件的位置,并未有太大的亮点。
# local-vmware-03 上执行 ssh -i ~/id_rsa dcos@192.168.36.132
六、踩坑记录
在 Jenkins 中配置 ssh-agent 时,每一步都配置的没有问题,直接在 Jenkins 服务器上用 ssh-agent 工具也可以登录,但是每次构建时都提示 Host key verification failed.
的报错。
经过分析,得出结论,是由于第一次登录时需要输入 yes / no 导致的认证失败。要想解决此问题,可通过在连接命令上增加 -o "StrictHostKeyChecking no"
来解决此问题[[3]](https://blog.csdn.net/ITzhang...。
ssh -o "StrictHostKeyChecking no" dcos@192.168.36.132
七、总结
通过上述几种免密登录方式的配置,我们可以 Get 到以下几个知识点:
- SSH 认证与身份文件紧紧相关,不同的服务器使用同一份私钥文件是可以的。
- 私钥文件极其重要,一定要保管好自己的私钥文件。
- 遇到坑的时候,多查一些资料,以及相关的 Linux man 文档,总会爬出来的。
八、参考资料
[1] https://gitee.com/lwx19960428...
[2] https://baike.baidu.com/item/...