“警告:远程主机标识已更改”— GitHub 是否更改了他们的 RSA 密钥?

问题描述 投票:0回答:6

就在不久前,我在推送到 GitHub 时开始收到此警告。

WARNING: REMOTE HOST IDENTIFICATION HAS CHANGED!

IT IS POSSIBLE THAT SOMEONE IS DOING SOMETHING NASTY!
Someone could be eavesdropping on you right now (man-in-the-middle attack)!
It is also possible that a host key has just been changed.

这是否正常,我该如何解决?

git github ssh ssh-keys
6个回答
579
投票

发生这种情况是因为在 2023 年 3 月 24 日,GitHub 更新了他们的 RSA SSH 主机密钥 用于保护 GitHub.com 的 Git 操作,因为私钥曾短暂暴露在公共 GitHub 存储库中。如果您在该日期之前记得 GitHub 在 SSH 客户端中的先前密钥指纹,您将收到该消息。

根据链接的博客文章,解决方案是通过运行此命令删除旧密钥:

$ ssh-keygen -R github.com

现在下一个

git
连接(拉、推或克隆)应该询问您是否信任新的 SSH 密钥。在输入
yes
之前,使用列表确保显示的新密钥有效:

https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/githubs-ssh-key-fingerprints

请参阅博文了解其他解决问题的方法。


31
投票

来自 Github:

在 2023 年 3 月 24 日世界标准时间 05:00 左右,出于谨慎考虑,我们更换了用于保护 GitHub.com 的 Git 操作的 RSA SSH 主机密钥。我们这样做是为了保护我们的用户免受对手冒充 GitHub 或通过 SSH 窃听他们的 Git 操作的任何机会。此密钥不授予对 GitHub 基础设施或客户数据的访问权限。此更改仅影响使用 RSA 通过 SSH 的 Git 操作。 GitHub.com 的 Web 流量和 HTTPS Git 操作不受影响。

解决方案:从 .ssh/known_hosts 中删除 github 的旧 RSA SSH 密钥并更新新密钥。 https://github.blog/2023-03-23-we-updated-our-rsa-ssh-host-key/#what-you-can-do


30
投票

根据 Github 的博客文章,他们的 SSH 密钥被泄露,因此他们重新生成了他们的密钥。

您需要通过运行删除存储的密钥:

$ ssh-keygen -R github.com

应该输出如下内容:

# Host github.com found: line 1
.ssh/known_hosts updated.

随后是获取新密钥的命令:

$ curl -L https://api.github.com/meta | jq -r '.ssh_keys | .[]' | sed -e 's/^/github.com /' >> ~/.ssh/known_hosts

完成后,您可以重新运行您尝试的

git
命令。


22
投票

是的,GitHub 更新了他们的 RSA 主机密钥,如 他们的博客文章 中所述。您可以按照那里的说明更新您的密钥。

然而,有些人发现OpenSSH还通过

CheckHostIP
选项保存了IP地址的主机密钥。这是在 OpenSSH 8.5 之前默认启用的,但往往没有帮助,因为它使旋转变得困难,因此在该版本中被禁用。也就是说,它可以像这样解决(在 Linux 和 Git Bash 上):

$ sed -i -e '/AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31\/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi\/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ==/d' ~/.ssh/known_hosts

在 macOS 上也是如此:

$ sed -i '' -e '/AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31\/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi\/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ==/d' ~/.ssh/known_hosts

无论是主机名还是 IP 地址,它都会删除找到的密钥。由于 GitHub 使用多个 IP 地址,实际上不可能枚举所有地址并用

ssh-keygen
将它们全部删除,因此手动删除密钥本身是最好的选择。

然后您可以按照博客文章中的说明自动更新密钥:

$ curl -L https://api.github.com/meta | jq -r '.ssh_keys | .[]' | \
  sed -e 's/^/github.com /' >> ~/.ssh/known_hosts

7
投票

在 Ubuntu 20.04 上,使用 Github 上的 ed25519 密钥,即使在运行

ssh-keygen -R github.com
之后,根据 main answer,我每次运行时都会看到这些通知
git push

$ git push
Warning: the ECDSA host key for 'github.com' differs from the key for the IP address '140.82.112.4'
Offending key for IP in /home/gabriel/.ssh/known_hosts:14
Matching host key in /home/gabriel/.ssh/known_hosts:15
Are you sure you want to continue connecting (yes/no)? yes
Warning: the ECDSA host key for 'github.com' differs from the key for the IP address '140.82.112.4'
Offending key for IP in /home/gabriel/.ssh/known_hosts:14
Matching host key in /home/gabriel/.ssh/known_hosts:15
Are you sure you want to continue connecting (yes/no)? yes
Warning: the ECDSA host key for 'github.com' differs from the key for the IP address '140.82.112.4'
Offending key for IP in /home/gabriel/.ssh/known_hosts:14
Matching host key in /home/gabriel/.ssh/known_hosts:15
Are you sure you want to continue connecting (yes/no)? yes

所以,我终于删除了我的

~/.ssh/known_hosts
文件,重命名如下:

(更新:尝试 @bk2204 的回答 而不是运行下面的

mv
cmd。谢谢,@Guntram Blohm)。

mv ~/.ssh/known_hosts ~/.ssh/known_hosts.bak

...现在

git push
终于可以正常工作了!我不在乎每当我再次使用 ssh 到特定服务器时我必须重新验证我的所有 ssh 目的地,所以有效地删除
~/.ssh/known_hosts
文件就可以了。除了推送到 GitHub 和 GitLab 之外,我几乎不使用 ssh。

注意:我第一次跑

git push
之后就得输入
yes
,如下图:

$ git push
The authenticity of host 'github.com (140.82.112.4)' can't be established.
ECDSA key fingerprint is SHA256:p2QAMXNIC1TJYWeIOttrVc98/R1BUFWu3/LiyKgUfQM.
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added 'github.com,140.82.112.4' (ECDSA) to the list of known hosts.
Everything up-to-date

但是,在输入

yes
之前,我首先在 GitHub 的网站上验证了
SHA256:p2QAMXNIC1TJYWeIOttrVc98/R1BUFWu3/LiyKgUfQM
指纹是正确的,并且来自 GitHub。 GitHub 在这里有每种密钥类型的指纹:https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/githubs-ssh-key-fingerprints

这些是 GitHub 的公钥指纹:

  • SHA256:uNiVztksCsDhcc0u9e8BujQXVUpKZIDTMczCvj3tD2s
    (RSA)
  • SHA256:br9IjFspm1vxR3iA35FWE+4VTyz1hYVLIE2t1/CeyWQ
    (DSA - 已弃用)
  • SHA256:p2QAMXNIC1TJYWeIOttrVc98/R1BUFWu3/LiyKgUfQM
    (ECDSA)
  • SHA256:+DiY3wvvV6TuJJhbpZisF/zLDA0zPMSvHdkr4UvCOqU
    (Ed25519)

3
投票

github 博客 简单地建议:

ssh-keygen -R github.com

不幸的是,这并不容易,我不断收到如下错误,表明 github 服务器在我的已知主机中,按 IP 地址存储。

Warning: the ECDSA host key for 'github.com' differs from the key for the IP address '192.30.255.113'
Offending key for IP in /.ssh/known_hosts:19
Matching host key in /.ssh/known_hosts:178
Are you sure you want to continue connecting (yes/no)? yes

你必须搜索与 github.com 的服务关联的 1000 个 IP 地址才能清理它们......😈

我设计了一个 Ruby 脚本来搜索通过 GitHub 元 API 发布的 github IP 地址。它是有限的——它跳过了巨大的“动作”IP 范围,并且只适用于 IPv4,但希望它能帮助其他人不必按

yes
很多次。

https://gist.github.com/jcward/5a64c17a6b61de0f7a4d85d004e7679e

出于存档目的转载于此:

#!/usr/bin/env ruby
#
# https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/githubs-ssh-key-fingerprints
# https://stackoverflow.com/questions/75830783
#
# Scan for github IP addresses in your knwon_hosts and remove them
# - Takes ~1.5 minutes on my machine
# - Skips the huge "actions" IP ranges
# - Skips IPv6

require 'json'

meta = JSON.parse `curl -s https://api.github.com/meta`

def num_to_ipv4 v
  (v >> 24 & 255).to_i.to_s + "." +
  (v >> 16 & 255).to_i.to_s + "." +
  (v >> 8 & 255).to_i.to_s + "." +
  (v >> 0 & 255).to_i.to_s
end

def get_ips_for octals, bits
  ips = []
  base = (octals[0] << 24) | (octals[1] << 16) | (octals[2] << 8) | octals[3]
  num = 2**(32-bits)
  0.upto(num) { |add|
    ips.push( num_to_ipv4( base + add ) )
  }
  return ips
end

meta.each { |key, value|
  next if key=="actions" # These ranges are too large
  if (value.is_a?(Array)) then
    value.each { |ip|
      if (ip.match(/(\d+)\.(\d+)\.(\d+)\.(\d+)\/(\d+)/)) then
        octals = [$1, $2, $3, $4].map(&:to_i)
        bits = $5.to_i
        ips = get_ips_for(octals, bits)
        puts "# Scanning #{ key } range -- #{ ips.length } IPs"
        ips.each { |ip|
          search = `ssh-keygen -H -F #{ ip }`
          if (search.length > 10) then
            puts "Running: ssh-keygen -R #{ ip }"
            `ssh-keygen -R #{ ip }`
          end
        }
      end
    }
  end
}
© www.soinside.com 2019 - 2024. All rights reserved.