Da diverso tempo realizzo progetti che ruotano nell’intorno dell’ecosistema IoT (Internet Of Things) utilizzando delle SBC (Single Board Computer) come il Raspberry Pi. All’interno dell’ecosistema IoT il Message Broker e uno di quei componenti, direi fondamentali, che abilitano le comunicazioni tra i “pezzi di ferro”.
Il protocollo MQTT è di fatto il re della connettività machine-to-machine (M2M), divenuto sempre più popolare con l’evoluzione e la divulgazione dei concetti IoT. Il protocollo MQTT può essere pensato come un analogo leggero e semplificato di AMQP, anch’esso basato sul modello publish/subscribe, ma fornisce un footprint di rete molto più piccolo e può essere utilizzato da dispositivi di piccole dimensioni e con limitate capacità di calcolo.
Esistono molti Message Broker MQTT Open Source e a pagamento disponibili per l’uso, come ad esempio:
Apache ActiveMQ è uno tra i più diffusi Message Broker Open Source, multi-protocollo, basato su Java. Supporta i protocolli standard del settore in modo che gli utenti ottengano i vantaggi delle scelte dei client su un’ampia gamma di linguaggi e piattaforme. Attualmente sono disponibili due “versioni” di ActiveMQ: il broker “classico” 5.x e il broker Artemis di “nuova generazione” per applicazioni di messaggistica basate sugli eventi (event-driven messaging applications). Quando Artemis raggiungerà un livello sufficiente di parità di funzionalità con la base di codice 5.x, diventerà ActiveMQ 6.
Nei miei progetti utilizzo solitamente RabbitMQ (ma anche CloudAMQP) e Apache ActiveMQ. Recentemente ho iniziato a fare qualche esperimento con Apache ActiveMQ Artemis installato come Message Broker su Raspberry Pi.
In questo articolo desidero mostrarvi come realizzare la propria immagine Docker di Apache ActiveMQ Artemis per piattaforme ARM e di conseguenza eseguibili su Raspberry Pi.
1. Da dove iniziare?
Si parte andando sulla home page del progetto ActiveMQ Artemis, e poi da qui, puntiamo subito alla sezione Easy Docker Creation.
ActiveMQ Artemis fornisce alcuni semplici script per iniziare a lavorare con Docker. Per fare in modo che sia possibile generare le proprie immagini Docker anche per piattaforme ARM, circa due settimane fa ho avuto modo di dare un contributo al progetto ActiveMQ Artemis, estendendo il modulo artemis-docker.
Prima di proseguire oltre vediamo quali sono i requisiti:
- git è opzionale. In caso è possibile scaricare da GitHub il progetto in formato zip;
- JDK 8 o 11. È consigliato creare le proprie immagini Docker SNAPSHOT utilizzando la JDK 11 per la build dei sorgenti, visto che il modulo artemis-docker consente di creare immagini Docker per ARM partendo dall’immagine di AdoptOpenJDK 11;
- Maven 3.x è opzionale. In caso è possibile utilizzare il wrapper Maven (mvnw) incluso all’interno del progetto;
- Docker 19.x/20.x;
- Docker Buildx. Per le versioni di Docker dalla 19.03, buildx è incluso, non è necessario installarlo in modo separato;
- Repository su Docker Hub dove ospitare le immagini Docker che andremo a creare. È necessario per poi rendere agevole l’installazione dell’immagine Docker creata sul vostro Raspberry Pi.
Iniziamo dunque eseguendo il clone del progetto ActiveMQ Artemis. Per il nostro scopo possiamo anche eseguite il clone del repository Git del progetto senza portarci dietro tutta la cronologia: git clone --depth 1 https://github.com/apache/activemq-artemis.git
2. Creiamo la nostra immagine Docker
Grazie al modulo artemis-docker, abbiamo una serie di opzioni per ottenere diverse immagini Docker:
- creare l’immagine Docker per la release ufficiale di ActiveMQ Artemis;
- creare l’immagine Docker per la distribuzione locale, ovvero, per la versione SNAPSHOT ottenuta dalla build dei sorgenti;
- creare l’immagine Docker basata su immagini CentOS e Debian con Java 8;
- creare l’immagine Docker basata su Ubuntu con Java 11 nell’implementazione di AdoptOpenJDK;
- creare l’immagine Docker per ARM (ARMv7/ARM64).
Il readme.md del modulo artemis-docker descrive chiaramente come perseguire le opzioni sopra elencante. Noi ci concentreremo su come creare l’immagine Docker per ARM, sia per la release ufficiale di ActiveMQ Artemis sia per la versione SNAPSHOT, quest’ultima utile al fine di provare le nuove funzionalità prima del rilascio della versione ufficiale.
La creazione dell’immagine Docker per ARM per la versione SNAPSHOT prevede i seguenti step. L’attuale versione di SNAPSHOT (al momento della pubblicazione di questo articolo) è la 2.18.0.
- Clone del repository di ActiveMQ Artemis.
- Build del progetto per ottenere la distribuzione SNAPSHOT.
- Preparazione dei Docker file per la distribuzione locale.
- Build dell’immagine Docker per ARM e push sul repository Docker Hub.
Il tempo di build del progetto è variabile in base alla potenza di calcolo della propria macchina, per esempio, sul mio Mac Book Pro (Mid-2017) i7-7660U con 16GByte di RAM è di circa 5 minuti (senza l’esecuzione di unit test). L’operazione di build dell’immagine Docker spende il tempo maggiore nelle operazioni di push e pull, e questo dipende dalla connettività che si ha a disposizione verso la rete internet.
Nel caso in cui non aveste una buona connettività di rete, potreste incorrere in errori di questo tipo:
- failed to compute cache key: failed commit on ref “layer-sha256:f60421c1f”: failed size validation: 2292149 != 24043427: failed precondition
- net/http: TLS handshake timeout
- failed to copy: unexpected status: 504 Gateway Time-out
A seguire sono indicati i comandi necessari per soddisfare i quattro step sopra descritti.
# 1. Clone the repository
$ git clone --depth 1 https://github.com/apache/activemq-artemis.git
# 2. Build of the project
$ cd activemq-artemis
# If you want skip the test use the -DskipTests argument
$ mvn clean install
# 3. Prepare the Docker file
$ cd artemis-docker
$ ./prepare-docker.sh --from-local-dist --local-dist-path ../artemis-distribution/target/apache-artemis-2.18.0-SNAPSHOT-bin/apache-artemis-2.18.0-SNAPSHOT
# 4. Build the Docker image for ARM. You should replace the {your-username} and {your-repository-name} placeholders with your values
$ cd ../artemis-distribution/target/apache-artemis-2.18.0-SNAPSHOT-bin/apache-artemis-2.18.0-SNAPSHOT
$ docker buildx build --platform linux/arm64,linux/arm/v7 --push -t {your-username}/{your-repository-name}:2.18.0-SNAPSHOT -f ./docker/Dockerfile-adoptopenjdk-11 .
Se l’esecuzione dello script prepare-docker.sh (step 3) va a buon fine, a schermo dovreste vedere quando mostrato dalla figura a seguire, ovvero, gli script (Docker file e script per l’esecuzione del container) che sono stati creati all’interno della directory docker che a sua volta si trova all’interno della directory di distribuzione di ActiveMQ Artemis, inoltre, troverete le informazioni utili per proseguire con la build dell’immagine Docker.
Figure 1 – Docker image build preparation script output
Per il comando di build dell’immagine Docker (step 4), dovreste sostituire i placeholder {your-username} / {your-repository-name} con i vostri valori. Nel mio caso questo si traduce in amusarra/apache-artemis.
Figure 2 – Execution of the buildx command to generate the Docker image for ARM
Dopo l’esecuzione dello step 4, dovreste vedere sul vostro repository Docker Hub l’immagine di ActiveMQ Artemis versione 2.18.0-SNAPSHOT. La figura a seguire mostra in particolare il contenuto del mio repository amusarra/apache-artemis.
Figure 3 – The content of the Docker Hub repository amusarra/apache-artemis after build and push
Se volessimo invece preparare l’immagine Docker di ActiveMQ Artemis versione 2.16.0 (l’attuale versione di release), gli step si riduco a due:
- preparazione dei Docker file per la versione release (in questo caso la 2.16.0);
- build dell’immagine Docker per ARM e push sul vostro repository Docker Hub.
# 1. Prepare the Docker file
$ cd artemis-docker
$ ./prepare-docker.sh --from-release --artemis-version 2.16.0
# 2. Build the Docker image for ARM
$ cd _TMP_/artemis/2.16.0
$ docker buildx build --platform linux/arm64,linux/arm/v7 --push -t {your-username}/{your-repository-name}:2.16.0 -f ./docker/Dockerfile-adoptopenjdk-11 .
La figura a seguire mostra l’output dello script prepare-docker.sh che a differenza della prima esecuzione, scarica la versione 2.16.0 di ActiveMQ Artemis e successivamente mostra gli script (Docker file e script per l’esecuzione del container) che sono stati creati all’interno della directory docker (che a sua volta e contenuta dentro la directory _TMP_/artemis/2.16.0/docker), inoltre, mostra le informazioni utili per proseguire con la build dell’immagine Docker.
Figure 4 – Docker image build preparation script output
A questo punto dovreste avere sul vostro repository Docker Hub la versione 2.16.0 e 2.18.0-SNAPSHOT di ActiveMQ Artemis.
Figure 5 – Execution of the buildx command to generate the Docker image for ARM
3. Raspberry Pi: Pull e Run
Finalmente ci siamo! Siete pronti a fare il pull dell’immagine dal nostro repository Docker e successivamente ottenere un container che esegue un’istanza di ActiveMQ Artemis?.
Prima di procedere dobbiamo soddisfare un requisito: Docker 19.x/20.x deve essere correttamente installato sul Raspberry Pi. Riguardo il modello di Raspberry Pi consiglio la versione 4 e il modello con almeno 4GByte di memoria RAM. Nel mio caso ho un Raspberry Pi 4 con 8GByte di RAM, sistema operativo Ubuntu 20.04.02 LTS e Docker 20.10.3.
Figure 6 – Raspberry Pi 4 system information by neofetch
Una volta soddisfatti i requisiti è possibile eseguire il pull e run del container ActiveMQ Artemis utilizzando i comandi a seguire. Eseguiamo il pull di entrambe le versioni delle immagini Docker, anche se poi andremo ad utilizzare la versione 2.16.0.
# 1. Pull the Docker Images of the ActiveMQ Artemis (2.16.0 and 2.18.0-SNAPSHOT)
$ docker pull amusarra/apache-artemis:2.18.0-SNAPSHOT
$ docker pull amusarra/apache-artemis:2.16.0
# 2. Run the ActiveMQ Artemis 2.16.0
$ docker run --rm -d --name activemq-artemis-2160 -p 61616:61616 -p 8161:8161 -p 1883:1883 amusarra/apache-artemis:2.16.0
Nel comando di esecuzione del container, specifichiamo quali porte TCP/IP devono essere esportate all’esterno, in questo caso: console (8161), MQTT (1883) e Multi-Protocol CORE,MQTT,AMQP,STOMP,HORNETQ,OPENWIRE.
La figura a seguire mostra i log del container ActiveMQ Artemis appena avviato correttamente. Le altre figure mostrano l’accesso al pannello di amministrazione di ActiveMQ Artemis, le cui credenziali di accesso (di default) sono artemis/artemis.
Figure 7 – View the logs of the ActiveMQ Artemis Docker container
Figure 8 – Login page of the ActiveMQ Artemis Management Console
Figure 9 – ActiveMQ Artemis view current status
4. Un test molto veloce ma efficace
Adesso che abbiamo messo in piedi sul Raspberry Pi il nostro Message Broker basato su ActiveMQ Artemis, proviamo a fare un semplice test che consiste in:
- creare un topic dove un producer invierà un messaggio (in formato JSON) contenente la temperatura della CPU;
- creare un producer che legge ogni 5 secondi la temperatura della CPU e invia il valore letto sul topic creato in precedenza;
- sottoscriversi al topic per leggere i valori pubblicati.
Chiameremo il topic con il nome RPI4.cpu-temp che andremo a creare utilizzando il primo comando a seguire. Il comando successivo è invece quello responsabile di leggere la temperatura della CPU ogni 5 secondi e pubblicare in il messaggio sul topic appena creato. Entrambe i comandi fanno uso del binario artemis che fa parte dei tool di gestione del server.
# 1. Create the topic RPI4.cpu-temp
$ docker exec -it activemq-artemis-2160 \
/bin/bash ./bin/artemis queue create --user artemis --password artemis \
--address RPI4 --anycast --durable --purge-on-no-consumers \
--auto-create-address --name cpu-temp
# 2. Send CPU Temperature on the topic RPI4.cpu-temp
$ while true; \
do docker exec -it activemq-artemis-2160 \
/bin/bash ./bin/./artemis producer --clientID rpi4 --destination topic://RPI4.cpu-temp --message "$(echo -n '{"cpu-temperature":'; cat /sys/class/thermal/thermal_zone*/temp | sed -e 's/\(.\)..$/.\1/'; echo -n '}')" --message-count 1 --user artemis --password artemis; \
sleep 5; \
done
La figura a seguire mostra il comando di pubblicazione del messaggio sul topic RPI4.cpu-temp in azione. Accedendo alla Management Console è possibile invece vedere alcune informazioni di dettaglio riguardo il numero di sessioni, il numero di connessioni e vedere quali sono gli attuali consumer del topic.
Figure 10 – Produce message to topic RPI4.cpu-temp
Figure 11 – Browse the Session on the ActiveMQ Artemis
Figure 12 – Browse the Consumer on the ActiveMQ Artemis
Figure 13 – Browse the Connection on the ActiveMQ Artemis
Per sottoscriversi al topic RPI4.cpu-temp al fine di poter leggere i valori di temperatura della CPU, potremmo per semplicità, utilizzare un comunissimo client MQTT. Nel mio caso ho utilizzato su macOS l’applicazione MQTT Explorer, di cui a seguire sono mostrate le figure che riguardano la configurazione della connessione verso il Message Broker e la visualizzazione dei dati ricevuti, anche in forma grafica.
Figure 14 – MQTT Explorer Connection configuration
Figure 15 – MQTT Explorer add the topic RPI4.cpu-temp
Figure 16 – MQTT Explorer view data on the RPI4.cpu-temp
Sul mio iPhone ho utilizzato l’app MQTT Analyzer ma esistono comunque app simili anche per la piattaforma Android, come per esempio MQTT Terminal. Le figure a seguire mostrano alcune schermate dell’app mentre legge i valori dal topic RPI4.cpu-temp.
Figure 17 – MQTT Analyzer Connection Settings
Figure 18 – MQTT Analyzer Reading the value on the topic RPI4.cpu-temp
A questo punto direi che possiamo ritenerci soddisfatti del risultato ottenuto. Con questo Message Broker le possibili applicazioni in ambito IoT sono davvero innumerevoli, spazio alla fantasia.
5. Risorse
A seguire vi lascio una serie di risorse che sono utili a scopo di approfondimento.
- Home del progetto ActiveMQ Artemis (https://activemq.apache.org/components/artemis/)
- Easy Docker Creation (https://github.com/apache/activemq-artemis/tree/master/artemis-docker)
- Apache ActiveMQ Artemis Documentation (https://activemq.apache.org/components/artemis/documentation/)
- Raspberry PI Sense HAT: Come pubblicare i dati su CloudAMQP via MQTT
- Raspberry Pi: Come eseguire un Docker Container Apache Karaf 4.2
- Docker: How to create Apache Karaf images for ARM and ARM64
- Internet of Things with Raspberry Pi 3 (https://www.packtpub.com/product/internet-of-things-with-raspberry-pi-3/9781788627405)
- Practical Python Programming for IoT (https://www.packtpub.com/product/practical-python-programming-for-iot/9781838982461)
6. Conclusioni
Pensavate che fosse così semplice installare Apache ActiveMQ Artemis anche su architetture hardware ARM?
Grazie alla partnership tra Docker e ARM (vedi Docker announced a partnership with Arm) annunciata nel mese di aprile del 2019, oggi, siamo stati in grado di eseguire il container Docker di ActiveMQ Artemis sull’architettura *linux/arm * del Raspberry Pi.
Grazie a buildx (di Docker) possiamo quindi creare immagini multi-arch sia per ARM sia per x86 utilizzando Docker. Grazie al tool buildx, siamo riusciti a prepare l’immagine di ActiveMQ Artemis per linux/arm64 e linux/arm/v7 che abbiamo poi usato per installare il servizio di Message Broker multi-protocollo sul Raspberry Pi.
L'articolo ActiveMQ Artemis: Easy Docker Creation also for ARM sembra essere il primo su Antonio Musarra's Blog.
Top comments (0)