SSH bağlantısını kontrol etmek için bir bash betiği nasıl oluşturulur?


90

Uzak makinelerde oturum açacak ve özel ve genel anahtarlar oluşturacak bir bash betiği oluşturma sürecindeyim.

Benim sorunum, uzak makinelerin çok güvenilir olmaması ve her zaman devrede olmamasıdır. SSH bağlantısının olup olmadığını kontrol edecek bir bash betiğine ihtiyacım var. İleride kullanmak üzere anahtarları gerçekten oluşturmadan önce.


2
Tipik olarak, ssh-keygenyerel makinede bir anahtar çifti oluşturmak için çalıştırılır , ardından ssh-copy-idgenel anahtarı uzak makinelere kopyalar. Görünüşe göre işleri farklı yapıyorsun. Neden, amacın nedir?
ephemient

1
Uzak makinelerin bağlantı kurma şeklini açıkça değiştirdiğiniz için, mosh'u dağıtmayı düşünün . mosh.mit.edu Kararsız bağlantılarda SSH'yi desteklemek için tasarlanmıştır. Onunla çok iyi deneyimlerim var.
Aeyoun

Geç biraz biliyorum ama onlar anahtarı olduğunu oldukça basit görünüyor @ephemient değil yerel makine için veya değil yerel kullanıcı için.
Terkedilmiş Sepet

Yanıtlar:


176

Bunu, ssh'nin size verdiği dönüş değeriyle kontrol edebilirsiniz:

$ ssh -q user@downhost exit
$ echo $?
255

$ ssh -q user@uphost exit
$ echo $?
0

DÜZENLEME: Başka bir yaklaşım da nmap kullanmak olacaktır (anahtarlara veya oturum açma öğelerine ihtiyacınız olmayacak):

$ a=`nmap uphost -PN -p ssh | grep open`
$ b=`nmap downhost -PN -p ssh | grep open`

$ echo $a
22/tcp open ssh
$ echo $b
(empty string)

Ancak mesajı grep etmeniz gerekir (nmap, bir bağlantı noktasının filtrelenmiş, kapalı veya açık olup olmadığını göstermek için dönüş değerini kullanmaz).

DÜZENLEME2:

Eğer ssh-port fiili duruma ilgilenen ediyorsanız, yerini alabilir grep openile egrep 'open|closed|filtered':

$ nmap host -PN -p ssh | egrep 'open|closed|filtered'

Sadece tamamlanmak için.


1
Tam olmak için, hangi dönüş kodunun başarı anlamına geldiğini ve bunun SSH'de başarısızlık olduğunu belirtebilir misiniz?
Henley Chiu

Acaba SSH denemesi orada asılı kalırsa?
Sibbs Kumar

2
Mükemmel cevap! Ancak, sshkapalı bir ana makineye girme girişiminin ancak örneğin 60 saniyelik bir zaman aşımından sonra başarısız olduğunu belirtmiyorsunuz - bu bazı kullanımlar için engelleyici olabilir. Ayrıca, bir ana bilgisayar adı tanımlanmışsa , ikinci yaklaşım başarısız olurken ~/.ssh/configbirinci sshyaklaşım çalışır . nmapFailed to resolve "<hostname>"
ssc

2
komutlar hakkında hiçbir açıklama yok ... ya da gerçekte ne yaptığınız .. nedir $?? vb
Toskan

# 1'in daha da kısa bir biçimi: ssh -q user@downhost exit | echo $? bağlantı sonucunu
echo'ya aktar

23

Bunun gibi bir şey kullanabilirsin

$(ssh -o BatchMode=yes -o ConnectTimeout=5 user@host echo ok 2>&1)

Ssh bağlantısı uygunsa bu "ok" çıktısını verecektir.


22
ssh -q -o "BatchMode=yes" -i /home/sicmapp/.ssh/id_rsa <ID>@<Servername>.<domain> "echo 2>&1" && echo $host SSH_OK || echo $host SSH_NOK

2
Bir satır çıkışı: (ssh -q -o "BatchMode = yes" -o "ConnectTimeout = 3" user@host.com "echo 2> & 1" && echo SSH_OK || echo SSH_NOK) | kuyruk -n1
Xdg

15

Yanıtınızı tamamlayarak @Adrià Cidreşunları yapabilirsiniz:

status=$(ssh -o BatchMode=yes -o ConnectTimeout=5 user@host echo ok 2>&1)

if [[ $status == ok ]] ; then
  echo auth ok, do something
elif [[ $status == "Permission denied"* ]] ; then
  echo no_auth
else
  echo other_error
fi

7

Deneyin:

echo quit | telnet IP 22 2>/dev/null | grep Connected

1
Bu yaklaşımın bir sorunu, ssh_config (yani / etc / ssh / config veya ~ / .ssh / config) içinde tanımlanan ana bilgisayarları tanımamasıdır
Ding-Yi Chen

1

Aşağıdaki sshkomut, 0başarılı bir bağlantıda çıkış koduna ve aksi takdirde sıfır olmayan bir değere sahip olmalıdır.

ssh -q -o BatchMode=yes user@remote.com exit

if [ $? != "0" ]; then
    echo "Connection failed"
fi

Harika! Hedef bağlantı noktasının filtrelendiği durumlarda daha hızlı çıkış için -o ConnectTimeout = 5 eklemesini de öneririm.
Daniel

0

Birinin yalnızca 22 numaralı bağlantı noktasının uzaktaki bir makinede açık olup olmadığını kontrol etmek istemesi durumunda, bu basit netcat komutu kullanışlıdır. Bunu kullandım çünkü nmap ve telnet benim için mevcut değildi. Ayrıca, ssh yapılandırmam klavye parolası kimlik doğrulamasını kullanıyor.

GUESSWHOz tarafından önerilen çözümün bir çeşididir.

nc -q 0 -w 1 "${remote_ip}" 22 < /dev/null &> /dev/null && echo "Port is reachable" || echo "Port is unreachable"

0

Uzak bir klasörün var olup olmadığını kontrol etmek veya gerçekten başka bir dosya testi yapmak isterseniz:

if [ -n "$(ssh "${user}@${server}" [ -d "$folder" ] && echo 1; exit)" ]; then
    # exists
else
    # doesn't exist
fi

Alıntıları unutma "$(ssh ...)".


Bu soruya cevap vermiyor. OP, uzak ssh konumundaki bir dosyayı kontrol etmeden SSH bağlantısının kurulup kurulamayacağını kontrol etmek ister.
Rakib Fiha

0

Birden çok arayüze sahip bir sunucuya bağlanmak için

ssh -o ConnectTimeout=1 -q Necktwi@192.168.1.61;[ $? = 1 ] || ssh -o ConnectTimeout=1 -q Necktwi@192.168.1.51

0

BASH 4+ komut dosyasını kullanma örneği:

# -- ip/host and res which is result of nmap (note must have nmap installed)
ip="192.168.0.1"
res=$(nmap ${ip} -PN -p ssh | grep open)

# -- if result contains open, we can reach ssh else assume failure) --
if [[ "${res}" =~ "open" ]] ;then
    echo "It's Open! Let's SSH to it.."
else
    echo "The host ${ip} is not accessible!"
fi

0

https://onpyth.blogspot.com/2019/08/check-ping-connectivity-to-multiple-host.html

Yukarıdaki bağlantı, bağlantıyı kontrol etmek için Python betiği oluşturmaktır. Benzer yöntemi kullanabilir ve kullanabilirsiniz:

ping -w 1 -c 1 "IP Address" 

Bash betiği oluşturma komutu.


2
Bu yalnızca uzak IP'ye ping atacaktır. Ssh bağlantısının mümkün olup olmadığını garanti etmez.
RJ

Bunu belirttiğiniz için teşekkürler, işte ssh için kod xlinu.blogspot.com/2019/09/… export user = "kullanıcı adı" dışa aktarma şifresi = "şifre" export i = "ana bilgisayar adı" dışa aktar SSHPASS = $ pass sshpass -e ssh $ user @ $ i -q "echo $ i Erişilebilir"
Dheeraj Kumar

-7

Burada yanlış sorunu çözmeye çalıştığını hissediyorum. Ssh artalan süreçlerini daha kararlı hale getirmeye çalışmanız gerekmez mi? Monit gibi bir şey çalıştırmayı deneyin ; bu, arka plan programının çalışıp çalışmadığını kontrol eder ve çalışmıyorsa yeniden başlatır (sshd'nin kapatılmasının arkasındaki kök sorunu bulmanız için size zaman verir). Yoksa ağ hizmeti sorunlu mu? Bakmayı dene man ifup. Bütün Lanet Şey seni kapatmaktan hoşlanıyor mu? Bu daha büyük bir sorun ... kutunuzu kapatan donanım arızalarını veya hizmetleri (belki bir sıcaklık monitörü?) Bulmak için günlüklerinize bakmayı deneyin (syslog ile başlayın).

Komut dosyalarınızı hataya dayanıklı hale getirmek harikadır, ancak kutucuğunuzu hataya dayanıklı yapmak da isteyebilirsiniz.


4
Sam: Betiğin onu kontrol etmesi için geçerli kullanım örnekleri var. Örneğin (benim gibi): Verilerimi rsync aracılığıyla evime yedeklemek için makinemde çalışan bir cron işi var. Şimdi dışarıdayım veya hatta sık sık bağlantım kesiliyor ve bağlantı mevcut değilse yeniden planlamam gerekiyor. Demişler Benim boxe çalışır oldukça iyi, ama: her zaman (ağ aka) kablosu
stwissel
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.