你如何防止 SourceTree/SSH 忘记你的 SSH 密钥? (我必须手动重新 运行 'ssh-add' 让它再次工作!)

How do you keep SourceTree/SSH from forgetting your SSH keys? (I have to manually re-run 'ssh-add' to get it to work again!)

更新 - 又发生了!!!

好的,所以这 又发生了!男人真是令人沮丧!但是这次我挖得更深一点,发现不知为什么,我的私钥被卸载了。

具体来说,当我调用这个...

ssh-add -l -E md5

我明白了...

The agent has no identities.

但是,如果我然后 运行 这个...

ssh-add /Users/[username]/.ssh/[private key]

一切恢复正常! SourceTree 连接正常。

问题是 为什么我必须保留 运行ning 'ssh-add' 命令?!为什么它总是忘记我的钥匙?!

如其他地方所述,不确定这是否会有所不同,但我正在 运行 配备 High Sierra 的 MacBook Pro,尽管在 Sierra 上也会发生这种情况。

原文Post:

这个让我既难过又恼火!! SourceTree(或 ssh 或其他东西!)每天都会 forgetting/not applying/ignoring 我的 SSH 密钥!不知道为什么。

Note: Updated to use BitBucket's info instead of GitHub.

这是我当前 config 文件的相关部分

# --- Sourcetree Generated ---
Host MarqueIV-Bitbucket
    HostName bitbucket.org
    User MarqueIV
    PreferredAuthentications publickey
    IdentityFile /Users/MarqueIV/.ssh/MarqueIV-Bitbucket
    UseKeychain yes
    AddKeysToAgent yes
# ----------------------------

这是我的 ~/.ssh 文件夹的 'ls'(t运行 已分类)

-rw-r--r--@ 1 MarqueIV  staff   421 Dec 14 11:25 config
-rw-r--r--@ 1 MarqueIV  staff  1808 Dec  9 14:20 known_hosts
-rw-------  1 MarqueIV  staff  3243 Dec  6 23:33 MarqueIV-Bitbucket
-rw-r--r--  1 MarqueIV  staff   781 Dec  6 23:33 MarqueIV-Bitbucket.pub

这是我的 known_hosts 文件(密钥已编辑)

bitbucket.org,104.192.143.3 ssh-rsa [redacted]
bitbucket.com,104.192.143.9 ssh-rsa [redacted]
104.192.143.2 ssh-rsa [redacted]

Note: Not sure if this matters, but you can see lines 1 and 2 seem to be duplicates.

这是 ssh -Tv git@bitbucket.org

的输出
OpenSSH_7.6p1, LibreSSL 2.6.2
debug1: Reading configuration data /Users/MarqueIV/.ssh/config
debug1: Reading configuration data /etc/ssh/ssh_config
debug1: /etc/ssh/ssh_config line 48: Applying options for *
debug1: Connecting to bitbucket.org port 22.
debug1: Connection established.
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_rsa type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_rsa-cert type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_dsa type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_dsa-cert type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_ecdsa type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_ecdsa-cert type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_ed25519 type -1
debug1: key_load_public: No such file or directory
debug1: identity file /Users/MarqueIV/.ssh/id_ed25519-cert type -1
debug1: Local version string SSH-2.0-OpenSSH_7.6
debug1: Remote protocol version 2.0, remote software version conker_1.0.315-a08d059 app-153
debug1: no match: conker_1.0.315-a08d059 app-153
debug1: Authenticating to bitbucket.org:22 as 'git'
debug1: SSH2_MSG_KEXINIT sent
debug1: SSH2_MSG_KEXINIT received
debug1: kex: algorithm: curve25519-sha256@libssh.org
debug1: kex: host key algorithm: ssh-rsa
debug1: kex: server->client cipher: aes128-ctr MAC: hmac-sha2-256-etm@openssh.com compression: none
debug1: kex: client->server cipher: aes128-ctr MAC: hmac-sha2-256-etm@openssh.com compression: none
debug1: expecting SSH2_MSG_KEX_ECDH_REPLY
debug1: Server host key: ssh-rsa SHA256:zzXQOXSRBEiUtuE8AikJYKwbHaxvSc0ojez9YXaGp1A
debug1: Host 'bitbucket.org' is known and matches the RSA host key.
debug1: Found key in /Users/MarqueIV/.ssh/known_hosts:1
debug1: rekey after 4294967296 blocks
debug1: SSH2_MSG_NEWKEYS sent
debug1: expecting SSH2_MSG_NEWKEYS
debug1: SSH2_MSG_NEWKEYS received
debug1: rekey after 4294967296 blocks
debug1: SSH2_MSG_SERVICE_ACCEPT received
debug1: Authentications that can continue: publickey
debug1: Next authentication method: publickey
debug1: Offering public key: RSA SHA256:h+6zCXg32Uw4fYxSUMwYst3zee8RFb9Z47H1QUTz58E /Users/MarqueIV/.ssh/MarqueIV-GitHub
debug1: Authentications that can continue: publickey
debug1: Trying private key: /Users/MarqueIV/.ssh/id_rsa
debug1: Trying private key: /Users/MarqueIV/.ssh/id_dsa
debug1: Trying private key: /Users/MarqueIV/.ssh/id_ecdsa
debug1: Trying private key: /Users/MarqueIV/.ssh/id_ed25519
debug1: No more authentication methods to try.
git@bitbucket.org: Permission denied (publickey).

看看它似乎没有应用 configknown_hosts 中定义的密钥?好像这会是个问题,不是吗?

Note: I'm using macOS Sierra, and I have updated my path to include /usr/bin before /usr/local/bin as outlined here. If I don't do that, I get an error saying ssh doesn't recognize UseKeychain yes in the config.

因此,几乎每天都是我必须经历的例行程序。我将使用 GitHub 作为示例。

  1. 我打开 SourceTree 并尝试从 GitHub 中提取最新的。它失败并显示 'git@github.com: Permission denied (publickey).' 消息。

  2. 我从 SourceTree 中删除了我的 GitHub 帐户。

  3. 我从我机器上的 .ssh 文件夹中删除了 public 和 GitHub 的私钥。

  4. 我转到 GitHub 并从我的帐户中删除旧的 public 密钥。

  5. 回到 SourceTree,我再次使用我的用户名和密码登录 GitHub。

  6. 登录后,使用 SourceTree,我为 GitHub 生成了一个新的 SSH 密钥对。

  7. 我将我的 public 密钥复制到我的 GitHub 帐户中的 SSH 区域。 (有时我注意到它为我添加了它,但我喜欢安全并仔细检查。)

  8. 现在又可以推拉了

我今天回家,在家登录。它再次失败。重复上述所有步骤。

如何让 SourceTree/ssh/whatever 记住我的 da*n 键,这样我就不必在每次更改位置时都这样做?!我错过了哪一步???

那么谁能就如何制作我的 SSH 密钥提供建议 'stick'?

首先,安装 latest Git for Windows release (the 2.15.1.2 one, by simply uncompressing the archive PortableGit-2.15.1.2-64-bit.7z.exe anywhere you want, and )

其次,请确保您的 SourceTree is using the System Git

三、test in command-line if your ssh key is recognized:

ssh -T git@github.com

Hi username! You've successfully authenticated, 
but GitHub does not provide shell access.

最后,确保 SourceTree / Tools / Option 使用 OpenSSH 客户端(不是 putty)

那么 SourceTree 在重用您的 ssh 密钥时应该没有问题。


根据您的日志,~/.ssh/config 生成是错误的:它提到您的用户名作为用户。
每当您与 github.com/bitbucket.org 建立 SSH 连接时,它永远不会像 "you" 那样。它总是 git.

Host MarqueIV-Bitbucket
    HostName bitbucket.org
    User MarqueIV
    PreferredAuthentications publickey
    IdentityFile /Users/MarqueIV/.ssh/MarqueIV-Bitbucket
    UseKeychain yes
    AddKeysToAgent yes

使用 ssh -Tv MarqueIV-Bitbucket

进行测试

那个~/.ssh/config摘录只适用于宿主MarqueIV-Bitbucket。如果您的 SSH 遥控器被列为 MarqueIV-Bitbucket:owner/repo,那么 SSH 和 SourceTree 应该 遵守该配置;您可以使用 ssh -Tv MarqueIV-Bitbucket 并通过将一个或多个遥控器更新为 MarqueIV-Bitbucket:owner/repo.git 格式来确认这一点。

好的,我想我已经弄清楚了所有的部分。

为了帮助人们得到他们想要的东西,这里是最前面的解决方案:

  1. 确保您要使用的密钥有密码保护,否则它们将不会添加到钥匙串。
  2. 确保在 config 文件中配置了您想要 auto-load 的键,并设置了 UseKeychainAddKeysToAgent
  3. 确保从终端连接到 config-defined 主机 !!
  4. 为 运行 创建 LaunchAgent ssh-add -A 以自动重新加载您的 Keychain-stored 密钥

好的,现在您知道该怎么做了,下面是 'why'。

正如我在问题中所解释的,最近,每当我重新启动时,我(错误地)认为系统正在丢失我的私钥。它并没有失去它们,只是无视它们。这是因为对于像我这样从不使用终端 GIT.

的人来说,一堆事情汇集在一起​​形成了一场完美的混乱风暴。
  1. 在 macOS 的最新版本中,Apple 更改了 SSH 的实现方式,以便更好地匹配 OpenSSH
  2. 的实现
  3. 作为 #1 的结果,ssh-add -K [privateKey] 不再将密钥存储在钥匙串中(它基本上忽略了 -K。)虽然它们确实被添加到该会话的 ssh 中——并且因此您的连接将再次工作——一旦您重新启动,它们将不再工作。 (这就是让我发疯的原因!)
  4. 即使对于钥匙串中 的钥匙,Apple 也不再自动加载它们,这意味着您每次都必须从终端手动调用 ssh-add -A 来重新加载它们重启。
  5. 但是,如上所述,ssh-add -K [privateKey] 不再将钥匙添加到钥匙串中,因此 ssh-add -A 对于以这种方式添加的钥匙来说无论如何都是毫无意义的。 (可以通过其他方式将它们添加到钥匙串。稍后会详细介绍。)

由于上述原因,在升级 OS 之前使用 -K 选项手动添加的任何密钥仍将位于您的钥匙串中。但是,Apple更改后添加的键不是。

也就是说,Apple 仍然可以将密钥存储在钥匙串中,但不能再来自 ssh-add。它现在仅适用于 config 文件中定义的主机。

现在这是将钥匙放入钥匙串的唯一方法。

同样,这是我的配置:

Host MarqueIV-Bitbucket
    HostName bitbucket.org
    User git <-- Make sure this is 'git', not what SourceTree puts here
    PreferredAuthentications publickey
    IdentityFile /Users/MarqueIV/.ssh/MarqueIV-Bitbucket
    UseKeychain yes    <-- Note here
    AddKeysToAgent yes <-- ...and here

但是等等!如果您查看我的配置文件,它 确实 设置了这些值!那么为什么它不起作用?

两件事。

  1. 我从不使用终端。我使用 SourceTree,它不使用该文件中的主机条目
  2. Apple 在技术上只在访问该主机时按需添加(和存储)密钥,而不是在(重新)加载文件时添加(和存储)密钥,这意味着除非您明确访问该主机,否则什么也不会发生。

在我的例子中,通过 SourceTree 添加密钥会在初始会话中添加它们,但是一旦我重新启动,密钥将再次无法加载,因此所有连接都会失败。 ssh-add -A 也不会修复它,因为它们又不在钥匙串中,这意味着我又回到了使用 ssh-add [privateKey] 在命令行上手动添加每个。好痛!!

然后我想到...如果该设置在配置文件中,并且可以从命令行使用该条目,那么我不应该能够直接连接到该主机,从而添加我的钥匙串的钥匙?让我们找出答案!我输入了这个...

ssh -T MarqueIV-BitBucket

果然,密钥不仅添加到 ssh 中,而且还再次添加到我的钥匙串中!我通过直接检查 Keychain Access 确认了这一点,它就在那里。

为了进一步测试,我运行这个...

ssh-add -D

删除了我所有的密钥。果然,我的SourceTree连接又全部失败了。

那我运行这个...

ssh-add -A

和 keychain-stored 键神奇地回来了,连接又开始工作了!哇!!

好的,差不多了,但还不完全是!重启怎么样?同样,Apple 不再自动从 Keychain 加载密钥。当然,现在只需快速到终端输入 ssh-add -A,但我不应该那样做!

进入 LaunchAgents!

LaunchAgents 和 LaunchDaemons 不在此讨论 post,但简而言之,它们允许您在重新启动时、按计划、系统发生更改等时执行某些操作

就我而言,我想要的东西在我登录 mac 时会 运行,因此 LaunchAgent 是最佳选择。

这是我的 plist,它定义了每次我登录我的帐户时如何执行 ssh-add -A(即使我从未接触过终端):

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>Label</key>
    <string>ssh-add-a</string>
    <key>ProgramArguments</key>
    <array>
        <string>ssh-add</string>
        <string>-A</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
</dict>
</plist>

因为我只想为我的特定用户使用它,所以我将它存储在这里:

~/Library/LaunchAgents

Note: Make sure to change the permissions to allow it to be executed, or it won't start!

果然,在重新启动时,我的所有密钥都恢复并处于活动状态!连接一切正常,children 播放,大人哭了,Code-dom!

是美好的一天

回顾一下:

  1. Apple 改变了 SSH 的工作方式
  2. 密钥不再从命令行添加到钥匙串
  3. Apple 也不再auto-loaded 存储在钥匙串
  4. 中的密钥
  5. 使用终端连接到 config-defined 固定的主机 #2
  6. 使用 LaunchAgent 修复 #3

希望对您有所帮助!现在是时候去拿一些 Icy-Hot 来治疗我的肩膀酸痛了,我一直在努力地拍打自己以解决这一切! ;)