Sistema de monitoreo de datos mediante un navegador en tiempo real con Websockets, ZMQ y PHP en AWS

Lo que se pretende es implementar un Tablero de Monitoreo de Datos en Tiempo Real mediante un navegador Web. Supongamos por ejemplo que una empresa necesita estar viendo informacion en tiempo real de sus ventas , sus pedidos con envios pendientes o cualquier informacion que se actualice con frecuencia y se requiera que se actualice el tablero en el momento que exista algun cambio en la informacion. El objetivo sera que estos tableros o “dashboards” se actualicen en el momento que la informacion cambie.

Para la implementacion del tablero usaremos los siguientes Cloud Services de AWS:

  • Base de datos con la informacion que se pretende mostrar. En nuestro caso usaremos MariaDb con el servicio de RDS.
  • Servidor WEB apache montado en una Instancia EC2 con ami Linux II y PHP 7.4.
  • Servicio de Mensajeria ZMQ montado en la misma Instancia EC2 que el Servidor WEB.
  • Librería libsodium para usar encriptación en los mensajes

Configuracion de Instancia EC2

Nuestra instancia EC2 esta basada en una imagen Amazon Linux 2 AMI (HVM), SSD Volume Type , que a su vez esta basada en CentOS por lo que los comandos de instalacion corresponden a esta distribucion de Linux.

Debido a que se van a descargar y compilar las librerias libsodium y zeromq, debemos de asegurar de tener instalado el compilador gcc. Si no esta instalado podemos instalarlo utilizando el administrador de paquetes yum.

sudo yum install -y gcc gcc-c++

En primer lugar debemos descargar la libreria de encriptacion libsodium y la instalamos usando los comandos ./configure && make && sudo make install :

curl https://download.libsodium.org/libsodium/releases/LATEST.tar.gz | tar -xz
cd libsodium-stable
./configure && make && sudo make install
cd ../ 
sudo rm -rf libsodium-stable

Despues debemos descargar la libreria de mensajes ZMQ. Buscar la ultima version en https://github.com/zeromq/libzmq/releases , actualmente es la version 4.3.4 y porcedemos tambien a instalarla:

wget https://github.com/zeromq/libzmq/releases/download/v4.3.4/zeromq-4.3.4.tar.gz 
tar xfz zeromq-4.3.4.tar.gz && rm zeromq-4.3.4.tar.gz
cd zeromq-4.3.4
export PKG_CONFIG_PATH=$PKG_CONFIG_PATH:/usr/local/lib/pkgconfig 
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/lib
./configure && make && sudo make install
cd ../ 
sudo rm -rf zeromq-4.3.4.tar.gz 

A continuacion instalamos la extension ZMQ de PHP que nos permite comunicarnos con el servidor de mensajes. En este punto ya debemos de tener instalado nuestro servidor Apache , asi como PHP.

git clone git://github.com/mkoppanen/php-zmq.git
cd php-zmq
phpize
./configure && make && sudo make install
cd ../
sudo rm -rf php-zmq

Posteriormente se debe de agregar la extension zmq.so al final del archivo de configuracion de PHP, normalmente ubicado en /etc/php.ini y agregamos la siguiente linea al final del archivo.

extension=zmq.so

o si lo hacemos mediante script:

sudo chown ec2-user /etc/php.ini
echo extension=zmq.so >> /etc/php.ini
sudo chown root /etc/php.ini

Después tenemos que instalar una librería para implementar un Websocket con PHP. Para esto utilizaremos Ratchet , la cual se instala utilizando composer, agregándola a los paquetes requeridos usando el comando:

php ~/composer.phar require cboden/ratchet

Lo anterior, asumiendo que composer se encuentra en el directorio home (~).

O bien si no se tiene instalado composer, el script completo para instalarlo junto con la libreria Ratchet es:

cd ~
mkdir composer
cd composer
sudo curl -sS https://getcomposer.org/installer | sudo php
php ~/composer/composer.phar require cboden/ratchet
php ~/composer/composer.phar upgrade

Ratchet es una libreria de Websockets que esta construida encima de otra libreria de Sockets llamada React.

React maneja las conexiones y la Entrada/Salida para Ratchet. Además de React, que viene con Ratchet, necesitamos otra biblioteca que forma parte de la suite React: React/ZMQ. lo podemos agregar a composer con el comando:

php ~/composer.phar require react/zmq

Esta biblioteca vincula los sockets de ZeroMQ al núcleo de Reactor, lo que nos permitirá manejar tanto los sockets de WebSockets como los de ZeroMQ. Para instalar, su archivo composer.json debería verse así

{
     "autoload": {
         "psr-4": {
             "MyApp\": "src"
         }
     },
     "require": {
         "cboden/ratchet": "^0.4.3",
         "react/zmq": "0.2.|0.3."
     }
 }

Scripts utilizados

Supongamos que nueva información acaba de ser generada y queremos publicarla en nuestro tablero, lo que vamos a hacer es mediante un script de PHP mandar un mensaje con esta informacion a la misma instancia donde esta corriendo el script. Es decir, vamos a mandar un mensaje a localhost , en nuestro caso por el puerto 5555 con la informacion deseada. El codigo quedaria de la siguiente manera:

$context = new ZMQContext();
$socket = $context->getSocket(ZMQ::SOCKET_PUSH, 'my pusher');
$socket->connect("tcp://localhost:5555");

$entryData = array(
        'category' => "dashboardVentas"
         , 'when'     => "Fecha :".$fecha_actual
        , 'title'    => $newArray
        );

$entryData = json_encode($entryData);
$socket->send($entryData);  // Se publican los datos JSON via ZMQ

LIgas Adicionales

Libreria ZMQ

http://wiki.zeromq.org/bindings:php

http://wiki.zeromq.org/build:encryption

LIBRERIA LIBSODIUM

https://libsodium.gitbook.io/doc/

Libreria PHP ZMQ BINDING

https://www.php.net/zmq

LIBRERIA REACT PHP

https://reactphp.org

LIBRERIRA Ratchet PARA WebSockets CON PHP

http://socketo.me/

Servidor APACHE modulo de Websockets

https://httpd.apache.org/docs/2.4/mod/mod_proxy_wstunnel.html

LIBRERIA AUTOBAHN EN JAVASCRIPT PARA WEBSOCKETS

https://crossbar.io/autobahn/

COMPOSER y PACKAGIST

https://phpenthusiast.com/blog/how-to-use-packagist-and-composer

AMI LINUX 2

https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/amazon-linux-ami-basics.html