Archiv der Kategorie: Computer

MQTT-Server auf dem Raspberry Pi

Ziel

Das Ziel ist es, auf einem Raspberry Pi einen MQTT-Server („Broker“) einzurichten, wie er bspw. für die Heimautomatisierung benötigt wird. In dieser Anleitung werde ich Mosquitto als Broker verwenden.

Voraussetzungen

Benötigt wird ein fertig eingerichteter Raspberry Pi, den man über SSH erreichen kann und für den man Root-Rechte hat. Hilfreich ist es, wenn man schon weiß, wie MQTT ungefähr funktioniert. Das kann man in der Anleitung aber auch nebenbei lernen.

Installation und Test

Zunächst loggt man sich auf dem Raspberry Pi ein und installiert den MQTT-Server und die Clients per apt:

sudo apt install mosquitto mosquitto-clients

Danach läuft der Server bereits und man kann ihn testen. Dazu ruft man einen Client auf und abonniert alle Topics:

mosquitto_sub -h localhost -v -t '#'

Dabei bedeutet „-h localhost“ dass man den Server auf dem gleichen Rechner benutzt (also den, den man gerade installiert hat), das „-v“ sorgt für eine umfangreichere Ausgabe und „-t ‚#’“ schließlich bedeutet, dass man bei allen Topics mithören möchte, die der Broker verarbeitet. Topics kann man sich vorstellen als Kanäle, über die man wie im Funkverkehr empfangen und senden kann, wenn man den passenden Kanal eingestellt hat. Man sendet hier allerdings nur an den Broker und der verteilt die Nachricht an alle weiter, die diesen Kanal bzw. dieses Topic empfangen möchten.

Da (vermutlich) noch kein anderer Client verbunden ist, wird man noch keine Ausgabe sehen. Zum weiteren Testen öffnet man deshalb ein weiteres Fenster, in dem man sich erneut mit dem Raspberry Pi verbindet. Dort veröffentlicht man dann eine Nachricht über den Broker:

mosquitto_pub -h localhost -t 'Test-Topic' -m 'Hallo Welt!'

Mit „-t“ wählt man dazu das Topic aus, unter dem man veröffentlichen will und mit „-m“ gibt man die Nachricht an. Im ersten Fenster sieht man dann die Ausgabe, die der Broker veröffentlicht hat:

Test-Topic Hallo Welt!

Der MQTT-Broker funktioniert also.

Konfiguration des Brokers

In der Grundkonfiguration gibt es keine Beschränkungen für den Zugriff auf den Broker. Jeder (aus dem Heimnetz) kann also Nachrichten veröffentlichen oder mitlesen. In einer minimalen Konfiguration wollen wir den Zugang nun einschränken. Dazu legen wir hier beispielhaft zwei User an, die jeweils ein Passwort bekommen.

Als erstes muss man eine Datei erzeugen, die die User/Passwort-Kombinationen enthält. Die erzeugt man, indem man sie schon gleich mit dem ersten User füllt, nennen wir ihn hier user1.

mosquitto_passwd -c passwords user1

Man wird nach dem Passwort für den User gefragt und muss dies noch einmal wiederholen. Dann wird die gewünschte Datei erzeugt, hier heißt sie passwords (wie hinter „-c“ angegeben).

Nun kann man noch beliebig viele weitere User hinzufügen:

mosquitto_passwd passwords user2

Wieder muss man das Passwort zweimal eingeben. Alternativ kann man auch die Option „-b“ verwenden und das Passwort in die Kommandozeile schreiben. Allerdings sollte man sich angewöhnen, nie Passwörter in Kommandos zu verwenden, denn diese werden dadurch auch für andere Benutzer auf dem gleichen Rechner sichtbar. Auch wenn man niemanden sonst auf seinen Rechner lässt, sollte man sich solche Unachtsamkeiten erst gar nicht angewöhnen.

Wir haben jetzt eine Datei passwords im aktuellen Verzeichnis liegen, also vermutlich in unserem Heim-Verzeichnis. Diese Datei verschieben wir nun ins passende Verzeichnis unter /etc. Und weil es sicher sein soll, überschreiben wir die Datei an den Benutzer root und gewähren nur ihm Schreibzugriff darauf:

sudo mv passwords /etc/mosquitto/conf.d/
sudo chown root:root /etc/mosquitto/conf.d/passwords
sudo chmod 644 /etc/mosquitto/conf.d/passwords

Jetzt brauchen wir noch eine Konfigurationsdatei, die diese Datei einbindet und die den anonymen Zugang unterbindet. Die legen wir im gleichen Verzeichnis ab wie die Passwort-Datei (also /etc/mosquitto/conf.d). Am besten macht man das gleich als root. Ich benutze meinen Lieblingseditor vim (eine beliebte Alternative ist nano):

sudo vim /etc/mosquitto/conf.d/auth.conf

Man fügt zwei Zeilen ein:

allow_anonymous false
password_file /etc/mosquitto/conf.d/passwords

Damit die neue Konfiguration greift, muss man den Dienst noch neu starten. Das muss man auch dann tun, wenn man nur die Datei mit den Passwörtern ändert.

sudo systemctl restart mosquitto

Danach kann man sich nur noch mit Mosquitto verbinden, wenn man einen der zuvor eingerichteten Zugänge benutzt. Eine anonyme Verbindung funktioniert nicht mehr und natürlich auch keine mit falschen Zugangsdaten.

Der Vollständigkeit halber möchte ich noch erwähnen, wie man ausprobieren kann, ob ein Zugang funktioniert, auch wenn man dazu das Passwort im Kommando angeben muss, was man ja nicht tun sollte! Hier geht es aber nicht anders:

mosquitto_pub -u user1 -P passwort1 -t 'Test-Topic' -m 'Ich bin drin!'

Wenn man ein falsches Passwort benutzt oder einen unbekannten Benutzernamen, wird der Broker die Verbindung nicht zulassen. Ebenso nicht, wenn man gar keine Zugangsdaten angibt.

Die Angabe des Host-Namens habe ich hier übrigens weggelassen, denn localhost ist der Default-Host.

Schauen wir zum Abschluss noch auf die beiden Direktiven allow_anonymous und password_file. Diese kann man auch jeweils weg lassen. Das ergibt vier Möglichkeiten, die alle zu einem unterschiedlichen Verhalten führen.

Fall 1: Wenn man keine der beiden Direktiven benutzt, kann man sich wie am Anfang anonym einloggen, also ohne Zugangsdaten. Man kann aber sogar beliebige Zugangsdaten benutzen, wenn man möchte.

Fall 2: Der Zustand, den wir zuletzt hatten, sowohl allow_anonymous false als auch password_file sind vorhanden. Dann kann man sich nicht mehr anonym verbinden und muss gültige Zugangsdaten angeben.

Fall 3: Es wird nur allow_anonymous false verwendet. Dann kann man sich nicht mehr anonym verbinden. Man kann sich allerdings mit beliebigen (!) Zugangsdaten verbinden.

Fall 4: Es wird nur password_file angegeben. Dann kann man sich anonym einloggen. Man kann aber auch Zugangsdaten angeben. Wenn man das tut, müssen diese allerdings zu einem hinterlegten Zugang passen. Man sollte dann aber explizit allow_anonymous true setzen. Benutzen kann man das mit weiteren Einstellungen um bspw. allen Usern lesenden Zugriff zu ermöglichen, das Schreiben aber zu beschränken.

Soweit eine erste Grundeinrichtung, die ohne viele Umstände funktioniert. Es gibt noch viele Konfigurationsmöglichkeiten, mit dem man Mosquitto weiter absichern kann.

Wichtig: Man sollte sich klar darüber sein, dass in der vorgestellten Grundkonfiguration die Zugangsdaten unverschlüsselt über die Leitung gehen! Das ist ein Problem, wenn jemand anderes im Heimnetz mitlesen kann. Im Zweifelsfall sollte man seinen Mosquitto besser noch per SSL absichern. Wie das geht, ist allerdings einen eigenen Artikel wert.

Raspberry Pi einfach und schnell einrichten

Worum es geht

Ziel ist es, ein Linux-System auf einen Raspberry Pi zu bringen. Dieses soll im „headless“-Modus laufen, also ohne grafische Oberfläche. Damit bekommt man ein Server-Grundsystem, dass man für verschiedene Dienste nutzen kann, wie es bspw. für die Heimautomatisierung gebraucht wird.

Voraussetzungen

Das wird benötigt:

  • Ein Raspberry Pi. Ich benutze das Modell 3 B+, welches schon WLAN an Bord hat. Mit älteren Modellen plus WLAN-Adapter sollte es aber auch funktionieren, ebenso ganz ohne WLAN, wenn man mit einem Netzwerkkabel arbeitet.
  • Eine microSD-Speicherkarte. Ich benutze eine 16 GB-Karte. Es funktioniert aber auch mit weniger (und natürlich auch mit mehr) Speicher.
  • Eine Stromversorgung für das Gerät (Micro-USB-Anschluss, mindestens 2 Ampere).
  • Ggf. ein Netzwerkkabel, wenn es mit dem WLAN nicht sofort funktioniert oder man kein WLAN nutzen will.
  • Einen Rechner mit Internet-Zugang zur Vorbereitung bzw. zur „Fernbedienung“. Ich benutze für diese Anleitung einen Linux-Rechner, damit geht es am einfachsten. Wer Windows benutzt, sollte herausfinden können, wie man einen Schritt auf andere Weise hinbekommt, teilweise erläutere ich das.
  • Einen Kartenleser, mit dem man die Daten auf der SD-Karte ändern kann.
  • Grundwissen über Computer-Netzwerke, insbesondere wie man einen Rechner im eigenen Netz erreicht und wie man SSH benutzt.

Teil 1: Vorbereitungen am PC

Im ersten Teil wird das Betriebssystem heruntergeladen und dann die Speicherkarte so vorbereitet, dass sie im RasPi genutzt werden kann. Dazu benötigt man den RasPi zunächst nicht. Alle Arbeiten erfolgen am PC.

Als Linux-Betriebssystem für den RasPi benutze ich Raspbian. Dieses lädt man sich zunächst herunter. Benötigt wird die „Lite“-Variante, die keine grafische Benutzeroberfläche (Desktop) enthält. Zum Zeitpunkt des Schreiben dieses Artikels ist das Raspbian Stretch Lite. Dabei bezeichnet „Stretch“ die Debian-Version, auf der Raspbian basiert.

Download-Seite: https://www.raspberrypi.org/downloads/raspbian/

Die Desktop-Varianten auf der Seite funktionieren im Folgenden auch. Für ein schlankes, schnelles System ist aber „Lite“ die richtige Wahl.

Beim Herunterladen erhält man ein Zip-Archiv, das eine einzige Datei enthält, nämlich ein Image mit dem Betriebssystem. Diese Datei entpackt man. Sie hat die Dateiendung .img und heißt bei mir

2018-11-13-raspbian-stretch-lite.img

Dieses Image schreibt man nun auf die Speicherkarte. Im Folgenden wird beschrieben, wie das unter Linux geht.

Zunächst schließt man die Speicherkarte am PC an. Dann kann man nachschauen, als welches Gerät sie eingehängt wurde.

lsblk -o KNAME,TYPE,SIZE,MODEL | grep disk
sda       disk   1,8T SAMSUNG xxx
sdb disk 238,5G SAMSUNG SSD xxx
sdc disk 14,9G Mass-Storage
nvme0n1 disk 232,9G Samsung SSD xxx

In diesem Fall also unter sdc, zu erreichen unter /dev/sdc. Das merkt man sich und ändert es in den von mir angegebenen Befehlen entsprechend ab. Das ist äußerst wichtig, denn bei Benutzung eines falschen Devices schreibt man auf einen anderen Datenträger, bspw. eine Festplatte!

Die Karte enthielt vermutlich schon mindestens eine Partition, die automatisch eingehängt wurde. Die hänge ich zuerst aus und schreiben dann das Image auf die Karte (nicht vergessen: sdc ggf. anpassen!):

sudo umount /dev/sdc?*
sudo dd bs=4M if=2018-11-13-raspbian-stretch-lite.img of=/dev/sdc status=progress conv=fdatasync

Die Speicherkarte kann man danach abziehen und wieder anstecken. Das System entdeckt dann darauf zwei Partitionen: boot und rootfs. Einige Dateien darin werden nun so angepasst, dass das Betriebssystem später problemlos startet und kaum noch weitere Arbeiten nötig sind. Bei mir sind die beiden Partitionen auf der SD-Karte so eingehängt, dass ich sie über /media/$USER erreichen kann. Auf anderen Systemen ist der Pfad ggf. anders.

Zunächst muss man auf dem neuen System einen Zugang per SSH ermöglichen. Dazu legt man einfach eine leere Datei ssh an, die im Root-Verzeichnis der Partition boot liegen muss.

touch /media/$USER/boot/ssh

Als nächstes wird die Verwendung des WLANs vorbereitet. Wenn man dies bereits zu diesem Zeitpunkt macht, kann man sich später per WLAN auf dem RasPi einloggen und muss kein Netzwerkkabel anschließen.

Dazu legt man wiederum in der boot-Partition eine Datei wpa_supplicant.conf an (/media/$USER/boot/wpa_supplicant.conf), die folgenden Inhalt hat:

ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev
update_config=1
country=DE

network={
ssid="WLAN-SSID"
psk="WLAN-Passwort"
}

An den Stellen WLAN-SSID und WLAN-Passwort muss man die Zugangsdaten zu seinem eigenen WLAN-Netz angeben. Als country habe ich DE angegeben, auch das sollte man ggf. anpassen.

Jetzt wäre man soweit, die Karte im RasPi einzusetzen, aber noch zwei Kleinigkeiten kann man am besten jetzt erledigen.

Zugang zum RasPi erhält man standardmäßig mit dem Benutzernamen pi und dem Passwort raspberry. Ich möchte aber mit meinem gewohnten Benutzernamen mac arbeiten und dazu keinen zweiten Account auf dem RasPi einrichten. Auch das Umbenennen ist später recht aufwendig. Deshalb machen wir das schon jetzt. Dazu werden mit zwei Kommandos ein paar Dateien in rootfs geändert:

sudo sed -i 's/\bpi\b/mac/g' /media/$USER/rootfs/etc/passwd /media/$USER/rootfs/etc/shadow /media/$USER/rootfs/etc/group
sudo mv /media/$USER/rootfs/home/pi /media/$USER/rootfs/home/mac

Das änderten den User pi zu mac und benennt das Home-Verzeichnis entsprechend um. Um einen eigenen Namen zu benutzen, muss das mac entsprechend an beiden Stellen geändert werden. Alternativ kann man auch die drei Dateien etc/passwd, /etc/shadow und /etc/group mit einem Editor so bearbeiten, dass man die Vorkommen von pi abändert in den bevorzugten Namen. Sie befinden sich in der Partition rootfs.

Zuletzt kann man noch den Host-Namen des Raspberrys schon jetzt ändern, um ihn später im eigenen Netz leichter finden zu können. Der voreingestellte Name ist raspberrypi und wird hier im Beispiel zu raspbian.

sudo sed -i 's/raspberrypi/raspbian/g' /media/$USER/rootfs/etc/hostname

Alternativ kann man auch die Datei /etc/hostname in rootfs mit einem Editor entsprechend ändern. Sie enthält nur eine Zeile mit dem späteren Hostnamen.

Das war es mit den Arbeiten am Dateisystem. Man hängt die Karte nun aus und kann sie anschließend vom PC abziehen.

sudo umount /media/$USER/boot /media/$USER/rootfs

Teil 2: Raspberry Pi konfigurieren

Die Speicherkarte steckt man nun in den RasPi und schließt ihn danach an den Strom an. Nach einer Weile sollte er im lokalen Netz auftauchen, entweder über WLAN verbunden, oder über ein angestecktes Netzwerkkabel. In der Standard-Konfiguration bekommt er per DHCP eine IP aus dem lokalen Netz zugewiesen. Alternativ kann er aber natürlich auch mit dem voreingestellten Namen angesprochen werden. In der Grundkonfiguration war das raspberrypi, oben habe ich das geändert in raspbian, welches ich nun benutzt. Ebenfalls benutze ich den geänderten Benutzernamen mac zum Einloggen. In der Grundkonfiguration war das pi.

Den RasPi erreicht man über SSH. Linux-Nutzer haben dafür alles an Bord. Windows-Nutzer werden vermutlich am ehesten PuTTY benutzen wollen.

ssh mac@raspbian

Das Standard-Passwort lautet raspberry (natürlich auch für den geänderten Benutzernamen). Und dieses sollte man auch als allererstes ändern. Wenn das Einloggen geklappt hat, gibt man ein

sudo raspi-config

… was man ein letztes Mal mit dem alten Passwort raspberry bestätigen muss.

Man wählt nun den ersten Menüpunkt Change User Password mit den Cursor-Tasten aus und drückt <Return>. Die Nachfrage bestätigt man erneut mit <Return> und gibt dann ein neues Passwort ein. Dieses muss man danach noch ein weiteres Mal zur Bestätigung eingeben. Danach hat man für den neuen Account ein eigenes Passwort (das man sich merken muss!).

Bevor man nun die weiteren Menüpunkte abarbeitet, sollte man zuerst den Punkt Update besuchen und das Tool auf den aktuellen Stand bringen. Es wird dann automatisch die aktuelle Version heruntergeladen und installiert und anschließend startet raspi-config neu.

Nun zu den weiteren Einstellmöglichkeiten. Unter Localisation Options sollte man unter Change Timezone die richtige Zeitzone auswählen, damit der RasPi später die richtige Uhrzeit hat. Unter Change Locale kann man zusätzlich de_DE.UTF-8 wählen (mit den Cursor-Tasten dorthin scrollen, mit der Leertaste auswählen und dann mit <Tab> aus der Auswahl springen). Diese Auswahl kann man danach als Default einstellen und enthält dann teilweise deutsche Meldungen im System.

Danach kann man sich die Advanced Options vornehmen. Expand Filesystem sollte auf modernen Systemen nicht mehr nötig sein, dort sollte die zweite Partition bereits beim ersten Start auf die maximale Größe gebracht worden sein. Das kann man gefahrlos aber auch ein zweites Mal machen. Unter Memory Split kann man die Größe des Grafik-Speichers verringern, denn man hat ja ein System ohne Desktop. Hier kann man 16 (MB) eingeben.

Damit ist man mit den wichtigen Punkten durch und kann raspi-config über Finish beenden. Evtl. möchte das System danach neu booten, je nachdem, was man alles ausprobiert hat.

Nun aktualisiert man noch die Software des kompletten Systems:

sudo apt update && sudo apt upgrade

… was man mit dem eigenen Passwort bestätigen muss. Ist dieser Vorgang durch, hat man ein vollständiges Linux-System, das auf dem aktuellen Stand ist.

Nun kann man noch individuelle Einstellungen vornehmen und bspw. weitere Pakete installieren mit Software, die man benötigt. Ich bevorzuge bspw. den Editor vim. Zusätzlich installiere ich auch git, was für spätere Erweiterungen sinnvoll sein kann. Software-Pakete kann man aber jederzeit auf diese Weise installieren, das muss nicht zu diesem Zeitpunkt passieren.

sudo apt install vim git

Außerdem logge ich mich am liebsten ohne Passwort ein. Dazu kopiert man einen zuvor erzeugten SSH-Key auf den RasPi (vom PC aus, von wo man sich einloggen möchte):

ssh-copy-id -i ~/.ssh/id_rsa.pub mac@raspbian

Damit ist die Grundinstallation des Raspberry Pi fertig. Je nach gewünschter weiterer Nutzung kann man nun noch weitere Software installieren und den RasPi für den Einsatz als Server oder Arbeitsmaschine ausrüsten.

Noch ein kleiner Hinweis zum Ausschalten des Systems. Wie jeden anderen Computer darf man den RasPi nicht einfach ausschalten (also den Stecker ziehen). Vorher muss man das System herunterfahren. Dies macht man mit diesem Kommando:

sudo poweroff