199

I want to clone a repo in a non-interactive way. When cloning, git asks to confirm host's fingerprint:

The authenticity of host 'bitbucket.org (207.223.240.182)' can't be established.
RSA key fingerprint is 97:8c:1b:f2:6f:14:6b:5c:3b:ec:aa:46:46:74:7c:40.
Are you sure you want to continue connecting (yes/no)? no

How do I force "yes" every time this questions pops up? I tried using yes yes | git clone ..., but it doesn't work.

EDIT: Here's a solution: Can I automatically add a new host to known_hosts? (adds entires to known_hosts with ssh-keyscan).

qwe
  • 2,037
  • 2
  • 14
  • 5
  • Interesting to see that even after two years this question does not have a proper answer. There are few other cases where git will prompt, for example if you try to clone over http and the server is asking for basic_auth. How to do this in non-interactice mode? – sorin Oct 23 '14 at 12:06
  • 3
    Adding the `-q` option (quiet) did it for me. Now I'm stuck automating the passphrase. –  Jun 21 '15 at 21:34

6 Answers6

148

I don't think that is the best solution, but it was a solution for me.

ANSWER:

Adding the domainnames to the known_hosts file using the ssh-keyscan command solved the issue:

ssh-keyscan <enter_domainname_e.g._github.com> >> ~/.ssh/known_hosts

Eric Leschinski
  • 4,211
  • 4
  • 21
  • 27
kroe
  • 1,620
  • 1
  • 10
  • 4
  • 12
    Please don't do this way. This is totally NOT secure: fingerprints are not here to annoy you but to make sure you're not facing a man-in-the-middle attack. Please see my answer below. – autra Oct 21 '15 at 12:17
  • 1
    as i said, "I don't think that is the best solution, but was a solution for me." because i was in a rush, surely there is "policataly correct way" of doing it (( : – kroe Oct 21 '15 at 14:05
  • 2
    It's not a question of politically correct :-) It's a question of whether it is secure or not. Your solution is secure if and only if you manually check the fingerprint after your `ssh-keyscan` and before adding it to `.ssh/known_hosts` to be the same as the one github has published on their website. You can do it in several ways, and mine is one of them. You can also do an equal check in your script, but at the end it all comes to this: you need your script to know which fingerprint it expects, and you need it to fail if it does not receive the correct one. – autra Nov 25 '15 at 09:35
  • duplicate of http://serverfault.com/questions/132970/can-i-automatically-add-a-new-host-to-known-hosts/132974#132974 and http://serverfault.com/questions/132970/can-i-automatically-add-a-new-host-to-known-hosts/631149#631149 – 030 Dec 20 '15 at 17:50
  • 18
    to add key ONLY if it not exists `ssh-keygen -F github.com || ssh-keyscan github.com >>~/.ssh/known_hosts` – Sang Dec 05 '17 at 10:04
  • 7
    Doing this once as part of a configuration management or provisioning run should be fine. If the fingerprint ever changes in the future, then ssh will work as intended and alert you that the cert has changed, returning a non 0 exit code. This is likely to stop any script where you're using ssh or git. – emhohensee Dec 23 '17 at 19:01
  • it output nothing, do I need add port ? – Mithril Dec 17 '18 at 02:46
  • @transang `(ssh-keygen -F github.com || ssh-keyscan github.com) >> ~/.ssh/known_hosts` the brackets made it work for me. With the brackets, it was not redirecting the output to the file – Shammi Shailaj Jul 21 '20 at 11:33
  • This is the best way to go. I care more about practicality! – Rainb Feb 06 '21 at 12:38
145

Neither "StrictHostKeyChecking no" nor "ssh-keyscan" options are secure. you need a manual fingerprint validation at some point to avoid MiTM attack if you stick with ssh.

Actually, you have 2 options:

Use https protocol instead of git

It won't ask you for a fingerprint, because ssh is not involved, https is used instead. For a security standpoint you are trusting root certificates installod on your OS. If you're using a minimalist image or Docker, you might need to install the ca-certificates package.

If you really want git+ssh protocol

Do you really need to add the key at runtime? This is not secure because you didn't check the fingerprint and that leaves you open to MiTM attacks. This is not just theoretical, and it has been proven to work.

Before running your script, get the key from github (on your local machine):

ssh-keyscan github.com > githubKey

Generate the fingerprint:

ssh-keygen -lf githubKey

And check it manually against those listed in this page (ok, there you trust https certificates and OpenSSL to bring you the original github website, but it's still a lot better than blindly accepting a public key).

Alternatively (trusting the same https and OpenSSL) you can fetch it from https://api.github.com/meta like this: curl -s https://api.github.com/meta | jq ."ssh_key_fingerprints" | grep RSA. (Thanks @willscripted for this one)

Then, you hardcode it in your script by adding in it:

echo '<copy paste the content of 'cat githubKey' on your machine>'  >> ~/.ssh/known_hosts

before the git clone.

The GitHub public key will only change if they believe it was compromised (or not secure enough). If this is ever the case, you want your script to fail anyway.

autra
  • 1,566
  • 1
  • 10
  • 10
  • 2
    You can't do non-interactive HTTPS with GitHub if you use two factor auth, unfortunately. – Brett Widmeier Apr 13 '16 at 13:17
  • 1
    I don't see why not. We are talking about a public repo here, no need for authentication. Cloning a private repo from a script is another thing entirely: you need to authorize your script to do so. – autra Apr 20 '16 at 10:44
  • Checking the fingerprint "manually" is less painful than it sounds, with the help of "search bar" in modern explorers (such as in [Chrome](https://support.google.com/chrome/answer/95635)). – Franklin Yu Aug 24 '16 at 03:20
  • Is there any way to supply the "expected" fingerprint as a command line argument to git clone instead of having to put it in a file first? – FGreg Jul 25 '19 at 16:19
  • It's actually ssh that needs to know the correct fingerprint. – autra Jul 25 '19 at 17:03
  • HTTPS option requires github.com password for non-public repos, so it's still interactive :( – Dzmitry Lazerka Aug 07 '19 at 22:20
  • OP never said it was about a private repo, but I'm pretty sure you can specify user / pass in the url. – autra Aug 20 '19 at 14:52
  • 2
    Github's key-scanned fingerprints can now be validated against the values in the developer api. `curl -i https://api.github.com/meta`. We still get to trust the certificate, but now in real-time rather than once manually. – willscripted Jun 16 '20 at 20:04
14

Adding the key to .ssh/known_hosts appears to be the right thing to do.

Though when you automate the task you want to make sure the key is not already contained and added on each clone/pull tasks.

This snippet will only add the fingerprint if not already found:

if [ ! -n "$(grep "^bitbucket.org " ~/.ssh/known_hosts)" ]; then ssh-keyscan bitbucket.org >> ~/.ssh/known_hosts 2>/dev/null; fi
udondan
  • 2,061
  • 15
  • 18
  • 1
    This was perfect. Can easily be put into a deploy script and is safer than disabling host verification. Here's a one-liner for github: `if [ ! -n "$(grep "^github.com " ~/.ssh/known_hosts)" ]; then ssh-keyscan github.com >> ~/.ssh/known_hosts 2>/dev/null; fi; ssh-agent bash -c "ssh-add /path/to/your/deploy/id_rsa; git clone -b master git@github.com:githubAccount/githubRepo.git /your/target/dir` – tweak2 Oct 14 '15 at 20:54
  • This does not work when _HashKnownHosts_ is enabled in _/etc/ssh/ssh_config_ (or _~/.ssh/config_). Instead of `[ ! -n "$(grep "^bitbucket.org " ~/.ssh/known_hosts)" ]` it would be better to use `[ ! "$(ssh-keygen -F bitbucket.org)" ]`, which finds both hashed and non-hashed lines in _known_hosts_. – Claus Conrad Apr 22 '16 at 17:23
11

I believe a better option here is to back up and empty your ~/.ssh/known_hosts file, manually perform the SSH connection, verifying the IP address and fingerprint, mv ~/.ssh/known_hosts ~/bitbucket_hosts, then use the contents of ~/bitbucket_hostsin your script to automatically append the known fingerprints to the known_hosts file (don't forget to restore the original ~/.ssh/known_hosts).

This step only needs to be performed once (on any machine, I believe), and once you have the fingerprints, you can incorporate it in to your automation script.

kenorb
  • 6,499
  • 2
  • 46
  • 54
Steven Soroka
  • 211
  • 2
  • 4
  • 1
    this is the most straightforward answer. Instead of scripting the generation of the fingerprint to put into known_hosts, just make a connection to generated the known_hosts file and copy the known_hosts file around – Joe Sep 19 '19 at 18:39
8

While I certainly understand that you want to automate such a process, doing so would be ill-advised. The reason why SSH and related networking subcomponents balk when using a secure protocol is to WARN a human that a system's public key is unknown. This is intentional - the user needs to explicitly inform the system the host is expected. You wouldn't want to auto accept every public key presented to you or part of the security in SSH or TLS/SSL could be compromised. One example is via a man-in-the-middle attack such as when a proxy software presents it's own key in the place of a host you expect.

Proceed with caution.

If you have no fear about the source of the code across the wire, you should explicitly and exclusively use the git:// protocol when cloning - it's authenticationless and in clear text.

Jeff Stice-Hall
  • 349
  • 2
  • 5
  • 3
    I can definitively see use cases where we need to enforce non-interactive uses of ``git clone``... and that doesn't mean we require to accept any check (the fingerprint one in particular). In my case, I would be perfectly glad to fail automatically on such thing. – vaab Apr 11 '14 at 11:04
  • How can you even know whether the key comes from a proxy or the git hosting website? MITM attacks wouldn't really be attacks if it was that obvious. – nurettin Jul 11 '23 at 08:25
6

As Jeff Hall said, doing so is dangerous as it allows undetected man-in-the-middle attacks. However, you could use the StrictHostKeyChecking no option in ssh to disable checking the host keys. However, I'd be very careful with that option if I were you.

Nam G VU
  • 287
  • 2
  • 5
  • 15
Wren T.
  • 337
  • 3
  • 5