Seleccionar página

jsonAunque normalmente el método JSON.stringify() hace el trabajo que necesitamos, podemos encontrarnos algunos casos donde la transformación de los objetos en cadenas con formato JSON que realiza este método no se ajuste a nuestras necesidades. Podemos desarrollar nuestra propia función para construir la cadena JSON, pero muy probablemente tendremos que rehacer un trabajo bastante complejo que JSON.stringify() hace eficientemente. Podemos hacer algo más interesante: modificar o implementando el método toJSON() en los objetos que queremos personalizar.

Date.prototype.toJSON

Los objetos de tipo Date disponen de un método toJSON() que establece de que forma codificará JSON.stringify() los objetos de este tipo. Si lo necesitamos podemos reescribir este método y personalizar la generación de las cadenas JSON para los objetos tipo Date.

Por ejemplo, si queremos incluir solo la fecha, eliminado la parte correspondiente a la hora, en los mensajes JSON, sólo tenemos que reescribir el método toJSON() de la siguiente forma:

Aviso: modificar un objeto predefinido de Javascript no es muy buena idea, ya que afecta a todas las librerías y programas que utilicemos a partir de este momento. Se incluye aquí sólo para explicar lo que se puede hacer, pero no recomendamos su utilización.

Date.prototype.toJSON = function () {
    return    this.getUTCFullYear() 
            + '-' 
            + ('0' + (this.getUTCMonth() + 1)).substr(-2) 
            + '-' 
            + ('0' + this.getUTCDate()).substr(-2);
}

A partir de este momento, todas los objetos tipo Date serán convertidos por JSON.stringify() sólo con la fecha, por ejemplo:

var biblioteca = {
    autores: [
        {    nombre: 'Miguel de Cervantes',
            nacimiento: new Date(1547, 8, 29),
            lugar: 'Alcalá de Henares, Madrid, España'
        },
        {    nombre: 'William Shakespeare',
            bautizo: new Date(1564, 3, 26),
            lugar: 'Stratford-upon-Avon, Warwickshire, Reino Unido'
        }
    ]
}
console.log(JSON.stringify(biblioteca));

Devuelve:

{"autores":[{"nombre":"Miguel de Cervantes","nacimiento":"1547-09-28","lugar":"Alcalá de Henares, Madrid, España"},{"nombre":"William Shakespeare","bautizo":"1564-04-25","lugar":"Stratford-upon-Avon, Warwickshire, Reino Unido"}]}

en vez del formato por defecto que es:

{"autores":[{"nombre":"Miguel de Cervantes","nacimiento":"1547-09-28T22:00:00.000Z","lugar":"Alcalá de Henares, Madrid, España"},{"nombre":"William Shakespeare","bautizo":"1564-04-25T22:00:00.000Z","lugar":"Stratford-upon-Avon, Warwickshire, Reino Unido"}]}

Añadir el método toJSON a nuestros objetos

De forma similar podemos crear nuestros propios métodos toJSON() para personalizar la forma en la que JSON.stringify() codificará nuestros objetos. Basta con añadir un método con el nombre toJSON para tengamos el nivel de personalización que deseemos.

Por ejemplo, en este caso vamos a crear un objeto que queremos enviar todo como una sola cadena y no con cada una de las propiedades (no es un ejemplo muy práctico, pero nos sirve para mostrar como funciona).

Primero veamos como quedaría con el comportamiento por defecto:

function Persona(nombre, apellido1, apellido2) {
    this.nombre = nombre || null;
    this.apellido1 = apellido1 || null;
    this.apellido2 = apellido2 || null;
}
var cervantes = new Persona('Miguel', 'de Cervantes', 'Saavedra');
console.log(JSON.stringify(cervantes)); // {"nombre":"Miguel","apellido1":"de Cervantes","apellido2":"Saavedra"}

Ahora añadimos el método toJSON() y personalizados la salida:

function Persona(nombre, apellido1, apellido2) {
    this.nombre = nombre || null;
    this.apellido1 = apellido1 || null;
    this.apellido2 = apellido2 || null;
    this.toJSON = function() {
        return '"nombre":"' + this.nombre + ' ' + this.apellido1 + ' ' + this.apellido2 + '"';
    }
}
var cervantes = new Persona('Miguel', 'de Cervantes', 'Saavedra');
console.log(JSON.stringify(cervantes)); // {"nombre":"Miguel de Cervantes Saavedra"}

Conclusión

La implementación personalizada del método toJSON() nos permitirá configurar el funcionamiento JSON.stringify() y de esta forma gestionar la serialización de nuestros objetos de forma precisa y sencilla.

Novedades

Desarrollar con cero dependencias, al menos una vez al año

La gran cantidad de utilidades, funciones, paquetes, módulos y frameworks que tenemos disponibles nos hacen la vida más sencilla y aumentan nuestra productividad, pero con el tiempo nos hacen olvidar lo más básico. De vez en cuando, atrévete a hacer un desarrollo con cero dependencias.

JSDayES – Vídeos

Si te lo has perdido o si quieres volver a ver las charlas y talleres del impresionante JSDayES 2017, aquí tienes todos los vídeos. Ponentes de primer orden, tanto nacionales como internacionales, muestran todos los aspectos de Javascript.

The CITGM Diaries by Myles Borins [video]

Myles Borins de Google, miembro del CTC de Node.js (Node.js Core Technical Committee), nos cuenta (en inglés, por supuesto) como funciona CITGM (Canary In The Gold Mine), una herramienta que permite obtener un módulo de NPM y probarlo usando una versión específica de NodeJS.