Optimización del rendimiento de una aplicación Node.js
Tags: node, javascript, spanish
Published: 2023-03-26 03:15:08


## Minimize blocking I/O operation
Node.js está diseñado para manejar operaciones de E/S sin bloqueo, lo que significa que puede manejar varias solicitudes simultáneamente sin bloquear el bucle de eventos. Para optimizar el rendimiento, minimice cualquier operación de E/S que bloquee mediante operaciones asincrónicas o dividiendo las tareas grandes en tareas más pequeñas.

```javascript
//Blocking I/O example
const fs = require('fs')

const data = fs.readFileSync('file.txt')

// Non-blocking I/O example
const fs = require('fs')

fs.readFile('file.txt', (err, data) => {
    if(err) throw err
    console.log(data)
})
```

## Use caching
El almacenamiento en caché es una técnica utilizada para almacenar datos a los que se accede con frecuencia en la memoria, de modo que se pueda acceder a ellos rápidamente y sin tener que recuperarlos de un disco o de la red. Utilice el almacenamiento en caché en su aplicación Node.js para reducir la cantidad de consultas a la base de datos y solicitudes de red.

```javascript
const NodeCache = require('node-cache')
const myCache = new NodeCache({ stdTTL: 100, checkperiod: 120 })

function getDataFromDatabase(id) {
  // Database query goes here
}

function getData(id) {
  let data = myCache.get(id)
  if (data == undefined) {
    data = getDataFromDatabase(id)
    myCache.set(id, data)
  }
  return data
}
```

## Use a load balancer
Si su aplicación maneja una gran cantidad de solicitudes, use un balanceador de carga para distribuir la carga de trabajo entre varias instancias de su aplicación. Esto mejorará el rendimiento y reducirá el riesgo de accidentes o tiempo de inactividad.

```javascript
const cluster = require('cluster')
const http = require('http')
const numCPUs = require('os').cpus().length

if (cluster.isMaster) {
  console.log(`Master ${process.pid} is running`)

  // Fork workers.
  for (let i = 0; i < numCPUs; i++) {
    cluster.fork()
  }

  cluster.on('exit', (worker, code, signal) => {
    console.log(`worker ${worker.process.pid} died`)
  })
} else {
  // Workers can share any TCP connection
  // In this case it is an HTTP server
  http.createServer((req, res) => {
    res.writeHead(200)
    res.end('hello world\n')
  }).listen(8000)

  console.log(`Worker ${process.pid} started`)
}

```

## Optimize your database queries
Las consultas a la base de datos pueden ser un cuello de botella importante en el rendimiento. Optimice las consultas de su base de datos minimizando la cantidad de consultas, indexando su base de datos y utilizando características específicas de la base de datos, como vistas y procedimientos almacenados.

```javascript
// Indexing example
db.collection('users').createIndex({ email: 1 })

// Stored procedure example
db.runCommand({
  eval: `function(email) {
    return db.users.findOne({ email: email })
  }`,
  args: ['john@example.com']
})
```

## Use a reverse proxy
Un proxy inverso puede mejorar el rendimiento al almacenar en caché y comprimir activos estáticos como CSS, JavaScript e imágenes. Esto reduce la carga en su servidor y acelera la entrega de estos activos a los clientes.

```javascript
const express = require('express');
const compression = require('compression');
const app = express();

app.use(compression());
app.use(express.static('public'));
```

## Use a task queue
Si su aplicación realiza tareas de ejecución prolongada o que consumen muchos recursos, use una cola de tareas para administrarlas. Esto le permite distribuir la carga de trabajo y reducir el riesgo de bloqueos o tiempo de inactividad.

```javascript
const kue = require('kue')
const queue = kue.createQueue()

function performTask(taskData, done) {
  // Long-running task goes here
  done()
}

queue.process('email', (job, done) => {
  performTask(job.data, done)
})
```

## Use a profiler
Un generador de perfiles es una herramienta que puede ayudarlo a identificar cuellos de botella en el rendimiento de su aplicación. Utilice un generador de perfiles para analizar el rendimiento de su código e identificar las áreas en las que puede realizar mejoras.

```javascript
const profiler = require('v8-profiler')

function runHeavyTask() {
  // Heavy task goes here
}

profiler.startProfiling('Heavy Task')
runHeavyTask()
const profile = profiler.stopProfiling()
console.log(profile)
```