logoImagina
iconCurso
Te recomendamos nuestro curso de JavaScript
Descubre el curso de JavaScript
Ir al curso
Descubre la formación a tu medida
Rellena el formulario para obtener más información sobre los cursos.
Tamaño de la empresa *
Términos y condiciones *

Novedades en JavaScript: desde la versión ES5 hasta la ES10

iconImage
Publicado 2024-03-07
Actualizado el 2024-03-21

¿Qué es JavaScript?

JavaScript es un lenguaje ligero e interpretado, dialecto del estándar ECMAScript, orientado a objetos con funciones de primera clase. Se utiliza principalmente en su forma del lado del cliente, implementando como parte de un navegador web permitiendo mejoras en la interfaz de usuario y páginas web dinámicas.

Actualmente el estándar ECMAScript, se encuentra en la versión ECMAScript 2019. A partir de las versiones ES5 y ES6 agregaron cambios significativos al lenguaje. Veremos algunos de ellos en este tutorial hasta la actual versión ES10.

Puedes aprender mucho más sobre JavaScript en nuestro curso de Javascript, así como en nuestro curso de Javascript avanzado.

Versión ES5 y ES6

Función Arrow

Para crear un código más limpio y claro. Veamos un ejemplo:

1// ES5 2// Imaginemos una variable data que incluye un array de objetos 3var data = [{...}, {...}, {...}, ...]; 4data.forEach(function(elem){ 5 // Tratamos el elemento 6 console.log(elem) 7});

En la versión ES6 se vería de la siguiente manera el código anterior:

1//ES6 2var data = [{...}, {...}, {...}, ...]; 3data.forEach(elem => { 4 console.log(elem); 5});

Clases

Ahora JavaScript tendrá clases con todo lo que conlleva, como por ejemplo, la herencia. Son muy parecidas a las funciones constructoras de objetos que realizábamos en el estándar anterior.

1class matematicas extends Libro { 2 constructor(tematica, paginas) { 3 super(tematica, paginas); 4 this.capitulos = []; 5 this.precio = ""; 6 // ... 7 } 8 metodo() { 9 // ... 10 } 11}

This

La variable this anteriormente teníamos que cachearla en otra variable ya que solo hace referencia al contexto en el que nos encontremos. Por ejemplo, en el siguiente código si no hacemos var that = this dentro de la función  document.addEventListener, this haría referencia a la función que pasamos por Callback y no podríamos llamar a foo().

1//ES3 2var obj = { 3 foo : function() {...}, 4 bar : function() { 5 var that = this; 6 document.addEventListener("click", function(e) { 7 that.foo(); 8 }); 9 } 10}

La función Arrow en la versión ES6 es más sencilla y visual:

1//ES6 2var obj = { 3 foo : function() {...}, 4 bar : function() { 5 document.addEventListener("click", (e) => this.foo()); 6 } 7}

Let y Const

Ahora podemos declarar variables con let en lugar de var si no queremos que sean accesibles más allá de un ámbito. Por ejemplo:

1//ES6 2(function() { 3 if(true) { 4 let x = "hola mundo"; 5 } 6 console.log(x); 7 //Da error, porque "x" ha sido definida dentro del "if" 8})();

Template Strings

Con ES6 podemos interpolar Strings de una forma más sencilla que como estábamos haciendo hasta ahora. Por ejemplo:

1//ES6 2let nombre1 = "JavaScript"; 3let nombre2 = "awesome"; 4console.log(Sólo quiero decir que ${nombre1} is ${nombre2’);

Destructuring

Tenemos nuevas formas de asignar valores a Arrays y a Objetos. Veamos unos ejemplos:

1var [a, b] = ["Buenos", "días"]; 2console.log(a); // "Buenos" 3console.log(b); // "días" 4 5var obj = { nombre: "Pepito", apellido: "Perez" }; 6var { nombre, apellido } = obj; 7console.log(nombre); // "Pepito"

Valores por defecto

Otra de sus novedades es asignar valores por defecto a sus variables, que se pasan por parámetros en las funciones. Antes teníamos que comprobar si la variable ya tenía un valor. Ahora con ES6 se la podremos asignar según creemos la función:

1//ES6 2function(valor = "foo") {...};

Módulos

A esto lo llamo un browserify nativo. Ahora JavaScript se empieza a parecer a lenguajes como Python o Ruby. Llamamos a las funciones desde los propios Scripts, sin tener que importarlos en el HTML, si usamos JavaScript en el navegador.

1//File: lib/person.js 2module "person" { 3 export function hello(nombre) { 4 return nombre; 5 } 6}

También se pueden exportar de esta manera:

1export function hello(nombre) {...};

Y desde otro fichero:

1//File: app.js 2import { hello } from "person"; 3var app = { 4 foo: function() { 5 hello("Pepe"); 6 } 7} 8export app;
Descubre la formación a tu medida
Rellena el formulario para obtener más información sobre los cursos.
Tamaño de la empresa *
Términos y condiciones *

Versión ES7

Array.prototype.includes(var)

Comprueba si un array contiene el valor pasado por parámetro. Básicamente, funciona igual que la función String.prototype.includes(var) para cadenas de texto (tratada en este post), pero para arrays. Con esta función ya no tendremos que utilizar el indexOf() para comprobar si un determinado valor está en un array.

1const array = [1, ‘string’, true, 33]; 2console.log(array.includes(‘string’)); //true 3console.log(array.includes(2)); //false

Operador de exponenciación ()

Este operador nos permite calcular la potencia de número. Le indicamos el número base y el exponente y nos hará el cálculo elevando el número base al exponente. Anteriormente, esto mismo, se podía hacer con la función Math.pow($base, $exponente), pero ahora no es necesario utilizarla gracias al operador .

1const base = 3; 2const exponente = 10; 3console.log(base ** exponente); 4console.log(Math.pow(base, exponente));

Ambos ejemplos de código anteriores se verían de la siguiente forma:

Salida de código Javascript en la consola, operador de exponenciación

Versión ES8

Funciones asíncronas

La novedad más importante de esta versión son las funciones asíncronas, que devuelven promesas y se tienen que declarar con la keyword asinc delante de la declaración de la función. Solamente dentro de estas funciones podemos usar await  e indicará que se detenga hasta que no esté resuelta la promesa de la función y cuando lo esté continuará con la ejecución normal. Utilizando async/await, se simplificará todo mucho mucho más pudiendo ejecutar código asíncrono como si fuese síncrono.

1const base = 3; 2const exponente = 10; 3console.log(base ** exponente); 4console.log(Math.pow(base, exponente));
Salida de código Javascript en la consola, función asíncrona

Vamos a usar el paquete node-fetch, el cual nos permitirá usar la función fetch en Node.js, que es el entorno donde estamos ejecutando el código en Repl.it. Si lo estas ejecutando en tu local en un navegador directamente, sin Node.js, no te hará falta instalar el paquete, ya que la función fetch es una función nativa de JS.

Object.entries(obj)

Es un método añadido a Object que recibe como parámetro un objeto y lo que nos devuelve es un array que contiene tantos arrays como propiedades tenga el objeto con la clave y el valor de las propiedades.

1const obj = { test: 1, foo: true, string: 'nombre'} 2console.log(Object.entries(obj));
Salida de código Javascript en la consola, object.entries()

Object.values(obj)

Este es otro método añadido a Object. Como el anterior, también recibe un objeto como parámetro y lo que nos devuelve son los valores de las propiedades del objeto pasado. Ejemplo:

1const obj = { test: 1, foo: true, string: 'nombre'} 2console.log(Object.values(obj));
Salida de código Javascript en la consola, object.values()

string.padStart(num, string)

padStart nos permite rellenar una cadena de texto desde el inicio de ésta hasta la longitud que hayamos indicado con los caracteres que queramos. Ejemplo:

1console.log("string".padStart(10)); 2console.log("string".padStart(10, "abc"));
Salida de código Javascript en la consola, string.padStart()

string.padEnd(num, string)

padEnd funciona igual que el anterior, pero en vez de rellenarlos por el principio de la cadena, lo rellena por el final de la cadena (último carácter).

1console.log("string".padEnd(10)); 2// "string " 3console.log("string".padEnd(10, "abc")); 4// stringabca
Salida de código Javascript en la consola, string.padEnd()

object.getOwnPropertyDescriptors()

El método Object.getOwnPropertyDescriptors() devuelve la descripción de las propiedades del objeto pasado por parámetro.

1const obj = { 2 test: 1, 3 foo: true, 4 string: 'nombre' 5} 6console.log(Object.getOwnPropertyDescriptors(obj))
Salida de código Javascript en la consola, object.getOwnPropertyDescriptors()

Versión ES9

rest/spread properties

Es similar a lo que se puede hacer con los parámetros de las funciones y los arrays desde ES6 pero con propiedades de objetos.

1const obj = { 2 name: 'John', 3 age: '32', 4 city: 'New York', 5 address: 'Address...' 6} 7// Rest 8const {name, age, ...rest} = obj; 9console.log(name, age, rest); // John 32 { city: 'New York', address: 'Address...' } 10// Spread 11const newObj = {name, job: 'Developer' , ...rest}; 12console.log(newObj); 13const copyObj = { ...newObj }; 14console.log(copyObj, newObj);
Salida de código Javascript en la consola,, rest/spread

promise: finally()

Es una función introducida en las promesas que se ejecutará siempre al finalizar la promesa, es decir, se ejecutará tanto si la promesa se ejecuta con éxito o es rechazada. Si lo has utilizado alguna vez y lo recuerdas, vendría a ser como él always del Ajax de jQuery.

Por tanto, ahora tendríamos tres posibles funciones callback para las promesas que serían .then(), .catch() y .finally().

1const fetch = require('node-fetch'); 2 3// Promise: finally() 4fetch('https://jsonplaceholder.typicode.com/todos/1') 5 .then(response => response.json()) 6 .then(json => console.log(json)) 7 .catch(error => console.log(error)) 8 .finally(() => console.log('Esto se mostrará siempre!'));
Salida de código Javascript en la consola, función finally()

Iteración asíncrona

Se ha introducido el await para bucles for, lo cual permite iterar sobre iterables asíncronos(promesas). Se tiene que utilizar dentro de funciones asíncronas como cualquier await. El bucle quedaría así:

1for await (const variable of iterable) { 2... 3}

Ejemplo:

1var asyncIterable = { 2 [Symbol.asyncIterator]() { 3 return { 4 i: 0, 5 next() { 6 if (this.i < 3) { 7 return Promise.resolve({ value: this.i++, done: false }); 8 } 9 10 return Promise.resolve({ done: true }); 11 } 12 }; 13 } 14}; 15 16(async function() { 17 for await (let num of asyncIterable) { 18 console.log(num); 19 } 20})();
Salida de código Javascript en la consola, función asíncrona

Cambios en RegExp

Se puede dar un nombre a los grupos de captura para referirse a ciertas partes de una cadena y que de esta manera que más claro. Por ejemplo:

1let {groups: {one, two}} = /^(?<one>.*):(?<two>.*)$/u.exec('foo:bar'); 2console.log(`one: ${one}, two: ${two}`);
Salida de código Javascript en la consola, RegExp

Mira detrás de las afirmaciones

Hay dos versiones para mirar detrás de las afirmaciones: positiva y negativa.

Positivo(?<=...)

Salida de código Javascript en la consola, postivo

Negativo(?<!...)

Salida de código Javascript en la consola, negativo

RegExp Unicode Property Escapes

Ahora podemos buscar caracteres mencionando su propiedad Unicode dentro /p{}

Salida de código Javascript en la consola, RegExp Unicode Property Escapes
[x, x * 2]);

//[Array(2), Array(2), Array(2)] //0: (2)[1, 2] //1: (2)[2, 4] //2: (2)[3, 6]

arr.flatMap(v => [v, v * 2]) //[1, 2, 2, 4, 3, 6, 4, 8, 5, 10] ```

Object.fromEntries()

Método transforma una lista de pares clave-valor en un objeto.

1var obj = { 2 key1: ‘value 1, 3 key2: ‘value 2, 4 key3: ‘value 35} 6 7var entries = Object.entries(obj) 8 9//(3) [Array(2), Array(2), Array(2)] 10//0: (2) [“key1”, “value 1”] 11//1: (2) [“key2”, “value 2”] 12//2: (2) [“key3”, “value 3”] 13 14var fromEntries = Object.fromEntries(entries) 15//{key1: “value 1”, key2: “value 2”, key3: “value 3”}

String.trimStart() & String.trimEnd()

El trimStart() es un método que elimina los espacios en blanco desde el principio de una cadena.

El trimEnd() es un método que elimina los espacios en blanco del final de una cadena.

Puedes pensar por qué otro método nuevo ya tiene dos métodos trimRight() y trimLeft() será un alias de los métodos nuevos.

Enlace de captura opcional

Permitir que los desarrolladores utilicen try/ catch sin crear un enlace no utilizado. Eres libre de seguir adelante haciendo uso del bloque catch sin un parámetro.

1try{ 2 throw new Error(“some error”); 3} catch { 4 console.log(“no params for catch”); 5}

Function.toString()

Este método devuelve una cadena que representa el código fuente de la función. Más espacios blancos, las nuevas líneas y los comentarios se eliminarán cuando lo haga, se conservarán con el código fuente original.

1function hello(text){ 2 var name = text; 3 //print name 4 console.log(‘Hello ${name}) 5} 6 7console.log(hello.toString()) 8// function hello(text){ 9// var name = text; 10// print name 11//console.log(‘Hello${name}’) 12//}

Symbol.description

Propiedad de solo lectura es una cadena que devuelve la descripción opcional de los Symbol objetos.

1var mySymbol = ‘My Symbol’ 2var symObj = Symbol(mySymbol) 3 4console.log(symObj) //Symbol(My Symbol) 5console.log(String(symObj) === ‘Symbol(${mySymbol})) //true 6console.log(symObj.description) //My Symbol

JSON.Stringify()

Este método convierte un objeto o valor de JavaScript en una cadena de texto JSON, opcionalmente reemplaza valores si se indica una función de reemplazo, o si se especifican las propiedades mediante un array de reemplazo.

1console.log(JSON.stringify({ x: 5, y: 6 })); 2// expected output: "{"x":5,"y":6}"  3console.log(JSON.stringify([new Number(3), new String('false'), new Boolean(false)])); 4// expected output: "[3,"false",false]" 5console.log(JSON.stringify({ x: [10, undefined, function(){}, Symbol('')] })); 6// expected output: "{"x":[10,null,null,null]}" 7console.log(JSON.stringify(new Date(2006, 0, 2, 15, 4, 5))); 8// expected output: ""2006-01-02T15:04:05.000Z""

Aprende JavaScript desde cero

Tras este repaso por todas las versiones de JavaScript, te recomendamos consultar la página de nuestro curso de Javascript, así como de nuestro curso de Javascript avanzado para aplicar todos estos conceptos y convertirte en un experto.

Descubre la formación a tu medida
Rellena el formulario para obtener más información sobre los cursos.
Tamaño de la empresa *
Términos y condiciones *
iconClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClienticonClient