Ein Beispiel-Script mit expect als Subscript

scripting

Das Paket expect bietet die Möglichkeit Scripte zu erstellen, die auf bestimmte Ausgaben anderer Programme warten und darauf reagieren. Das funktioniert auch bei entfernten Rechnern, wie ich mit folgendem fiktiven Beispiel zeigen möchte.
Es wird dabei angenommen, dass das Administrations-Passwort auf mehreren Servern automatisch geändert werden soll. Der Einfachheit halber geht das Script davon aus, dass alle Server das gleiche Administrationspasswort haben, was der Sicherheit nicht unbedingt zuträglich ist.
Auf dem ausführenden Rechner muss natürlich das Paket expect installiert sein.

Zugangsdaten für expect

Die Zugangsdaten bekommt expect aus einer csv-Datei pw_list.csv, in der der Admin-Kontoname, das aktuelle Passwort und das neue Passwort stehen. Diese Datei sieht dann z.B. so aus.

admin huThz%d#lhIFt UE4s#jkl!zqJdER

Das Script prüft nicht auf Return- und New-Line-Codes, so dass am Ende der Zeile kein RETURN stehen darf.

Die Liste der IP-Adressen

Die IP-Adressen der Rechner stehen in einer zweiten csv-Datei ip_list.csv, die in jeder Zeile eine Adresse enthält, um sie mit read LINE einzulesen. Auch hier sollte am Ende kein RETURN stehen, damit das Script sich sauber beendet.

10.10.1.200
10.10.1.201
10.10.1.202
10.10.2.200

Das Startscript

Das Startscript kümmert sich um das Einlesen der Variablen und ruft für jede IP-Adresse in der ip_list.csv das expect-Script pw_expect.sh auf.
Im Einzelnen passeirt folgendes: In Zeile 5 und 6 werden die Dateinamen in Variablen geschrieben und in Zeile 7 bis 11 die Zugangsdaten eingelesen. Danach wird jede IP-Adresse aus der IP-Liste ip_list.csv abgearbeitet.
Durch das sleep 10 hat man am Bildschirm die Möglichkeit, das Ergebnis für jede Adresse zu überprüfen. Da im expect-Script ein LOG-File definiert wird, wird die Bildschirmausgabe auch mit protokolliert.

#!/bin/bash
# pw_change.sh

# Vatiablen belegen
IPLIST="ip_list.csv"
PWLIST="pw_list.csv"
while read LINE; do
	ADMIN="$(echo "$LINE" | awk '{print $1}')";
	OLDPW="$(echo "$LINE" | awk '{print $2}')";
	NEWPW="$(echo "$LINE" | awk '{print $3}')";
done < $PWLIST

# IP-Liste abarbeiten
while read LINE; do
	IPSRV="$(echo "$LINE")";
        expect pw_expect.sh $ADMIN $IPSRV $OLDPW $NEWPW
sleep 10
done < $IPLIST

Das expect-Script

Zeile 5 setzt zunächst mal den Timeout für expect auf unendlich. Danach werden die von pw_change.sh übergebenen Werte in Variablen eingelesen und mit spawn ssh die Verbindung zum Rechner hergestellt. Die vom Zielrechner erwarteten Zeichenketten sind hier sehr verkürzt, um sowohl deutsche als auch englische Systeme abdecken zu können.

#!/usr/bin/expect
#pw_expect.sh

log_file expect.log
set timeout -1
set eadmin [lindex $argv 0]
set eipsrv [lindex $argv 1]
set eoldpw [lindex $argv 2]
set enewpw [lindex $argv 3]
spawn ssh $eipsrv -l $eadmin
expect { "word: " { send "$eoldpw\r" }
	"(yes/no)?" { send "yes\r" exp_continue }
	"word: " { send "$eoldpw\r" }
}
expect { "$ " { send "passwd\r" }
}
expect { "UNIX*: " { send "$eoldpw\r" }
}
expect { "n*UNIX*: " { send "$enewpw\r" }
}
expect { "*UNIX*: " { send "$enewpw\r" }
}
expect { "$ " { send "logout\r" }
}
expect eof

Wird eine Zeichenfolge in der Konsole ausgegeben, die von expect erwartet wird. dann wird der Inhalt der Variablen oder ein Text gesendet.
In Zeile 11 bis 13 sieht man, wie man zwei unterschiedliche Möglichkeiten auswertet. Verbindet man sich bei per SSH mit einem Rechner das erste Mal, dann wird nicht sofort das Passwort abgefragt, sondern zuerst die Bestätigung für den Schlüssel angezeigt, die man mit yes bestätigen muss und erst danach kommt die Passwortabfrage.
Der Aufbau ist wie bei einer OR-Verknüpfung mit dem Unterschied, dass nach dem Erkennen des (yes/no)? in Zeile 12 durch exp_continue auch Zeile 13 noch ausgeführt wird. Bei einer OR-Verknüpfung (also ohne exp_continue) würde nur eine der drei Möglichkeiten abgearbeitet.

Fehlerbehebung

Treten Fehler auf, dann ist die erste Wahl, expect in Zeile 16 von pw_change.sh mit dem Parameter -d aufzurufen.

Was ich hier gezeigt habe, ist nur ein sehr kleiner Ausschnitt aus den Fähigkeiten des Pakets expect.
Weitere Informationen und Beispiele findet man dazu auf der -> Manpage.

Ähnliche Beiträge:
-> Dateien mit Batch-Script umbenennen
-> Bildschirmauflösung von Raspberry-Pi in der Virtualbox ändern

Buy Me a Coffee at ko-fi.com

You May Also Like

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert

Diese Website verwendet Akismet, um Spam zu reduzieren. Erfahre mehr darüber, wie deine Kommentardaten verarbeitet werden.

Aus persönlichen Gründen...

... kann ich den Blog im Moment leider nicht wie gewohnt betreuen und Anfragen zeitnah beantworten. Lediglich die technische Funktionalität versuche ich aufrecht zu erhalten. Sollte es trotzdem was Neues hier geben, dann schreibe ich eine Info in die Telegram-Gruppe.


In der Telegram-Gruppe können Sie sich weiterhin mit anderen Lesern von Împuşcătura austauschen.

Zur Telegram-Gruppe