O que podemos esperar das novas versões do JavaScript
Por sete anos consecutivos, o JavaScript foi eleita a linguagem de programação mais popular entre os desenvolvedores, e o que tem facilitado a adoção de novos entusiastas são as novas funcionalidades que vem facilitando cada vez mais sua utilização.
Para você se preparar e ficar atualizado, eu preparei uma lista com as novidades do JavaScript que terá um grande impacto na forma em que escrevemos o código.
Processo de evolução
O padrão JavaScript é chamado ECMAScript e é controlado pelo ECMA International, que possui um comitê chamado Ecma Technical Committee 39 (TC39) responsável pela evolução desse padrão.
Esse processo de evolução é feito através de propostas sugeridas pela própria comunidade, e possui quatro estágios de maturidade:
- Proposta (proposal): o comitê espera dedicar tempo à análise do espaço do problema, soluções e preocupações transversais.
- Rascunho (draft): o comitê espera que o recurso seja desenvolvido e eventualmente incluído no padrão.
- Candidato (candidate): A solução está completa e nenhum trabalho adicional é possível sem a implementação, uso significativo e feedback externo.
- Finalizado (finished): Todas as alterações resultantes da implementação são integradas.
O estágio zero é quando é permitido a entrada na especificação.
Você pode fazer uma proposta preenchendo este formulário, mas é bom conhecer as propostas em andamento para ter mais contexto.
Índice das propostas listadas aqui:
Optional Catch Binding
Atualmente o JavaScript obriga a declaração do erro ao usar o try-catch, mas seu uso é opcional, então a variável pode ser criada desnecessariamente. A proposta é deixar a declaração desta variável opcional, assim como seu uso.
Exemplo do try-catch sem o uso da variável de erro com e sem esta proposta:
A nomenclatura unused
normalmente é usada para deixar explícito que não foi utilizado, o que não seria necessário com esta proposta, mas quando se é utilizado normalmente é nomeado como e
, err
ou error
.
Há um debate se esta proposta não iria incentivar a má prática de ignorar o erro, mas pela minha experiência esse reforço nunca funcionou como o esperado.
Nullish Coalescing
Quando fazemos uma operação booleana no JavaScript como if (myVar) {}
, estamos validando se a variável myVar
é falsy, e algumas vezes queremos validar só se é nullish (null
ou undefined
). Considere este exemplo:
const label = product.price || "Não definido";
Se o valor de product.price
for igual a zero, o JavaScript erá definir o valor de label
como "Não definido"
, pois zero é falsy. Com esta proposta, poderíamos validar se product.price
se é apenas null
ou undefined
assim:
const label = product.price ?? "Não definido";
Optional Chaining
Apesar de estar em estágio 4, essa proposta está sendo bem esperada pela comunidade, pois ele ajuda a tratar o erro mais comum do JavaScript: Uncaught ReferenceError.
Acessar uma propriedade ou método de um objeto deveria ser algo simples como message.body
ou message.send()
, mas se message
não foi definido será lançado o erro Uncaught ReferenceError: message is not defined
. A situação fica ainda pior em uma cadeia de referências, como message.body.user.firstName
por exemplo, cada referência deveria ser valida para evitar o erro. Esta proposta visa simplificar esta validação usando o operador ?.
, exemplo:
Outras formas abordadas:
obj?.prop // acesso opcional à propriedade estática
obj?.[expr] // acesso opcional à propriedade dinâmica
func?.(...args) // acesso opcional à função ou método
Esta proposta pode ser usada em conjunto com a proposta Nullish Coalescing (tópico anterior):
const timeout = response.settings?.timeout ?? 300;
Pipeline Operator
Comumente no JavaScript precisamos encadear algumas funções em sequência da seguinte forma:
const double = n => n * 2;
const increment = n => n + 1;
const const result = Math.round(increment(double(Math.sqrt(81))));
Com esta proposta poderíamos deixar de uma forma mais legível:
result = 81 |> Math.sqrt |> double |> increment |> Math.round;
Repare que a ordem das funções fica invertida, é como se o pipeline |> apontasse o sentido da sequência. Com esta proposta fica mais fácil também organizar esta cadeia em linhas:
result = 81
|> Math.sqrt
|> double
|> increment
|> Math.round;
Do expressions
Para o JavaScript cada chave é um novo escopo, então normalmente utilizamos funções para encapsular um bloco de código do restante do código. Só que a fazer isso você acaba quebrando a leitura linear do código:
function doDumbStuff() {
const x = doOtherStuff();
return x;
}
O que doOtherStuff()
faz mesmo? Não sei, procura aí no código!
Mas com esta proposta podemos deixar tudo junto e ainda sim manter um novo escopo:
function doDumbStuff() {
const x = do {
let tmp = 2;
tmp * tmp + 1
};
return x;
}
A variável tmp
seria acessível somente dentro da expressão do{}
, a propósito, o valor de x retornado é 5.
Essa proposta será um grande avanço para linguagens como JSX que não aceita statement, só expressões:
(
<nav>
<Home
userName={do {
const user = localStorage.getItem("user");
const name = user ? user.name : "";
name.lowerCase();
}}
/>
{
do {
if (loading) {
<Loading />
} else if (loggedIn) {
<LogoutButton />
} else {
<LoginButton />
}
}
}
</nav>
)
Use e participe
O Babel dá suporte para a maioria das propostas em todos os estágios, mas como a própria documentação alerta, use com muita cautela, pois não há nenhuma garantia que a proposta vai ser aceita.
Nas propostas que listei aqui está com o link para o GitHub com suas respectivas especificações, e pelas issues de cada um você pode participar da discussão, nem que seja como leitor.
Todas as propostas estão bem documentadas neste repositório, há várias outras propostas interessantes que vale conhecer também. A MDN possui uma referência abrangente do JavaScript que me ajudou na pesquisa deste artigo, assim como me ajuda no dia a dia do desenvolvimento front-end.