首先我得说和 ssh 相关的一切机制的确比较复杂,很容易让人晕头转向,若是你想完全掌握这个知识体系就必须系统的学习一下相关的知识。因此 first thing first,我推荐一本书给你,不妨抽时间把它一劳永逸了: git
SSH, The Secure Shell,这本书的初版有中文的。 github
接着说你的这个特定的问题。 shell
你首先得了解一件事:ssh-add 这个命令不是用来永久性的记住你所使用的私钥的。实际上,它的做用只是把你指定的私钥添加到 ssh-agent 所管理的一个 session 当中。而 ssh-agent 是一个用于存储私钥的临时性的 session 服务,也就是说当你重启以后,ssh-agent 服务也就重置了。 安全
若是是为了永久记住对应的私钥是哪一个,咱们不能依赖 ssh-agent 服务。能依赖什么则取决于如下哪些方案适合你的使用场景。 ruby
你没有在问题里描述你所使用的操做系统,因此我以我平常使用的 Mac OS X 为例。Mac 系统内置了一个Keychain 的服务及其管理程序,能够方便的帮你管理各类秘钥,其中包括 ssh 秘钥。ssh-add 默认将制定的秘钥添加在当前运行的 ssh-agent 服务中,可是你能够改变这个默认行为让它添加到 keychain 服务中,让 Mac 来帮你记住、管理并保障这些秘钥的安全性。 bash
你所要作的就是执行下面的命令: session
$ ssh-add -K [path/to/your/ssh-key]
以后,其余的程序请求 ssh 秘钥的时候,会经过 Keychain 服务来请求。下面的截图里你能够看到我当前的机器上 Keychain 为我管理的有关 ssh 的秘钥,这其中包括我本身生成的四个,以及 Github Client App 本身使用的一个——前者几个都是供 ssh 相关的命令所使用,然后者则指明了仅供 Github.app 这个应用程序使用。 另外,它们都是 login keychains 也就是只有当前用户登陆以后才会生效的,换了用户或是未登陆状态是不能使用的,这就是 Keychain 服务所帮你作的事情。 app
这个问题也是我没有彻底吃透的,按照某些资料描述,作了以上的工做以后,应用程序应该可以自动匹配适用的 ssh 秘钥了。可是在我学习的过程当中也遇到过非得手动指定的状况(那个时候我还不了解 Keychain 的做用,都是手动去 ssh-add 的),因而另一种机制能够帮你解决这个问题,即 ssh config。 ssh
一言蔽之,ssh config 就是一个配置文件,描述不一样的秘钥对应的设置——包括主机名、用户名、访问策略等等。 工具
如下我截取了本地配置的两个片断:
这两段配置分别对应 Github 和 Coding 这两个服务所使用的秘钥。第一行的 Host 只是一个名字,第三行的Hostname 才是对应的真实地址,可是二者最好保持一致,这样不用在脑壳里转换。
用这样的配置,当我 git clone https://github.com/user/repo 的时候,id_rsa 秘钥会被使用,当我git clone https://coding.net/user/repo 的时候,很显然 nightire 秘钥会被使用。
固然,此配置不局限于 Git,全部底层使用 SSH 的应用和命令都会遵守配置文件的指示来找到对应的私钥。
回到本节开始的话题,我相信有了 Keychain 作管理应该是不须要这个配置文件的,可是我尚未机会去作测试。目前的环境一切正常,等到我换新机器从新配置环境的时候我会试一试看。
关于 Host 和 Hostname 的对应关系,若是 Hostname 是域名则最好保持一致。可是这里有两个诀窍:
1. 若是同一域名下有两个不一样的配置怎么办?
以 Github 为例,若是我有两个帐户,一个我的的,一个组织的,而且要使用不一样的秘钥,那么我能够这么写:
这里 Host 后面对应的是 Github 的两个用户名,也就是 github.com/nightire 和 github.com/very-geek
2. 若是域名是数字 IP,是否能够简化呢?
Host 能够帮助你把对应的 IP 变成好记的名字。好比说我在公司内部配置了 Git Server(基于 gitolite 或 Gitlab 或任何工具),正常的访问地址是:git://xxx.xxx.xxx.xxx:repo.git,以下的配置则能够帮你把它简化成:git.visionet:repo.git
很是有用。
有。若是 ssh-add 已经能够知足你的要求(除了启动之后还要再来一遍之外),那么你彻底能够用脚本自动化这件事。简单地把你输入的 ssh-add 命令的内容写进 .bashrc 或 .bash_profile(或其余任何你使用的 shell 环境配置文件)中去,这样只要你打开终端,就等于自动作了这件事情。
不过如我以前所说,这个机制是依赖 ssh-agent 服务的,而且只能在终端下有效。而用 Keychain 机制的话,是整个系统内都有效的(包括不依赖终端的应用程序)而且无需开启 ssh-agent 服务。
最后 Keychain 服务不是只有 Mac 才有的,我刚才搜索了一下,Windows 和 各类 Linux 都有对应的机制,不过我没用过,只能以 Mac 为例了。了解了这些概念,相信你能够本身查获得具体的方法。