Raspberry Pi et RabbitMQ


Avec la multiplication des ordinateurs à la maison et l’arrivée des Raspberry, il y a de nombreux projets de collecte de données, de mesures, etc. Aujourd’hui nous allons voir comment utiliser un broker pour permettre à toutes ces machines de s’échanger simplement des informations grâce à des messages via RabbitMQ.

rabbit_header_logo

RabbitMQ implémente entre autre le protocole AMQP qui permet de transporter des messages contenant de l’information. Ce transport se fait de point à point ou bien sur le principe de l’abonnement à un type de message. Pour certains cela va vous faire penser au boulot où dans les entreprises on retrouve souvent la solution IBM Websphere MQ.
Il y a aussi le protocole MQTT qui lui est plus adapté pour la capture de données pour tout ce qui est capteurs et mesures.

Une fois installé sur le Raspberry, celui-ci se transforme en centre de communication, va recevoir des messages et les renvoyer vers les bons destinataires. Alors à quoi cela va-t-il nous servir ?
Et bien je dirais tout ce qu’une machine a comme information et que vous ne voulez pas conserver dessus ou qui doit déclencher une action sur une autre. Par exemple, une image capturée puis envoyée sur une autre machine pour l’archiver, une mesure qui doit déclencher des actions sur d’autres serveurs, etc.

Comment utiliser le service ? Par programme ou script. Sur le site officiel vous allez retrouver des clients en Java, .NET ou Erlang (le langage utilisé pour développé RabbitMQ). Vous avez aussi des possibilités avec Python (voir ici) ce qui dans le cas du Raspberry peut être plus performant. Pour mes tests en tant que client, je suis sur un Mac donc j’ai pris le Java. Les exemples sont en fin d’article.

Vous pouvez aller encore plus loin en utilisant plusieurs Raspberry Pi en cluster pour améliorer vos performances. Mais c’est déjà à un autre niveau pour moi 🙂

Nous allons donc voir comment installer RabbitMQ sur notre Raspberry Pi (chez moi un modèle 256Mb)

  • Mettre à jour le système
    apt-get update && apt-get -y upgrade
  • Télécharger l’archive. La dernière version est la 3.1.5.
    wget http://www.rabbitmq.com/releases/rabbitmq-server/v3.1.5/rabbitmq-server_3.1.5-1_all.deb
  • Installer les paquets supplémentaires
    apt-get install -y erlang logrotate
  • Installer RabbitMQ
    dpkg -i rabbitmq-server_3.1.5-1_all.deb

    Si vous avez une erreur essayez la commande

    apt-get -f install

    Elle va installer les dépendances manquantes et RabbitMQ.

  • Activer les plugins de gestion du serveur
    rabbitmq-plugins enable rabbitmq_management

    Puis redémarrer le service

    service rabbitmq-server restart
  • Accéder au Raspberry Pi à l’adresse http://<ip du raspberry>:15672/#/
    RabbitMQ_ManagementLe serveur web, même sur un 256Mb, est vraiment rapide.
  • Tout doit être au vert.
    RabbitMQ_ManagementSi besoin créer un fichier /etc/rabbitmq/rabbitmq.config en y ajoutant les lignes suivantes :
    Pour une limite minimale de 25Mb d’espace disque :

    [{rabbit, [{disk_free_limit, 25000000}]}].

    Pour une limite de la mémoire à 50% de la capacité du Raspberry (je n’en ai pas eu besoin pour les tests) :

    [{rabbit, [{vm_memory_high_watermark, 0.5}]}].

    Si vous avez d’autres problèmes, vous pouvez trouver plus d’informations sur cette page.

  • Pour la partie client, installer Java sur un autre Raspberry, le même Raspberry, un Mac, Windows, etc. Dans mon cas voici le programme pour envoyer un message au serveur sur le Raspberry, n’oubliez pas de changer l’IP par celle de votre serveur RabbitMQ :
    import com.rabbitmq.client.ConnectionFactory;
    import com.rabbitmq.client.Connection;
    import com.rabbitmq.client.Channel;
    
    public class Send {
    
      private final static String QUEUE_NAME = "hello";
    
      public static void main(String[] argv) throws Exception {
    
        ConnectionFactory factory = new ConnectionFactory();
        //factory.setHost("localhost");
        factory.setHost("192.168.1.25");
        Connection connection = factory.newConnection();
        Channel channel = connection.createChannel();
    
        channel.queueDeclare(QUEUE_NAME, false, false, false, null);
        String message = "Hello World!";
        channel.basicPublish("", QUEUE_NAME, null, message.getBytes());
        System.out.println(" [x] Sent '" + message + "'");
    
        channel.close();
        connection.close();
      }
    }

    Et le programme pour aller écouter les messages sur une file. Encore une fois n’oubliez pas de changer l’IP par celle de votre serveur RabbitMQ :

    import com.rabbitmq.client.ConnectionFactory;
    import com.rabbitmq.client.Connection;
    import com.rabbitmq.client.Channel;
    import com.rabbitmq.client.QueueingConsumer;
    
    public class Recv {
    
        private final static String QUEUE_NAME = "hello";
    
        public static void main(String[] argv) throws Exception {
    
        ConnectionFactory factory = new ConnectionFactory();
        //factory.setHost("localhost");
        factory.setHost("192.168.1.25");
        Connection connection = factory.newConnection();
        Channel channel = connection.createChannel();
    
        channel.queueDeclare(QUEUE_NAME, false, false, false, null);
        System.out.println(" [*] Waiting for messages. To exit press CTRL+C");
    
        QueueingConsumer consumer = new QueueingConsumer(channel);
        channel.basicConsume(QUEUE_NAME, true, consumer);
    
        while (true) {
          QueueingConsumer.Delivery delivery = consumer.nextDelivery();
          String message = new String(delivery.getBody());
          System.out.println(" [x] Received '" + message + "'");
        }
      }
    }

    Pour compiler tout ça, il faut commencer par télécharger les JAR :

    wget http://www.rabbitmq.com/releases/rabbitmq-java-client/v3.1.5/rabbitmq-java-client-bin-3.1.5.tar.gz

    Décompresser l’archive et mettre vos fichiers Java dans le répertoire qui vient d’être créé.
    Ensuite compiler avec la commande

    javac -cp rabbitmq-client.jar Send.java Recv.java

    Et enfin vous voilà prêt à exécuter vos exemples. Pour envoyer :

    java -cp .:commons-io-1.2.jar:commons-cli-1.1.jar:rabbitmq-client.jar Send

    Vous voyez dans la console d’administration le message qui n’a pas été consommé :
    RabbitMQ_Management

    Et maintenant pour consommer le message, vous lancez le programme de réception :

    java -cp .:commons-io-1.2.jar:commons-cli-1.1.jar:rabbitmq-client.jar Recv

    [*] Waiting for messages. To exit press CTRL+C
    [x] Received 'Hello World!'

Voilà votre premier message a été échangé. Il ne vous reste plus qu’à imaginer les possibilités pour interconnecter vos systèmes. Pour moi cette solution est vraiment simple et rapide à mettre en place et permet de se passer facilement de scripts complexes pour du scp ou autre commande pour envoyer des données.

Vous aimez cet article ? Supportez-moi sur Patreon!

Vous aimerez aussi...