← Volver al Blog

JavaScript y JSON: Guía Completa de JSON.parse() y JSON.stringify()

Domina el trabajo con JSON en JavaScript. Aprende JSON.parse(), JSON.stringify() y mejores prácticas para aplicaciones web modernas.

Big JSON Team12 min de lecturaProgramación
B

Big JSON Team

Technical Writer

Expert in JSON data manipulation, API development, and web technologies. Passionate about creating tools that make developers' lives easier.

12 min lectura

# JavaScript y JSON: Guía Completa de JSON.parse() y JSON.stringify()

JavaScript tiene soporte nativo excelente para JSON. Esta guía completa te enseñará todo sobre trabajar con JSON en JavaScript, desde lo básico hasta técnicas avanzadas.

¿Por Qué JSON y JavaScript van Juntos?

JSON significa JavaScript Object Notation, lo que significa que fue diseñado originalmente para JavaScript. Sin embargo, la sintaxis es ligeramente diferente:

// Objeto JavaScript

const objJS = {

nombre: 'Ana', // Claves sin comillas

edad: 30,

activo: true

};

// JSON válido

const objJSON = {

"nombre": "Ana", // Claves con comillas dobles

"edad": 30,

"activo": true

};

JSON.parse() - De Cadena a Objeto

Convierte una cadena JSON en un objeto JavaScript:

Uso Básico

const jsonString = '{"nombre":"Carlos","edad":35,"ciudad":"Madrid"}';

const persona = JSON.parse(jsonString);

console.log(persona.nombre); // "Carlos"

console.log(persona.edad); // 35

console.log(typeof persona); // "object"

Parsear Arrays

const jsonArray = '[1, 2, 3, 4, 5]';

const numeros = JSON.parse(jsonArray);

console.log(numeros); // [1, 2, 3, 4, 5]

console.log(Array.isArray(numeros)); // true

Parsear Objetos Anidados

const jsonComplejo = {

"usuario": {

"nombre": "María González",

"contacto": {

"email": "maria@ejemplo.com",

"telefono": "+34600123456"

},

"roles": ["admin", "editor"]

}

};

const datos = JSON.parse(jsonComplejo);

console.log(datos.usuario.nombre); // "María González"

console.log(datos.usuario.contacto.email); // "maria@ejemplo.com"

console.log(datos.usuario.roles[0]); // "admin"

Función Reviver

El segundo parámetro de JSON.parse() permite transformar valores:

const jsonConFechas = {

"nombre": "Laura",

"fechaNacimiento": "1990-05-15T00:00:00.000Z",

"ultimaConexion": "2024-01-15T10:30:00.000Z"

};

// Reviver para convertir strings de fecha a objetos Date

const usuario = JSON.parse(jsonConFechas, (clave, valor) => {

// Detectar strings de fecha ISO

if (typeof valor === 'string' && /^d{4}-d{2}-d{2}T/.test(valor)) {

return new Date(valor);

}

return valor;

});

console.log(usuario.fechaNacimiento instanceof Date); // true

console.log(usuario.ultimaConexion.getFullYear()); // 2024

Manejo de Errores

function parsearJSONSeguro(jsonString) {

try {

return {

exito: true,

datos: JSON.parse(jsonString)

};

} catch (error) {

return {

exito: false,

error: error.message

};

}

}

// JSON válido

const resultado1 = parsearJSONSeguro('{"nombre":"Juan"}');

console.log(resultado1.exito); // true

console.log(resultado1.datos); // {nombre: "Juan"}

// JSON inválido

const resultado2 = parsearJSONSeguro('{nombre:"Juan"}');

console.log(resultado2.exito); // false

console.log(resultado2.error); // "Unexpected token n in JSON at position 1"

JSON.stringify() - De Objeto a Cadena

Convierte un objeto JavaScript en una cadena JSON:

Uso Básico

const persona = {

nombre: 'Pedro Sánchez',

edad: 42,

ciudad: 'Barcelona',

activo: true

};

const jsonString = JSON.stringify(persona);

console.log(jsonString);

// {"nombre":"Pedro Sánchez","edad":42,"ciudad":"Barcelona","activo":true}

Pretty Printing

const datos = {

nombre: 'Ana',

habilidades: ['JavaScript', 'React', 'Node.js']

};

// Sin formato

console.log(JSON.stringify(datos));

// {"nombre":"Ana","habilidades":["JavaScript","React","Node.js"]}

// Con indentación de 2 espacios

console.log(JSON.stringify(datos, null, 2));

/

{

"nombre": "Ana",

"habilidades": [

"JavaScript",

"React",

"Node.js"

]

}

/

// Con indentación de 4 espacios

console.log(JSON.stringify(datos, null, 4));

// Con tabs

console.log(JSON.stringify(datos, null, ' '));

Función Replacer

El segundo parámetro permite filtrar o transformar valores:

const usuario = {

nombre: 'Carlos',

password: 'secreto123',

email: 'carlos@ejemplo.com',

edad: 30,

rol: 'admin'

};

// Filtrar propiedades sensibles

const jsonSeguro = JSON.stringify(usuario, (clave, valor) => {

if (clave === 'password') {

return undefined; // Omitir campo

}

return valor;

}, 2);

console.log(jsonSeguro);

/

{

"nombre": "Carlos",

"email": "carlos@ejemplo.com",

"edad": 30,

"rol": "admin"

}

/

Replacer como Array

const producto = {

id: 123,

nombre: 'Portátil',

precio: 999.99,

stock: 50,

categoria: 'Electrónica',

proveedor: 'TechCorp'

};

// Incluir solo propiedades específicas

const jsonLimitado = JSON.stringify(

producto,

['id', 'nombre', 'precio'],

2

);

console.log(jsonLimitado);

/

{

"id": 123,

"nombre": "Portátil",

"precio": 999.99

}

/

Manejo de Tipos Especiales

const datos = {

fecha: new Date(),

funcion: function() { return 'hola'; },

simbolo: Symbol('id'),

indefinido: undefined,

numero: 42,

nulo: null

};

console.log(JSON.stringify(datos, null, 2));

/

{

"fecha": "2024-01-15T10:30:00.000Z",

"numero": 42,

"nulo": null

}

/

// Nota: función, símbolo y undefined son omitidos

Métodos toJSON()

Los objetos pueden definir su propia serialización JSON:

class Usuario {

constructor(nombre, email, password) {

this.nombre = nombre;

this.email = email;

this.password = password;

this.fechaCreacion = new Date();

}

toJSON() {

// Personalizar la serialización

return {

nombre: this.nombre,

email: this.email,

fechaCreacion: this.fechaCreacion.toISOString(),

// password omitido por seguridad

};

}

}

const usuario = new Usuario('Laura', 'laura@ejemplo.com', 'secreto');

console.log(JSON.stringify(usuario, null, 2));

/

{

"nombre": "Laura",

"email": "laura@ejemplo.com",

"fechaCreacion": "2024-01-15T10:30:00.000Z"

}

/

Trabajar con APIs

Fetch con JSON

// GET Request

async function obtenerUsuarios() {

try {

const response = await fetch('https://api.ejemplo.com/usuarios');

if (!response.ok) {

throw new Error(HTTP error! status: ${response.status});

}

const usuarios = await response.json(); // Parsea JSON automáticamente

console.log(usuarios);

} catch (error) {

console.error('Error:', error);

}

}

// POST Request

async function crearUsuario(datosUsuario) {

try {

const response = await fetch('https://api.ejemplo.com/usuarios', {

method: 'POST',

headers: {

'Content-Type': 'application/json',

},

body: JSON.stringify(datosUsuario) // Convertir a JSON

});

const resultado = await response.json();

console.log('Usuario creado:', resultado);

} catch (error) {

console.error('Error:', error);

}

}

// Uso

crearUsuario({

nombre: 'Isabel Ruiz',

email: 'isabel@ejemplo.com',

edad: 28

});

XMLHttpRequest (método antiguo)

function obtenerDatos(url, callback) {

const xhr = new XMLHttpRequest();

xhr.onload = function() {

if (xhr.status === 200) {

const datos = JSON.parse(xhr.responseText);

callback(null, datos);

} else {

callback(new Error('Error en la petición'));

}

};

xhr.onerror = function() {

callback(new Error('Error de red'));

};

xhr.open('GET', url);

xhr.send();

}

// Uso

obtenerDatos('https://api.ejemplo.com/datos', (error, datos) => {

if (error) {

console.error(error);

} else {

console.log(datos);

}

});

LocalStorage y SessionStorage

Guardar Datos

const configuracion = {

tema: 'oscuro',

idioma: 'es',

notificaciones: true

};

// Guardar en localStorage

localStorage.setItem('config', JSON.stringify(configuracion));

// Guardar en sessionStorage

sessionStorage.setItem('tempData', JSON.stringify({usuario: 'Ana'}));

Leer Datos

// Leer de localStorage

const configGuardada = localStorage.getItem('config');

if (configGuardada) {

const config = JSON.parse(configGuardada);

console.log(config.tema); // 'oscuro'

}

// Función helper reutilizable

function obtenerDeStorage(clave, porDefecto = null) {

try {

const item = localStorage.getItem(clave);

return item ? JSON.parse(item) : porDefecto;

} catch (error) {

console.error('Error al parsear desde storage:', error);

return porDefecto;

}

}

// Uso

const config = obtenerDeStorage('config', {tema: 'claro', idioma: 'es'});

Deep Clone

Clonar objetos profundamente usando JSON:

const original = {

nombre: 'Roberto',

contacto: {

email: 'roberto@ejemplo.com',

telefono: '+34600123456'

},

habilidades: ['JavaScript', 'Python']

};

// Deep clone

const clon = JSON.parse(JSON.stringify(original));

// Modificar clon no afecta al original

clon.contacto.email = 'nuevo@ejemplo.com';

clon.habilidades.push('React');

console.log(original.contacto.email); // 'roberto@ejemplo.com'

console.log(original.habilidades); // ['JavaScript', 'Python']

console.log(clon.contacto.email); // 'nuevo@ejemplo.com'

console.log(clon.habilidades); // ['JavaScript', 'Python', 'React']

Limitaciones del método JSON:
const objeto = {

fecha: new Date(),

funcion: () => 'hola',

map: new Map([['a', 1]]),

set: new Set([1, 2, 3])

};

const clon = JSON.parse(JSON.stringify(objeto));

console.log(clon.fecha instanceof Date); // false (es string)

console.log(clon.funcion); // undefined

console.log(clon.map); // {} (objeto vacío)

console.log(clon.set); // {} (objeto vacío)

Validación de JSON

Validador Simple

function esJSONValido(str) {

try {

JSON.parse(str);

return true;

} catch (e) {

return false;

}

}

console.log(esJSONValido('{"nombre":"Ana"}')); // true

console.log(esJSONValido('{nombre:"Ana"}')); // false

console.log(esJSONValido('{"edad":30,}')); // false

Validador con Detalles

function validarJSON(str) {

try {

const resultado = JSON.parse(str);

return {

valido: true,

datos: resultado,

error: null

};

} catch (error) {

return {

valido: false,

datos: null,

error: {

mensaje: error.message,

posicion: error.message.match(/position (d+)/)?.[1]

}

};

}

}

const resultado = validarJSON('{nombre:"Ana"}');

console.log(resultado);

/

{

valido: false,

datos: null,

error: {

mensaje: "Unexpected token n in JSON at position 1",

posicion: "1"

}

}

/

Mejores Prácticas

1. Siempre Maneja Errores

// ✅ Bueno

try {

const datos = JSON.parse(jsonString);

procesarDatos(datos);

} catch (error) {

console.error('Error al parsear JSON:', error);

// Manejar el error apropiadamente

}

// ❌ Malo

const datos = JSON.parse(jsonString); // Puede lanzar error

2. Valida Estructura de Datos

function validarUsuario(obj) {

const camposRequeridos = ['nombre', 'email'];

for (const campo of camposRequeridos) {

if (!(campo in obj)) {

throw new Error(Campo requerido faltante: ${campo});

}

}

if (typeof obj.email !== 'string' || !obj.email.includes('@')) {

throw new Error('Email inválido');

}

return true;

}

try {

const usuario = JSON.parse(jsonString);

validarUsuario(usuario);

// Procesar usuario validado

} catch (error) {

console.error('Validación fallida:', error);

}

3. Sanitiza Datos de Usuario

function sanitizarUsuario(datosUsuario) {

// Filtrar campos permitidos

const camposPermitidos = ['nombre', 'email', 'edad'];

const datosSanitizados = {};

for (const campo of camposPermitidos) {

if (campo in datosUsuario) {

datosSanitizados[campo] = datosUsuario[campo];

}

}

return datosSanitizados;

}

// Uso en API

app.post('/usuarios', (req, res) => {

try {

const datosUsuario = sanitizarUsuario(req.body);

// Guardar datosUsuario en base de datos

} catch (error) {

res.status(400).json({error: error.message});

}

});

4. Usa Pretty Print en Desarrollo

const NODE_ENV = process.env.NODE_ENV || 'development';

function serializarJSON(datos) {

if (NODE_ENV === 'development') {

return JSON.stringify(datos, null, 2); // Pretty print

} else {

return JSON.stringify(datos); // Minificado

}

}

Rendimiento

Comparación de Métodos de Clonación

const objeto = { / datos grandes / };

// JSON.parse/stringify - Más lento pero simple

console.time('JSON');

const clon1 = JSON.parse(JSON.stringify(objeto));

console.timeEnd('JSON'); // ~5ms para objetos grandes

// structuredClone - Más rápido y maneja más tipos (moderno)

console.time('structuredClone');

const clon2 = structuredClone(objeto);

console.timeEnd('structuredClone'); // ~2ms

Optimizar Stringify

// Para objetos muy grandes, considera usar streaming

const { Transform } = require('stream');

class JSONStringifyStream extends Transform {

constructor() {

super({ objectMode: true });

this.first = true;

}

_transform(chunk, encoding, callback) {

if (this.first) {

this.push('[');

this.first = false;

} else {

this.push(',');

}

this.push(JSON.stringify(chunk));

callback();

}

_flush(callback) {

this.push(']');

callback();

}

}

Conclusión

JavaScript tiene soporte excelente y nativo para JSON. Dominar JSON.parse() y JSON.stringify() es esencial para cualquier desarrollador web moderno.

Puntos Clave

  • Usa JSON.parse() para convertir strings JSON a objetos
  • Usa JSON.stringify() para convertir objetos a JSON
  • Siempre maneja errores con try/catch
  • Usa el parámetro de espaciado para pretty printing
  • Valida y sanitiza datos de usuario
  • Aprovecha toJSON() para serialización personalizada

¡Domina JSON en JavaScript y lleva tus aplicaciones web al siguiente nivel!

Share:

Artículos Relacionados

Read in English