TypeScript, favoreça o uso de Type Definitions

O TypeScript é um superset do JavaScript que fornece principalmente tipagem estática opcional, classes e interfaces. Um dos grandes benefícios é permitir que IDEs forneçam um ambiente mais rico para detectar erros comuns à medida que escrevemos nosso código.

Contudo, o navegador não entende TypeScript e para que nosso código seja um código válido, ele precisa ser compilado para JavaScript. São os arquivos resultantes da compilação que são importados pelo navegador. Frameworks como Angular e Ionic utilizam TypeScript como linguagem padrão.

Agora que já temos uma visão geral sobre esta poderosa linguagem, vejamos um simples exemplo que prepara o terreno do tópico abordado neste post:

let nome: string = 'Flávio'; 
nome = 12; // [ts] Type '12' is not assignable to type 'string'.

TypeScript é ainda capaz de inferir o tipo, sem a necessidade de indicá-lo:

let nome = 'Flávio'; // inferiu o tipo string
nome = 12; // [ts] Type '12' is not assignable to type 'string'.

Além disso, a linguagem traz por padrão type definitions para funções e API’s do DOM, permitindo que a IDE detecte erros de sintaxe em nosso código ao usarmos esses recursos, inclusive fornecendo autocomplete:

Mas como proceder para utilizarmos bibliotecas de terceiros que não foram criadas com TypeScript?

Utilizando bibliotecas que não foram criadas com TypeScript

Podemos pegar como exemplo o jQuery, uma das bibliotecas mais populares e que ainda invade o coletivo imaginário dos desenvolvedores. Contudo, se tentarmos usar o global $ em nosso código, teremos um erro de compilação do TypeScript:

let elemento = $('p'); // [ts] Cannot find name '$'

O erro de compilação ocorre porque o TypeScript não entende que $ é uma variável do escopo global e definida pelo jQuery. Faz todo sentido, porque para o TypeScript variáveis não declaradas podem resultar em erros em nosso programa. E agora?

Solução 1: declare var, “calando a boca” do compilador

Uma solução para “calar a boca” do compilador e deixar nosso código compilar é a seguinte:

declare var $: any;
let elemento = $('p'); // deixou o compilador feliz

No entanto, essa solução só deve ser usada em último caso, pois apesar de ter silenciado o compilador, a variável $ foi definida como o tipo any. Como o próprio tipo já indica, o valor da variável pode ser qualquer coisa e o TypeScript não saberá se os métodos e atribuições feitas com ela são válidos. Sendo assim, a solução que vimos tira um dos grandes benefícios da linguagem.

Solução 2, mais indica: baixando type definitions

A boa notícia é que mesmo o jQuery não sendo uma biblioteca criada com TypeScript, é possível criar seu type definition, mais ainda, ele pode ser disponibilizado pelo autor da biblioteca ou por terceiros.

Neste caso, para que possamos tipar a variável $ com o tipo JQuery e nos beneficiarmos do autocomplete e checagem estática do TypeScript podemos baixar seu type definition através do comando:

npm install @types/jquery --save-dev

Como o compilador do TypeScript depende do Node.js para funcionar, temos acesso ao npm, seu gerenciador de pacotes. Por padrão, o compilador TypeScript procura essas definições baixadas dentro da pasta node_modules, local no qual o type definition que acabamos de baixar estará disponível.

Agora, podemos reescrever nosso código assim, sem o declare var:

let elemento = $('select'); // TypeScript infere o tipo JQuery

Ou se for a propriedade de uma classe:

class Controller {

   private elemento: JQuery; // definindo o tipo!

   constructor() {

       this.elemento = $('select');
       /* se fizermos this.elemento, teremos acesso à todas as funções do jQuery, 
         inclusive validação dos tipos de parâmetros
       */
   }
}

Conclusão

Baixar o definition type da sua biblioteca favorita é um caminho mais adequado do que simplesmente silenciar o compilador com declare var. No entanto, pode ser que existam mais de uma definição criada por diferentes autores e cabe ao desenvolvedor baixar aquela mais atualizada, o que requererá uma verificação detalhada de sua parte.

Por fim, há o repositório DefinitelyTyped que centraliza vários typings, quem sabe aquele da sua biblioteca preferida existe lá, ou, caso não exista em nenhum lugar, que tal contribuir com a comunidade sendo o primeiro a criar sua type definition?

Twitter: @flaviohalmeida

2 Comentários

  1. Patrick 01/06/2017 at 13:47 #

    O comando para instalação está incorreto, faltou somente o j do jQuery, npm install @types/jquery –save-dev . De qualquer forma, excelente dica!

  2. Flávio Almeida 01/06/2017 at 14:20 #

    Ops! Atualizei a instrução npm install @types/jquery --save-dev. Estava faltando o “j” do jQuery! 🙂

Deixe uma resposta