Back to Home

馃摑 - Buffers en Node.JS

5 min read

En el mundo de la internet y lo que mayor importancia se demuestra al navergar, es la informaci贸n. En general, en la internet es muy comun aprovechar y proveer diferentes tipos de informaci贸n, como son im谩genes, videos, entre otros.

A medida que el tiempo pasa, las aplicaciones son m谩s concurrentes, relacionado a toneladas de informaci贸n, y es sumamente complicado ofrecer toda informaci贸n de un abrir y cerrar de ojos.

驴 Pero si lo pensamos de esta forma ? ... Supongamos que creamos un servicio de alto consumo de informaci贸n, como lo puede ser un servicio de streaming o subir/bajar archivos de nuestro servicio privado. Tenemos implicaciones m谩s inquietantes cuando hablamos de ... 驴 Como llevamos toda esa informaci贸n hacia el destino y que no afecte la experiencia ni el consumo alto al momento de hacer un tipo de proceso como presentamos anteriormente ?

Existe algo llamado Buffers en Node.JS, que se define como:

Los objetos Buffer se usan para representar datos binarios en forma de una secuencia de bytes. Muchas API de Node.js, por ejemplo, flujos y operaciones del sistema de archivos, admiten Buffers, ya que las interacciones con el sistema operativo u otros procesos generalmente siempre ocurren en t茅rminos de datos binarios.

Esto quiere decir que cualquier representaci贸n de datos son transformados en secuencias dividas (bytes), con el 煤nico prop贸sito de no enviar una informaci贸n en bruto sino que vaya de forma progresiva, veamos los siguientes ejemplos:

const buffer = Buffer.from('necromancer') // <Buffer 6e 65 63 72 6f 6d 61 6e 63 65 72>

En el anterior ejemplo se transforma un tipo de dato String a Buffer, por lo que se puede resumir que nuestra cadena de texto fue divida en secuencias de bytes.

Pero este tipo de clase, se entiende como:

  • Esta clase es una subclase de TypedArray por lo que son bloques de memoria de tama帽o fijo y no pueden contener ning煤n otro valor.
  • El tama帽o de un Buffer es definido cuando se crea y no puede ser cambiado.

Etiquetas de Codificaci贸n

Existen muchos cuando hablamos en general de codificaci贸n, pero entre tipo de datos como lo son String y Buffers, los que com煤nmente se usan:

  • utf8: Multi-byte encoded Unicode characters.
  • hex: Encode each byte as two hexadecimal characters.
  • base64: Base64 encoding.

Puedes encontrar otras etiquetas aqu铆.

A continuaci贸n veremos unos breves ejemplos de su creacion y comportamiento:

Crear un buffer

En primera instancia la clase Buffer en el entorno de Node.JS es una propieda global por lo que es accesible en cualquier archivo de tu proyecto y sin necesidad de require(). Para iniciar, existen varias formas de crear un buffer.

// Ejemplo basico para crear un Buffer

const buffer1 = Buffer.alloc(10) // <Buffer 00 00 00 00 00 00 00 00 00 00>

En el anterior ejemplo se ha creado un buffer "vacio" con el limite de tama帽o de 10 bytes, siguiendo con este ejemplo, podemos agregar algun espaico en memoria de ese objeto buffer:

// Llenar los espacios varios y representarlos en un byte el caracter mostrado

buffer1.fill('y') // <Buffer 79 79 79 79 79 79 79 79 79 79>

buffer1.toString('utf8') // 'yyyyyyyyyy'

De los 10 bytes reservados en memoria fueron llenados cada byte con el caracter Y (recordemos que por defecto cada conversi贸n por defecto eval煤a la codificaci贸n utf8).

Otra funcionalidad para crear buffers pero m谩s din谩micos al momento de hablar de espacio en reserva, es derivado a esta funci贸n nativa de la clase:

// Crear un nuevo buffer pasando un valor ya sea string or array<bytes>

const buffer2 = Buffer.from('doom') // <Buffer 64 6f 6f 6d>

Esta funcion reservada llamada from permite convertir caracteres o listas directamente a Buffers teniendo en cuenta el tama帽o del dato de origen, en este caso fue 'doom', con un tama帽o de 4 bytes en memoria.

Tambien podemos cambiar el valor de alguna posicion de nuestro buffer:

// Modificar alguna posici贸n de nuestro buffer

buffer2[0] = 0x44

buffer2.toString('utf8') // 'Doom'

En el ejemplo anterior ha sido reemplazado la primera posici贸n de nuestro buffer, que contiene el valor "d" y al ser cambiado este debe ser representado como una codificaci贸n en utf8 a lo que traduce en que "D" es equivalente a 0x44

Propiedades

A continuaci贸n veremos algunas funciones b谩sicas (pero muy 煤tiles) cuando usamos buffers:

buffer.keys()

Este retorna la cantidad de indices asociados al buffer:

// Traer el numero de indices en un `Iterator`

const buffer3 = Buffer.from('lovecraft')

buffer3.keys() // [0, 1, 2, 3, 4, 5, 6, 7, 8]

buffer.lastIndexOf(value[, byteOffset][, encoding])

Esta funci贸n verifica en que posici贸n del arreglo de buffer se encuentra el valor que especificamos por par谩metros:

// Verificar la posicion de un valor determinado

buffer3.lastIndexOf('v') // 2

buffer.concat(Buffer[], [,totalLength])

Basicamente juntar N+1 de buffers para devolver como resultado un nuevo buffer:

// Juntar varios objetos para retornar uno nuevo

const bufferSpace = Buffer.from([0x20]) // Representa un spacio `' '`

const buffer4 = Buffer.concat([buffer2, bufferSpace, buffer3])

buffer4.toString('utf8') // 'Doom lovecraft'

buffer.isEncoding(enconding)

Revisa y valida que tipo de codificaci贸n es referenciado en el objeto buffer:

buffer4.isEncoding('utf8') // true

buffer4.isEnconding('base64') // false

Conclusi贸n

Logramos saber un poco en manera de introducci贸n que son los buffers, como se crean y que tipo de comportamientos trae en si, pero dentro de sus casos m谩s utiles son al momento de integrarlos con Streams, tomando como gran ventaja la facilidad de migrar datos progresivamente, convertir una imagen, o ofrecer videos en tiempo real.

Espero que les haya gustado este breve post, un saludo. 馃榿