Udostępnianie tego samego `ssh-agent` pomiędzy wieloma sesjami logowania

61

Czy istnieje wygodny sposób, aby upewnić się, że wszystkie dane logowania od danego użytkownika (tj. Mnie) używają tego samego agenta ssh? Wyhakowałem scenariusz, aby większość czasu działała, ale przez cały czas podejrzewałam, że jest jakiś sposób, żeby to przegapić. Ponadto od tego czasu nastąpił niesamowity postęp w technologii komputerowej, na przykład ta strona internetowa.

Więc celem jest to

  • za każdym razem, gdy loguję się do skrzynki, niezależnie od tego, czy odbywa się to przez SSH, czy w sesji graficznej rozpoczętej z gdm / kdm / etc lub na konsoli:
    • jeśli moja nazwa użytkownika nie ma obecnie ssh-agenturuchomionej, jedna jest uruchamiana, zmienne środowiskowe są eksportowane i ssh-addwywoływane.
    • w przeciwnym razie współrzędne istniejącego agenta są eksportowane do zmiennych środowiskowych sesji logowania.

Ta funkcja jest szczególnie cenna, gdy dane pudełko jest używane jako punkt przekaźnikowy podczas sshwchodzenia do trzeciego pudełka. W takim przypadku unika się konieczności wpisywania hasła klucza prywatnego za każdym razem, gdy ssh jest wpisywane, a następnie chcemy na przykład zrobić git pushcoś lub coś.

Skrypt podany poniżej robi to głównie niezawodnie, chociaż ostatnio spartaczył się, gdy X się zawiesił, a następnie rozpocząłem kolejną sesję graficzną. W tym przypadku mogło się zdarzyć coś innego.

Oto mój zły scenariusz. Pozyskuję to z mojego .bashrc.

# ssh-agent-procure.bash
# v0.6.4
# ensures that all shells sourcing this file in profile/rc scripts use the same ssh-agent.
# copyright me, now; licensed under the DWTFYWT license.

mkdir -p "$HOME/etc/ssh";

function ssh-procure-launch-agent {
    eval `ssh-agent -s -a ~/etc/ssh/ssh-agent-socket`;
    ssh-add;
}

if [ ! $SSH_AGENT_PID ]; then
  if [ -e ~/etc/ssh/ssh-agent-socket ] ; then
    SSH_AGENT_PID=`ps -fC ssh-agent |grep 'etc/ssh/ssh-agent-socket' |sed -r 's/^\S+\s+(\S+).*$/\1/'`; 
    if [[ $SSH_AGENT_PID =~ [0-9]+ ]]; then
      # in this case the agent has already been launched and we are just attaching to it. 
      ##++  It should check that this pid is actually active & belongs to an ssh instance
      export SSH_AGENT_PID;
      SSH_AUTH_SOCK=~/etc/ssh/ssh-agent-socket; export SSH_AUTH_SOCK;
    else
      # in this case there is no agent running, so the socket file is left over from a graceless agent termination.
      rm ~/etc/ssh/ssh-agent-socket;
      ssh-procure-launch-agent;
    fi;
  else
    ssh-procure-launch-agent;
  fi;
fi;

Powiedz mi, że jest lepszy sposób, aby to zrobić. Proszę również nie dręczyć niespójności / gaf (np. Wkładanie varrzeczy etc); Napisałem to jakiś czas temu i od tego czasu nauczyłem się wielu rzeczy.

intuicyjny
źródło
1
KeyError: Nie znaleziono „DWTFYWT”; miałeś na myśli WTFPLv2 ?
grawitacja
@grawity: dzięki za ten link, ich FAQ sprawiły, że mój dzień: Przy okazji, dzięki WTFPL, mogę również… Och, ale tak, oczywiście, że możesz. Ale czy mogę… Tak, możesz. Czy… Tak! hahahahahaha
szarlatan
@grawity: Nie, właśnie tak chciałem, żebyś pomyślał, mwahahaha.
intuicyjnie

Odpowiedzi:

25

Równie dobrze mogę wrzucić własną odmianę do miksu:

function sshagent_findsockets {
    find /tmp -uid $(id -u) -type s -name agent.\* 2>/dev/null
}

function sshagent_testsocket {
    if [ ! -x "$(which ssh-add)" ] ; then
        echo "ssh-add is not available; agent testing aborted"
        return 1
    fi

    if [ X"$1" != X ] ; then
        export SSH_AUTH_SOCK=$1
    fi

    if [ X"$SSH_AUTH_SOCK" = X ] ; then
        return 2
    fi

    if [ -S $SSH_AUTH_SOCK ] ; then
        ssh-add -l > /dev/null
        if [ $? = 2 ] ; then
            echo "Socket $SSH_AUTH_SOCK is dead!  Deleting!"
            rm -f $SSH_AUTH_SOCK
            return 4
        else
            echo "Found ssh-agent $SSH_AUTH_SOCK"
            return 0
        fi
    else
        echo "$SSH_AUTH_SOCK is not a socket!"
        return 3
    fi
}

function sshagent_init {
    # ssh agent sockets can be attached to a ssh daemon process or an
    # ssh-agent process.

    AGENTFOUND=0

    # Attempt to find and use the ssh-agent in the current environment
    if sshagent_testsocket ; then AGENTFOUND=1 ; fi

    # If there is no agent in the environment, search /tmp for
    # possible agents to reuse before starting a fresh ssh-agent
    # process.
    if [ $AGENTFOUND = 0 ] ; then
        for agentsocket in $(sshagent_findsockets) ; do
            if [ $AGENTFOUND != 0 ] ; then break ; fi
            if sshagent_testsocket $agentsocket ; then AGENTFOUND=1 ; fi
        done
    fi

    # If at this point we still haven't located an agent, it's time to
    # start a new one
    if [ $AGENTFOUND = 0 ] ; then
        eval `ssh-agent`
    fi

    # Clean up
    unset AGENTFOUND
    unset agentsocket

    # Finally, show what keys are currently in the agent
    ssh-add -l
}

alias sagent="sshagent_init"

A potem za każdym razem, gdy się loguję, jeśli chcę dołączyć agenta (czego nie zawsze), po prostu piszę sagent.

Zed
źródło
2
if [ ! -x "$(which ssh-add)" ];należy zastąpić przez if ! which ssh-add;lub if ! command -v ssh-add. (Pamiętaj, [to tylko polecenie)
grawitacja
Cóż, możesz to zrobić, ale tak naprawdę musiałoby if ! which ssh-add > /dev/nullto uniemożliwić wydrukowanie ścieżki, w którym to momencie nie jestem do końca pewien, czy to jest bardziej zrozumiałe, chociaż przypuszczam, że oszczędza to jedno dodatkowe wywołanie polecenia.
Zed
więc w zasadzie odpowiedź brzmi: nie. bzdury. Wygląda na to, że jest bardziej rozwinięty niż mój hack, więc prawdopodobnie będzie przydatny. Dziwne, że nie ma bardziej uporządkowanego sposobu na zrobienie tego, wydaje się, że byłoby to całkiem przydatne.
intuicyjnie
Jestem w stanie repositorować wszystko w tych dniach, więc skonfigurowałem repozytorium github dla twojego skryptu. Dzięki jeszcze raz. Mam nadzieję, że byłem wystarczająco formalny, jeśli chodzi o licencjonowanie: ~ /
intuicyjnie
Nie mam nic przeciwko Skomentuj tutaj, jeśli ktoś zgłosi poprawki.
Zed
36

ssh -A [user@]remotehost

Myślę, że to może być to, czego szukasz. Użyj przełącznika -A podczas uruchamiania ssh do przodu ssh-agent. Oto przypadek użycia:

Mam zdalny serwer, który ma na nim kilka repozytoriów git ze zdalnym wskazywaniem na github. Bez agenta ssh działającego w sesji ekranowej muszę wprowadzić hasło dla mojego klucza, aby wykonać „master git pull origin”. Booo! Ponadto muszę mieć zainstalowany klucz prywatny na zdalnym serwerze - więcej Boooo!

Zamiast tego po prostu używam ssh -A [user@]remotehostprzekazuje mój lokalnie uruchomiony ssh-agent. Teraz nie potrzebuję już mojego klucza prywatnego, aby istniał nawet na zdalnym hoście. Nie sądzę, żebyś w ogóle musiał wykonywać skrypty z ssh-agent.

h355ian
źródło
4
Nie wiedziałem o tym, ale okazało się, że właśnie tego szukałem, kiedy trafiłem na to pytanie.
Will McCutchen,
1
To jest nawet lepsze niż to, czego szukałem! Świetna odpowiedź!
WhyNotHugo
1
Zobacz także man 5 ssh_configna ForwardAgentustawienie config. Domyślnie włącza przekazywanie agentów, eliminując potrzebę -Aargumentu. Przed użyciem przekazywania agenta należy pamiętać, że istnieje ryzyko bezpieczeństwa, w którym inni uprzywilejowani użytkownicy na zdalnym komputerze mogą uzyskać dostęp do gniazda przekazanego agenta. Jest to również wspomniane na stronie man. Wyjaśnia to dobrze tutaj .
starfry
Myślę jednak, że opcja AllowAgentForwarding musi być ustawiona na yes na serwerze
Ziofil
20

Oto całkiem fajny, który działa również w Cygwin:

SSH_ENV=$HOME/.ssh/environment

function start_agent {
     echo "Initialising new SSH agent..."
     /usr/bin/ssh-agent | sed 's/^echo/#echo/' > ${SSH_ENV}
     echo succeeded
     chmod 600 ${SSH_ENV}
     . ${SSH_ENV} > /dev/null
     /usr/bin/ssh-add;
}

# Source SSH settings, if applicable

if [ -f "${SSH_ENV}" ]; then
     . ${SSH_ENV} > /dev/null
     #ps ${SSH_AGENT_PID} doesn't work under cywgin
     ps -efp ${SSH_AGENT_PID} | grep ssh-agent$ > /dev/null || {
         start_agent;
     }
else
     start_agent;
fi

Dodaj go do swojego .bash_profile lub .bashrc

Źródło: http://www.cygwin.com/ml/cygwin/2001-06/msg00537.html

vonhogen
źródło
Działa również dobrze z Git Bash (mingw64) dla systemu Windows
Dolphin
1
${SSH_ENV}musi być, "${SSH_ENV}"jeśli w
nazwie
Ta odpowiedź wydaje się podskakiwać w Internecie. Tutaj jest na znacznie większym wątku przepływu stosu . Najlepsze / najprostsze podejście IMHO.
Luke Davis,
6

Ostatnio zacząłem używać:

https://github.com/ccontavalli/ssh-ident

Wszystko, co muszę zrobić, to dodać:

  alias ssh=/path/to/ssh-ident

W moim pliku .bashrc. Skrypt zajmuje się:

  • tworzenie agenta, gdy jest on najpierw potrzebny
  • załaduj niezbędne klucze na żądanie
  • współużytkuj agentów przez wiele sesji logowania
  • zarządzaj wieloma agentami, po jednym dla każdej „tożsamości”, której używam online, i używaj odpowiedniego agenta na podstawie hosta, z którym się łączę lub bieżącego katalogu roboczego.
MarkMo
źródło
ssh-ident jest fantastyczny! Odblokowuje klucz i ładuje agenta, gdy próbuję ssh zamiast konieczności wcześniejszego odblokowania klucza. To sprawia, że ​​kluczowe limity czasu są przydatne. Co ważniejsze, utrzymuje moich agentów oddzielnie dla różnych zastosowań (poważne zagrożenie bezpieczeństwa; root na jednej maszynie ma mój poziom dostępu do wszystkich innych maszyn, do których bieżący agent ma klucze!)
00prometheus
5

Wolę, aby wszystko było tak proste, jak to możliwe: (fragment kodu ~/.profile)

check-ssh-agent() {
    [ -S "$SSH_AUTH_SOCK" ] && { ssh-add -l >& /dev/null || [ $? -ne 2 ]; }
}

# attempt to connect to a running agent
check-ssh-agent || export SSH_AUTH_SOCK="$(< ~/.tmp/ssh-agent.env)"
# if agent.env data is invalid, start a new one
check-ssh-agent || {
    eval "$(ssh-agent -s)" > /dev/null
    echo "$SSH_AUTH_SOCK" > ~/.tmp/ssh-agent.env
}

Nie myślałem o użyciu -awcześniej, ale może być łatwiej:

check-ssh-agent || export SSH_AUTH_SOCK=~/.tmp/ssh-agent.sock
check-ssh-agent || eval "$(ssh-agent -s -a ~/.tmp/ssh-agent.sock)" > /dev/null
grawitacja
źródło
Miły. Uprościłem to nieco w mojej odpowiedzi (poniżej).
Eter
2

W moim przypadku mam wytworną konfigurację w PowerShell i chciałem, aby cygwin używał tego samego agenta ssh. Musiałem trochę zmodyfikować ścieżkę, ponieważ używają różnych folderów tmp, a utworzony plik .env to UTF16 z BOM i CR \ LF, więc dobrze się z tym radziło. Powinno działać dodanie następującego pliku .bashrc używanego przez cygwin:

# Connect to ssh-agent started by posh-git
SSH_AGENT_ENV=$(cygpath "$LOCALAPPDATA\Temp")
if [ -z $SSH_AUTH_SOCK ] && [ -z $SSH_TTY ]; then  # if no agent & not in ssh
  if [ -f "$SSH_AGENT_ENV/.ssh/SSH_AUTH_SOCK.env" ]; then
    AUTH_SOCK=$(iconv -c -f UTF-16LE -t US-ASCII "$SSH_AGENT_ENV/.ssh/SSH_AUTH_SOCK.env" | tr -d '\r\n')
    export SSH_AUTH_SOCK="${AUTH_SOCK/\/tmp/$SSH_AGENT_ENV}"
    ssh-add -l > /dev/null
    if [ $? = 2 ] ; then
      echo "Failed to setup posh-git ssh-agent using $AUTH_SOCK"
      unset SSH_AUTH_SOCK
    else
      echo "Found posh-git ssh-agent $AUTH_SOCK"
    fi
  else #Start new agent if you want (not shared by posh-git)
    echo "failed to setup posh-git ssh-agent"
    #eval `ssh-agent -s` > /dev/null
  fi
fi
Greg Bray
źródło
1

Ponownie przykład, aby od razu umieścić plik .bash_profile i poprosić o dodanie domyślnego klucza podczas logowania. Przekazywanie nie było w moim przypadku opcją.

do-ssh-agent() {
  # function to start the ssh-agent and store the agent details for later logon
  ssh-agent -s > ~/.ssh-agent.conf 2> /dev/null
  . ~/.ssh-agent.conf > /dev/null
}

# set time a key should be kept in seconds
keyage=3600

if [ -f ~/.ssh-agent.conf ] ; then
  . ~/.ssh-agent.conf > /dev/null
  ssh-add -l > /dev/null 2>&1
  # $?=0 means the socket is there and it has a key
  # $?=1 means the socket is there but contains no key
  # $?=2 means the socket is not there or broken
  stat=$?
  if [ $stat -eq 1 ] ; then
    ssh-add -t $keyage > /dev/null 2>&1
  elif [ $stat -eq 2 ] ; then
    rm -f $SSH_AUTH_SOCK
    do-ssh-agent
    ssh-add -t $keyage > /dev/null 2>&1
  fi
else
  do-ssh-agent
  ssh-add -t $keyage > /dev/null 2>&1
fi
Jorrit Jorritsma
źródło
1

To jest moje rozwiązanie, zaadaptowane z https://superuser.com/a/141233/5255 (w tym wątku):

# attempt to connect to a running agent - cache SSH_AUTH_SOCK in ~/.ssh/
sagent()
{
    [ -S "$SSH_AUTH_SOCK" ] || export SSH_AUTH_SOCK="$(< ~/.ssh/ssh-agent.env)"

    # if cached agent socket is invalid, start a new one
    [ -S "$SSH_AUTH_SOCK" ] || {
        eval "$(ssh-agent)"
        ssh-add -t 25920000 -K ~/.ssh/id_rsa
        echo "$SSH_AUTH_SOCK" > ~/.ssh/ssh-agent.env
    }
}
Eter
źródło
1

utwórz plik ~ / ssh-agent.sh

agent_out_file="$HOME/ssh-agent.out"

function initialize {
    pgrep ssh-agent && kill $(pgrep ssh-agent)
    ssh-agent -s > $agent_out_file 
    . $agent_out_file
}

pgrep ssh-agent
if [ $? -eq 0 ]; then # ssh agent running
    ssh-add -l > /dev/null 2>&1
    status=$?
    if [ $status -eq 0 ]; then # can connect to ssh agent and keys available
        echo nothing to do
    elif [ $status -eq 1 ]; then # can connect to ssh agent and no keys available
        echo nothing to do
    elif [ $status -eq 2 ]; then # cannot connect to ssh agent
        . $agent_out_file
    fi
else # ssh agent not running
    initialize   
fi

dołącz plik do .bashrc

. ~/ssh-agent.sh
raghavan
źródło
0

Dodałem coś, co działa dla mnie. Najpierw sprawdza, czy masz uruchomionego agenta, jeśli tak, to ustawi dla niego odpowiednie środowiska, jeśli nie, to go utworzy. Eliminuje również tworzenie dodatkowych agentów:

Po prostu włóż to do swojego .bashrc

function start_agent() {
    killall ssh-agent  2> /dev/null
    ssh-agent | sed 's/ Agent pid//' > $SSH_ENV
    . $SSH_ENV > $SSH_PID_FILE
    ssh-add ~/.ssh/bb_readonly_rsa 2> /dev/null
}

mkdir -p "$HOME/.ssh/agent"
SSH_ENV="$HOME/.ssh/agent/env"
SSH_PID_FILE="$HOME/.ssh/agent/pid"

if [[ -e $SSH_PID_FILE ]]; then
    SSH_PID=$(< $SSH_PID_FILE) 
    PROCESS=$(ps -p $SSH_PID -o comm=)

    if [[ $PROCESS == 'ssh-agent' ]]; then
        . $SSH_ENV > $SSH_PID_FILE
    else 
        start_agent
    fi  
else
    start_agent
fi
Reza Sanaie
źródło
0

Mam również odmianę tego problemu, zaczerpniętą bezpośrednio z mojego .bashrc:

# File for storing SSH agent information
OSH=".agent.${HOSTNAME}"

# Test if an agent file exists
if [ -f ${OSH} ];

    # We have one, so let's use it
    then eval `cat ${OSH}` >/dev/null

else

    # No file exists, so we must spawn a new agent
    eval `ssh-agent | tee ${OSH}` >/dev/null

fi

# Try to list agent keys
ssh-add -l &>/dev/null

# Determine the agent status
case $? in

    # Current and SSH keys installed, nothing to do here
    0) ;;

    # Current but no SSH keys installed, so we must add them
    1) ssh-add ;;

    # Stale, so we must redo from scratch with a new agent, then add keys
    *) eval `ssh-agent | tee ${OSH}` >/dev/null && ssh-add ;;

esac

To rozwiązanie przechowuje kopię informacji agenta SSH w katalogu domowym. W przypadku posiadania katalogu domowego z automatycznym podłączeniem do systemu plików NFS, który może być współużytkowany przez wiele hostów, nazwa hosta jest używana jako część nazwy pliku w celu ich rozróżnienia, więc logowanie z jednego komputera nie spowoduje zablokowania pliku agenta używanego na innym.

Zachowanie:

1) Pierwsze sesje użytkownika są monitowane o podanie hasła kluczowego.

2) Sesje druga, trzecia i czwarta (et cetera) dziedziczą agenta SSH i klucz (klucze) dodane w pierwszej.

3) Jeśli agent zostanie zabity lub ulegnie awarii, pierwsza kolejna sesja utworzy nowego agenta, zastąpi plik agenta nowym - i ponownie poprosi o podanie hasła klucza. Kolejne utworzone sesje będą zachowywać się jak scenariusz 2), dopóki nowy agent SSH pozostanie uruchomiony.

Oliver Jones
źródło
0

(odnosi się to do posta 2 wyższego, nie mogłem dodać komentarza)

@raghavan: Twój przykład jest przydatny, ale sugeruje zmianę dwóch linii, które mają

pgrep ssh-agent

do

pgrep -u $ USER ssh-agent> / dev / null

dzięki czemu zostaną znalezione tylko agenty działające pod bieżącym użytkownikiem, a identyfikator pid nie zostanie wyświetlony na ekranie (czystszy).

Sugerowałbym również zmianę $ HOME / ssh-agent.out na $ HOME / .ssh-agent.out

pozdrowienia

boran
źródło
0

Przeczytałem twoje oryginalne rozwiązanie i kilka sugerowanych, ale postanowiłem uprościć proces na własny użytek. Oto co dodałem we własnym .bashrc:

    # get active ssh-agent, or launch new
    SSH_AGENT_PID=$(ps -fC ssh-agent | grep "ssh-agent -a ${HOME}/.ssh/ssh-agent-socket" | awk '{print $2}')
    if [ -z "${SSH_AGENT_PID}" ]; then
      # If there is no ssh-agent running, we'll make sure one hasn't left a socket file dangling
      rm ${HOME}/.ssh/ssh-agent-socket &> /dev/null
      # And of course start one
      eval $(ssh-agent -a ${HOME}/.ssh/ssh-agent-socket)
    else
      # We found a process matching our requirements, so sticking with that
      export SSH_AGENT_PID
      export SSH_AUTH_SOCK="${HOME}/.ssh/ssh-agent-socket"
    fi

Podjąłem tutaj kilka założeń:

  • Że istnieje katalog ~ / .ssh.
  • Że chcesz tylko jedno gniazdo agenta ssh na użytkownika w systemie.
  • Czy zmienna środowiskowa HOME jest ustawiona (bo dlaczego by nie, prawda?).
  • Że ręcznie poradzisz sobie z sytuacją, w której działa proces, ale z jakiegoś powodu nie używa on wskazanego pliku gniazda.

Podsumowując, wydaje mi się, że to proste rozwiązanie.

użytkownik946031
źródło
0

Odkryłem, że często miałem ssh-agenturuchomionych wiele procesów i że PID w nazwie pliku gniazda nigdy nie był zgodny z PID działającego ssh-agent, więc zhackowałem coś, aby spróbować odzyskać te warunki, na podstawie wielu powyższych przykładów.

Jest to pojedyncza funkcja, wykorzystuje zmienną Zsh jako identyfikator użytkownika, jeśli istnieje, i próbuje poświęcić mniej czasu na analizowanie możliwie dużych /tmpkatalogów, ograniczając find(1)nieco więcej.

Prawdopodobnie wciąż jest podatny na błędy i skomplikowany, ale niektóre pobieżne testy wskazują, że działa głównie w moich przypadkach użycia, więc oto:

attach_ssh_agent () {
  jeśli [-n "$ SSH_AGENT_PID"]; następnie
    ssh-add -l> / dev / null
    ret = $?
    jeśli [$ ret -ge 2]; następnie
      echo „Agent pid $ SSH_AGENT_PID jest mniej niż przydatny (ret = $ ret) - zabijanie ...”
      zabij $ SSH_AGENT_PID
      rozbroić $ SSH_AGENT_PID
    elif [$ ret = 1]; następnie
      echo „Agent pid $ SSH_AGENT_PID jest mniej niż przydatny (ret = $ ret) - będzie go inicjował ...”
    jeszcze
      echo „Agent pid $ SSH_AGENT_PID”
      powrót
    fi
  fi
  jeśli [-S "$ SSH_AUTH_SOCK"]; następnie
    ssh-add -l> / dev / null
    ret = $?
    jeśli [$ ret = 2]; następnie
      echo „Socket $ SSH_AUTH_SOCK nie działa - usuwanie ...”
      rm -f $ SSH_AUTH_SOCK
      odblokuj SSH_AUTH_SOCK
    elif [$ ret = 1]; następnie
      echo „Socket $ SSH_AUTH_SOCK wskazuje na agenta bez kluczy ...”
      ssh-add
    jeszcze
      echo "Znaleziono ssh-agent $ SSH_AUTH_SOCK (ret = $ ret)"
      powrót
    fi
  fi
  dla sf w $ (find / tmp / -mindepth 2 -maxdepth 2 -uid $ {UID: - $ (id -u)} -path '/tmp/ssh-*/agent.*' -type s); zrobić
    test -r $ sf || dalej
    eksport SSH_AUTH_SOCK = $ sf
    SSH_AGENT_PID = $ (basename $ SSH_AUTH_SOCK | cut -d. -F2)
    # wyścigi z innymi widłami procesowymi, argh
    spróbuj = 50
    podczas gdy [$ try -gt 0]; zrobić
      try = $ (($ try-1))
      eksport SSH_AGENT_PID = $ (($ SSH_AGENT_PID + 1))
      echo „Testowanie $ SSH_AUTH_SOCK -> $ SSH_AGENT_PID”
      ssh_agent_running = $ (ps -u $ USER | grep ssh-agent)
      if [-z "$ ssh_agent_running"]; następnie
        echo „Socket $ SSH_AUTH_SOCK nie zawiera łącza do żadnego działającego agenta - usuwanie ...”
        rm -f $ SSH_AUTH_SOCK
        dalej
      fi
      jeśli echo „$ ssh_agent_running” | \
           awk „$ 1 == '$ SSH_AGENT_PID” {
                  znaleziono = 1;
                  wyjście (0);
              }
              KONIEC {
                  Jeśli znaleziono) {
                      print ”nie znaleziono uruchomionego PID„ $ SSH_AGENT_PID ””;
                      wyjście (1);
                  }
              } ”; następnie
        ssh-add -l> / dev / null
        ret = $?
        jeśli [$ ret -ge 2]; następnie
          echo „Socket $ SSH_AUTH_SOCK nie zawiera linku do przydatnego agenta w $ SSH_AGENT_PID - usuwanie ...”
          rm -f $ SSH_AUTH_SOCK
          zabij $ SSH_AGENT_PID
          odblokuj SSH_AGENT_PID
          kontynuuj 2
        elif [$ ret = 1]; następnie
          echo „Socket $ SSH_AUTH_SOCK zawiera link do mało przydatnego agenta w $ SSH_AGENT_PID - seeding ...”
          ssh-add
          Jeśli ! ssh-add -l> / dev / null; następnie
            echo „Socket $ SSH_AUTH_SOCK nadal zawiera link do mniej przydatnego agenta w $ SSH_AGENT_PID - przerywanie.”
            powrót
          jeszcze
            przerwa
          fi
        jeszcze
          przerwa
        fi
      jeszcze
# echo "Nie można dopasować gniazda $ SSH_AUTH_SOCK do agenta PID $ SSH_AGENT_PID - pomijanie ..."
        dalej
      fi
    gotowy
    if [$ try -gt 0]; następnie
      echo „Znaleziono ssh-agent $ SSH_AUTH_SOCK”
      echo „Agent pid $ SSH_AGENT_PID”
      powrót
    fi
  gotowy
  if [-n "$ try" -a -n "$ SSH_AUTH_SOCK" -a -n "$ ssh_agent_running"]; następnie
    echo „Próbowaliśmy wiele razy, ale nie mogliśmy dopasować $ SSH_AUTH_SOCK do żadnego z działających agentów, westchnienie”
    echo „$ ssh_agent_running”
    echo „Pozostawienie tych resztek i rozpoczęcie nowego agenta ...”
  fi
  eval $ (ssh-agent -t 28800)
  ssh-add
}
Josip Rodin
źródło
0

Oto moja uwaga na ten temat. „ Źródło ” poniższego skryptu z mojego pliku .bash_profile :

MYAGENTS=(`pgrep -U $USER -f ^ssh-agent$|sort -n`)

echo "Found ${#MYAGENTS[@]} ssh-agents."

# Let's try to take over the agents, like we do everynight Pinky!
if [[ "${MYAGENTS[@]}" ]];then
  KEEPER=${MYAGENTS[0]}
  echo KEEPER: $KEEPER
  OUTCAST=${MYAGENTS[@]:1}
  [[ "$OUTCAST" ]] && { echo "Goodbye agent $OUTCAST"; kill $OUTCAST; }
  SSH_AUTH_SOCK=`awk '/tmp\/ssh/ {print $NF}' /proc/$KEEPER/net/unix`
  export SSH_AUTH_SOCK;
  SSH_AGENT_PID=$KEEPER; export SSH_AGENT_PID;
else
  NEWAGENT="`ssh-agent`"
  echo $NEWAGENT;
  eval $NEWAGENT
fi

ssh-add -l | grep "The agent has no identities" && ssh-add
AX Labs
źródło
0

Oto prosty skrypt, który zawsze ponownie użyje tego samego agenta ssh lub uruchomi ssh-agent, jeśli nie jest uruchomiony. Kluczem jest skorzystanie z -aopcji użycia tej samej nazwy gniazda. W przeciwnym razie domyślnie wybierze losową nazwę gniazda za każdym razem. Możesz łatwo połączyć te 3 linie w alias 1-liniowy.

# set SSH_AUTH_SOCK env var to a fixed value
export SSH_AUTH_SOCK=~/.ssh/ssh-agent.sock

# test whether $SSH_AUTH_SOCK is valid
ssh-add -l 2>/dev/null >/dev/null

# if not valid, then start ssh-agent using $SSH_AUTH_SOCK
[ $? -ge 2 ] && ssh-agent -a "$SSH_AUTH_SOCK" >/dev/null

źródło

wisbucky
źródło