Skip to content

Commit 615b273

Browse files
committed
improve HostKeyCallback
1 parent b3b6e1d commit 615b273

File tree

1 file changed

+36
-16
lines changed

1 file changed

+36
-16
lines changed

utils/file.go

Lines changed: 36 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -176,8 +176,10 @@ func processScpUri(src string) (io.ReadCloser, error) {
176176
return nil, fmt.Errorf("no username provided for scp connection")
177177
}
178178

179+
knownHostsPath := ResolvePath("~/.ssh/known_hosts", "")
180+
179181
// try loading ssh agent keys
180-
clientConfig, _ := auth.SshAgent(u.User.Username(), KnownHostsLogWarningCallBack) // skipcq: GSC-G106
182+
clientConfig, _ := auth.SshAgent(u.User.Username(), getCustomHostKeyCallback(knownHostsPath, "/tmp/foobar")) // skipcq: GSC-G106
181183

182184
// if CLAB_SSH_KEY is set we use the key referenced here
183185
keyPath := os.Getenv("CLAB_SSH_KEY")
@@ -464,23 +466,41 @@ func ProcessDownloadableAndEmbeddedFile(nodename string, fileRef string, filenam
464466
return fileRef, nil
465467
}
466468

467-
// KnownHostsLogWarningCallBack is a KnownHostsCallback implementation that relies on the
468-
// implementation of the crypto package of golang. However, it will not error out if the
469-
// Hostkey is unknown, but issue a warning in the logs, if the host is unknown.
470-
func KnownHostsLogWarningCallBack(hostname string, remote net.Addr, key ssh.PublicKey) error {
471-
// rely on the knownhosts implementation of the crypto package
472-
// cretae an instance of it
473-
khFile := ResolvePath("~/.ssh/known_hosts", "")
474-
origKHCB, err := knownhosts.New(khFile)
475-
if err != nil {
476-
return err
469+
// getCustomHostKeyCallback returns a custom ssh.HostKeyCallback.
470+
// it will never block the connection, but issue a log.Warn if the
471+
// host_key cannot be found (due to absense of the entry or
472+
// the file being missing)
473+
func getCustomHostKeyCallback(knownHostsFiles ...string) ssh.HostKeyCallback {
474+
var usefiles []string
475+
// check
476+
for _, file := range knownHostsFiles {
477+
if !FileExists(file) {
478+
log.Debugf("known_hosts file %s does not exist.", file)
479+
continue
480+
}
481+
usefiles = append(usefiles, file)
477482
}
478483

479-
// delegate the call
480-
err = origKHCB(hostname, remote, key)
484+
// load the known_hosts file retrieving an ssh.HostKeyCallback
485+
knownHostsFileCallback, err := knownhosts.New(usefiles...)
481486
if err != nil {
482-
// But if an error crops up, make it a warning and continue
483-
log.Warnf("error while performing host key validation based on %q for hostname %q (%v). continuing anyways", khFile, hostname, err)
487+
log.Debugf("error loading known_hosts files %q", strings.Join(knownHostsFiles, ", "))
488+
// this is an always failing knownHosts checker.
489+
// it will make sure that the log message of the custom function further down
490+
// is consistently logged. Meaning if file can't be loaded or entry does not exist.
491+
knownHostsFileCallback = func(hostname string, remote net.Addr, key ssh.PublicKey) error {
492+
return fmt.Errorf("error loading known_hosts files %v", err)
493+
}
494+
}
495+
496+
// defien the custom ssh.HostKeyCallback function.
497+
return func(hostname string, remote net.Addr, key ssh.PublicKey) error {
498+
// delegate the call
499+
err = knownHostsFileCallback(hostname, remote, key)
500+
if err != nil {
501+
// But if an error crops up, make it a warning and continue
502+
log.Warnf("error performing host key validation based on %q for hostname %q (%v). continuing anyways", strings.Join(knownHostsFiles, ", "), hostname, err)
503+
}
504+
return nil
484505
}
485-
return nil
486506
}

0 commit comments

Comments
 (0)