Wie erhalte ich HostName aus einem ausführbaren Skript in der SSH-Konfigurationsdatei?

10

Ich muss häufig von einem bestimmten Cluster aus in einen beliebigen Computer ssh (alle Computer im Cluster sind identisch). Die Anzahl der verfügbaren Computer im Cluster ändert sich jedoch häufig, sodass ich ein Skript habe, das einen beliebigen Hostnamen aus dem verfügbaren Cluster zurückgibt, der meinen Anforderungen entspricht (z. B. online und mit dem richtigen Betriebssystem).

Beachten Sie auch, dass ich die Weiterleitung von Kerberos-Anmeldeinformationen (GSSAPIAuthentication) zur Authentifizierung verwende.

Im Moment ssh ich mit ssh `get_host`. Ich möchte stattdessen ausführen ssh cluster. Bei einem bekannten Hostnamen ist dies mit den folgenden Anweisungen einfach /ssh/config:

Host cluster
    HostName static_host.cluster.domain.tld
    GSSAPIAuthentication yes
    GSSAPIDelegateCredentials yes

Wie kann ich das HostNamemithilfe meines Skripts dynamisch auswählen ? (Oder hat SSH eine andere Methode, um meine gewünschte Funktion zu unterstützen?) Ich möchte Folgendes tun, aber es funktioniert nicht:

Host cluster
    HostName `get_host`   # This does not work
    ...

Grawity hat gezeigt, dass es ProxyCommandsich um ein Skript handeln kann, das den Hostnamen abruft und die sshVerbindung mit netcatoder weiterleitet socat. Dadurch werden die Kerberos-Anmeldeinformationen jedoch nicht weitergeleitet. Hilfe dabei wird ebenfalls geschätzt.

BEARBEITEN:

Sie können dies mit Kerberos nicht wie gewünscht tun (siehe Kommentare in der akzeptierten Antwort). Daher verwende ich dieses Skript ssh-wrapperals sshAlias ​​für das dynamische Umschreiben des sshBefehlszeilenarguments. Es ist nicht robust, aber es funktioniert für mich.

#!/bin/bash

# Mapping between host aliases and dynamically-generated hostname
declare -A MAP
MAP[cluster]=`gethost`

# Find and replace on all positional args
args=$*
for key in ${!MAP[@]}; do
    replace=${MAP[$key]}
    args=`echo ${args} | sed "s/\(^\|[[:space:]]\)${key}\(\$\|[[:space:]]\)/${replace}/"`
done

# Execute using called-name if not this script
if [ "ssh-wrapper" != "`basename $0`" ]; then
    exec $0 ${args}
# Otherwise, assume ssh and execute
else
    exec ssh ${args}
fi
David B.
quelle
Verwandte Frage zum Serverfehler .
Michael - Wo ist Clay Shirky

Antworten:

6

~/.ssh/config::

Host cluster
    ProxyCommand ~/bin/cluster-connect

~/bin/cluster-connect::

#!/bin/bash
socat stdio tcp:$(get_host):22
user1686
quelle
Vielen Dank. Dies (oder netcat $(get_host) 22) funktioniert hervorragend für die Verbindung. Aber es scheint nicht meine Kerberos-Anmeldeinformationen zu übergeben. Ich habe GSSAPIAuthentication yesund GSSAPIDelegateCredentials yesunter Host clusterin meiner .ssh/configDatei, und sie funktionieren, wenn der Hostname explizit angegeben wird, aber nicht, wenn ich durch den ProxyCommand route. Gedanken? Ich werde die Frage ebenfalls ändern.
David B.
Ich glaube nicht, dass Sie das erreichen können - Sie sshmüssen den Ziel-Hostnamen kennen, um das richtige Ticket zu erhalten, und es gibt einfach keine Möglichkeit, es dynamisch bereitzustellen (ohne einen Wrapper zu verwenden, der einfach ausgeführt wird ssh $(get_host) "$@", was Sie meines Wissens nicht wollen ). Es kann funktionieren, wenn alle Server im Cluster das gleiche Kerberos-Prinzip haben, aber ich glaube nicht, dass dies jemals jemand tut.
user1686
Leider, macht aber Sinn. Ich habe einen Quick Wrapper geschrieben, um ein dynamisches Suchen / Ersetzen durchzuführen (der Frage hinzugefügt). Es wird in einigen Szenarien kaputt gehen, funktioniert aber für mich.
David B.
Dynamisches Suchen / Ersetzen? ...
user1686
Nur eine einfache Substitution in den Befehlszeilenargumenten für ssh, von einer im Skript gespeicherten Host-Alise- bis Host-Generierungs-Skript-Zuordnung.
David B.