Y por fin hemos llegado a la última parte exclusiva de Node, ya lo siguiente que veremos con será, después de MongoDB, como usar las 2 cosas para hacer una API completa.
Aunque sea lo último no tiene porque dejar de ser interesante, ya que usando lo que veremos a continuación podemos aumentar el rendimiento de nuestra aplicación notablemente (eso sí, siempre dependiendo del entorno).
¿Y que es un Cluster? Bueno pues para hacerlo simple un cluster son 2 o más servicios, programas, ordenadores, servidores....que funcionan como uno solo. Bajo este concepto tendríamos varías opciones de configuración: balanceo de carga, alta disponibilidad.... Si queréis saber más siempre podéis mirar en la Wiki
En nuestro caso, NodeJS, nos permite tener varios workers que trabajan por si solos, para hacerlo simple es como si iniciaramos varias veces nuestra aplicación de NodeJS y cada una trabajara por si sola (realmente tenemos un proceso master que gestiona el resto y podemos pasar datos, comunicar eventos o lo que necesitemos entre los workers, entre los workers y el master y viceversa).
Para configurarlo en nuestra aplicación de node tenemos que hacerlo antes de que inicie el server para escuchar las peticiones por lo que vamosa nuestro proyecto de Express y dentro de la carpeta bin en el fichero www hacemos lo siguiente:
Buscamos la linea donde tenemos el comentario Create server
/**
* Create HTTP server.
*/
var server = http.createServer(app);
Y justo encima ponemos lo siguiente:
const cluster = require('cluster')
if (cluster.isMaster){
console.log(`Master is running in process ${process.pid}`)
const numCPUS = require('os').cpus()
numCPUS.map(() => {
cluster.fork()
})
}else {
/**
* Create HTTP server.
*/
var server = http.createServer(app);
Como véis lo que hacemos es requerir el módulo cluster y básicamente es que si es el Master comprobamos cuantas CPUs tenemos y generamos un worker por cada una. El numCpus lo que devuelve es un array donde cada elemento es información de cada CPU, yo simplemente he recorrido el array con el map y por cada elemento le he indicado que genere un worker. Esto se podría hacer de más formas con un for normal o como queráis.
Para ver cuantos workers instancia vamos a añadir un log que indique que ha iniciado un worker, justo debajo de los server.on y cerramos el else
server.listen(port);
server.on('error', onError);
server.on('listening', onListening);
console.log(`Worker ${process.pid} Started`)
} //No nos olvidemos de cerrar el else en este punto
Bien creo que ya estamos listos para ejecutarlo, asi que ya sabéis
npm start
Y si miramos el log
A mi me ha arrancado 4 workers, esto dependerá del número de CPUs de cada equipo.
Hablemos un poco más de como funciona un cluster en Node. En este caso específico se útiliza el método round-robin para repartir la carga entre los workers (lo mejor es que miréis el link que he puesto si queréis saber como funciona).
Tango el master como los workers producen eventos a los que nos podemos suscribir, al mismo estilo que hicimos con el event emitter en su momento, lo más fácil para que veais que eventos tenemos y que podemos hacer con ellos es que miréis la documentación oficial que como veréis viene con mucho código de ejemplo para que lo entendáis mejor.
También es posible que el master mande mensajes a los workers, veamoslo con un pequeño ejemplo. Dentro del if, es decir en el master añadimos
//Nos da una lista con los workers que tenemos
const workersOnline = cluster.workers
workersOnline[2].send("Hi ninjaWorker 2")
workersOnline[4].send("Hi ninjaWorker 4")
Y en el else donde instanciamos los workers
process.on('message',(message)=>{
console.log(`Soy un worker y este es el mensaje ${message}`)
})
Nos suscribimos al evento message y devolvemos un mensaje en consola con el mensaje, fácil ¿verdad?, si ahora ejecutamos veremos como nos aparece el mensaje que hemos pasado a cada worker, y además cada vez que ejecutemos nos aparecerá en distinto momento ya que no sabemos cuando se instancia cada worker
Esto solo es un ejemplo si repasais la documentación veréis que podéis hacer multitud de cosas distintas ;)
Bueno y hasta aquí la parte de Cluster, como habéis visto es relativamente sencillo y ya podéis usarlo tranquilamente en vuestros proyectos con NodeJS.
También (por el momento) aquí finalizamos la parte específica de Node ya lo siguiente que veremos será usandolo con MongoDB para trabajar con esta base de datos y crear una API Rest con un entorno más realista, así que empezaré con una nueva línea dedicada a MongoDB dentro de nada, espero que la parte de Node os haya parecido interesante y suficiente para poder realizar vuestros propios proyectos.
Estad atentos a los siguientes ;) nos vemooosssss un abrazoooorrrrr



