Come ottenere la passphrase della chiave SSH una volta e solo quando necessario?


15

(Ho letto molte delle domande su questo sito che sembrano correlate e credo che questa sia una domanda veramente nuova.)

Ho molte chiavi su molti server e sono tutte protette da passphrase.

Mi piace inserire passphrase tanto quanto mi piace inserire le password: è una vera perdita di produttività.

  • I comandi ssh-agent + ssh-add possono essere utilizzati su una shell di login per indicare che è necessario inserire la passphrase solo una volta al login

  • il portachiavi può essere usato per mantenere in vita un agente ssh oltre il logout, quindi ad esempio puoi averlo così devi solo inserire la passphrase una volta all'avvio, oppure puoi tenerlo in vita per circa un'ora.

Il problema che ho è che entrambe queste soluzioni vengono in genere avviate in un login shell (ad esempio .zshrc) basandosi sul fatto che inserisco la mia passphrase quando eseguo l'accesso, anche se non avrò bisogno di sbloccarlo. (Non sono contento che il portachiavi mantenga un agente in vita indefinitamente.)

Quello che mi piacerebbe ricevere una passphrase (per un agente) solo quando necessario .

Quindi posso accedere al server A, fare alcune cose, quindi ssh al server B e a quel punto chiedere la passphrase. Fare alcune cose sul server B, disconnettersi. Di nuovo su A, fai ancora un po 'di roba, di nuovo da ssh a B e non ho bisogno della mia passphrase (è trattenuta da un agente).

Noto che questo è possibile su desktop grafici come Gnome: si ottiene un pop-up che chiede la passphrase per sbloccare la chiave privata non appena si tenta di ssh. Quindi questo è quello che sto cercando, ma da una console.


Perché non generare semplicemente chiavi ssh senza passphrase? Se hai intenzione di affrontare tutti questi problemi comunque?
devnull

1
Se qualcuno entra e ci sono chiavi senza password (o un agente ssh attivo), possono avere accesso anche a molti altri server. Anche le chiavi senza passphrase possono essere rubate e utilizzate altrove.
artfulrobot,

Per quanto ne so, non c'è modo di fare quello che vuoi senza sacrificare un certo livello di sicurezza, il che sembra che tu non voglia fare. C'è stata una risposta approfondita di Thomas Nyman che spiega molte possibilità se non l'hai già letto: unix.stackexchange.com/a/90869/82289 . Mi aggiro nella mia azienda usando un server intermedio che gestisce le sessioni ssh con Tmux.
Devnull

@DevNull sembra strano che puoi farlo con un desktop ma non con un terminale, no? Sicuramente ha solo bisogno che l'agente passi alla tty se non sono state aggiunte chiavi? Questo deve essere il modo in cui funzionano le GUI?
artfulrobot

Potresti dare un'occhiata alla mia risposta qui: unix.stackexchange.com/a/184160/89706 (Link alla domanda: unix.stackexchange.com/questions/90853/… )
Johnny Wong

Risposte:


16

Non aggiungere nulla a nessuno dei tuoi script di avvio della shell, questo è un hacker non necessario.

Invece, aggiungi

AddKeysToAgent yes

al tuo .ssh / config

In questo modo, ssh-add viene eseguito automaticamente la prima volta che si lancia in un'altra casella. Devi solo reinserire la chiave quando scade da ssh-agent o dopo il riavvio.


Vorrei che le persone commentassero quando votavano. Se non è giusto è importante, sappiamo perché non è giusto. Grazie per la pubblicazione, non ho avuto il tempo di provare il tuo suggerimento da solo.
artfulrobot

Mi chiedevo anche io, forse a causa dei miei messaggi incrociati?
Toby,

Questo funziona per me. Comunque è un'aggiunta molto recente a openssh (7.2). Nel caso in cui aiuti chiunque, openssh 7.3 è disponibile in Debian Sid.
artfulrobot,

@artfulrobot: Strano, dato che ho avuto lo stesso comportamento (auto-ssh-add al primo richiamo di ssh) che funziona da anni, fino a quando non si è finalmente fermato qualche tempo fa. Cercando la causa, ho trovato AddKeysToAgent e ho ipotizzato che la ragione per cui si è fermata è stata che per caso dovevo aver ripulito il mio .ssh / config e AddKeysToAgent insieme ad esso. Ora mi chiedo perché funzionasse molto prima che OpenSSH 7.2 venisse rilasciato? Non me lo sto immaginando :-)
Toby,

@Toby questo è esattamente ciò di cui ho bisogno. Sfortunatamente, ssh-agent non sembra avviarsi automaticamente in Kubuntu, quindi questa è la prossima cosa che devo risolvere.
Ogaday,

7

Zsh ha un preexechook che esegue una funzione prima dell'esecuzione di un comando immesso sulla riga di comando. Ecco un hook che cerca sshnella tua riga di comando e, se trovato, verifica l'esistenza di un agente ssh. Se questo non viene trovato, esegue il portachiavi.

Quindi, in questo modo, il portachiavi viene eseguito solo prima dei comandi ssh, e solo se necessario.

Metti questo nel tuo ~/.zshrc:

function check_ssh {
  [[ $3 =~ '\bssh\b' ]] || return
  [[ -n "$SSH_AGENT_PID" && -e "/proc/$SSH_AGENT_PID" ]] \
    && ssh-add -l >/dev/null && return
  eval `keychain --eval id_dsa --timeout 60`
}    
autoload -U add-zsh-hook
add-zsh-hook preexec check_ssh

Ciò che accade qui è ogni volta che viene digitato un comando, check_sshviene chiamato prima dell'esecuzione del comando.

La prima riga della funzione controlla il comando espanso per l' sshutilizzo di una regex Zsh. sshdeve avere confini di parole su \bentrambi i lati. Se questo non viene trovato, la funzione ritorna.

La riga successiva verifica l'esistenza di un processo dell'agente SSH nella variabile di ambiente e che tale processo esista ancora nella tabella dei processi, quindi che almeno una chiave è stata aggiunta all'agente. Se tutto ciò è OK, allora l'agente ssh è impostato e non abbiamo bisogno di fare nulla, quindi ritorna.

Finalmente iniziamo il portachiavi, con l'agente che deve rimanere in vita per un'ora.

Rimane ancora il problema con roba ssh incorporata, come gito rsynco scpcome quella che non attiverà la funzione (potresti aggiungerli a regex).


Anche senza zsh, si potrebbe creare un breve script con lo stesso effetto e posizionarlo PATHdavanti al sshclient reale . Potrebbe anche funzionare con rsyncet al, se leggono PATHinvece di essere eseguiti /usr/bin/sshdirettamente.
ilkkachu,

2

Per zsh, ho scritto una serie di utility e wrapper per fare più o meno quello che vuoi: https://www.vinc17.net/unix/index.en.html#zsh-ssh-utils

In realtà lo fa ancora di più, perché ssh-agentsarà condiviso da tutte le sessioni di accesso (desktop o tramite SSH, e anche lo schermo GNU è supportato se si avvia da esso shell di accesso, ad esempio con shell -zshnel ~/.screenrcfile), e si chiuderà solo dopo il l'ultima sessione termina.

Nota: utilizzo solo una passphrase per tutte le mie chiavi. Non sono sicuro del comportamento per diverse passphrase; potrebbero essere necessari alcuni cambiamenti.


Wow, è un bel po 'di codice. Bel lavoro e grazie per la condivisione. Penso di aver bisogno di qualcosa di più semplice: SSH è uno strumento piuttosto essenziale per me.
artfulrobot,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.