Fazendo Javascript OO de forma fácil - Parte 2

Há cerca de 5 anos, fiz um post sobre como escrever Javascript OO de forma fácil utilizando a orientação a objetos da linguagem através de Constructor Functions e Object Literal. Hoje, com o ES6, o esquema de Prototype ainda continua, mas a sintaxe ficou muito mais fácil e intuitiva, valendo a pena dar um revival no tema para explorar um pouquinho mais das novas funcionalidades.

Então, nobre leitor, prepare o seu Babel e vamos escrever algumas classes na nova sintaxe do Javascript.

Açúcares sintáticos

Sim! A sintaxe apresentada no ECMAScript 6 não passa de açúcar sintático!

Na prática, o Javascript continua utilizando a orientação a objetos através de Prototype. Mas isso não diminui em nada o valor desse approach para com a linguagem. Fazer Javascript OOP é a realidade de muitas aplicações (complexas ou não), e caso você queira escrever componentes utilizando React, verá que a dupla ES6 + React é capaz de produzir componentes com código extremamente legível e elegante.

Vamos começar escrevendo nossa classe Pessoa:

class Pessoa {
  constructor({ nome, idade }) {
    this.nome = nome;
    this.idade = idade;
  }

  sayTheName() {
    console.log(this.nome);
  }
}

let pessoa = new Pessoa({ idade: 18, nome: "Guido" });
pessoa.sayTheName(); // Guido
console.log(pessoa.__proto__.sayTheName); // function sayTheName

Agora possuímos a palavra reservada class para a construção de classes. Além disso, temos a inserção do método constructor, que será executado no momento em que a instância for criada.

Não precisamos mais da assinatura Pessoa.prototype.method = function para adicionarmos um método. Agora há uma sintaxe específica, muito mais clara e fácil de lembrar.

"Stay classy San Diego! (sandiegouniontribune.com)"
Stay classy San Diego! (sandiegouniontribune.com)

Note que no momento de instanciar a classe, nada muda em relação à versão atual. O que temos de mais "exótico" é a capacidade de nomearmos parâmetros (como os **kwargs do Python), na definição do construtor.

Esse conceito, apresentado na linha constructor({nome, idade}), é chamado de destructuring.

Para chegarmos a um resultado parecido no ES5, precisaríamos fazer o seguinte:

var Pessoa = function Pessoa(options) {
  var nome = options.nome;
  var idade = options.idade;

  this.nome = nome;
  this.idade = idade;
};

Herança

Lembra da confusão que era fazer heranças no Javascript? Pois bem, ganhamos nessa nova versão da linguagem a palavra reservada extends:

class Atleta extends Pessoa {
  constructor({ nome, idade, esporte = "Basquete" }) {
    super({ nome: nome, idade: idade });

    this.esporte = esporte;
  }
}

let jogador = new Atleta({ idade: 22, nome: "Fulano", esporte: "Futebol" });
console.log(jogador.nome); // Fulano
console.log(jogador.esporte); // Futebol

let jogador2 = new Atleta({ idade: 28, nome: "Beltrano" });
console.log(jogador2.nome); // Beltrano
console.log(jogador2.esporte); // Basquete

E para tornar ainda mais fácil essa prática, também ganhamos a função reservada super, que é responsável por executar o método pai, dada a chamada em um determinado método de uma classe filha.

Para finalizar o nosso exemplo, na linha constructor({nome, idade, esporte='Basquete'}) temos a apresentação do recurso default. Com ele, somos capazes de definir valores padrões caso a passagem de determinado parâmetro seja omitida.

Considerações finais

Se tem algo que chama a atenção com o advento do ECMAScript 6 é a facilidade na construção de classes e objetos, uma coisa que sempre foi muito confusa (mas não menos eficiente) em Javascript.

Bibliotecas como o React tem feito um bom uso desse recurso, proporcionando soluções limpas e legíveis, fáceis de estender e customizar.

O suporte pelos browsers ainda não é dos melhores, se fazendo necessário o uso do Babel para o transpiling de ES6 para ES5. Mesmo assim, nada que impeça o uso de sintaxe ES6 nos seus próximos projetos.

Confira a versão "transpilada" no Babel.

Até a próxima!

Referências