El error «invisible» que todo desarrollador TypeScript conoce
\nEstás escribiendo código en TypeScript, todo va bien, pero de repente — una línea roja ondulada debajo de la importación. El compilador te dice algo alarmante: Could not find a declaration file for module 'module-name'. '/path/to/module-name.js' implicitly has an 'any' type. Si alguna vez has trabajado con TypeScript, seguro que te has encontrado con este mensaje. Aparece cuando intentas importar un módulo JavaScript para el que no existe un archivo de declaración (generalmente con la extensión .d.ts).
En Stack Overflow, esta pregunta ha acumulado miles de visitas. Y no es casualidad: el problema parece complejo, aunque en realidad tiene varias soluciones simples y elegantes. En este artículo, analizaremos por qué ocurre el error y compararemos cuatro enfoques principales para solucionarlo. Aprenderás qué método elegir según la situación y podrás olvidarte para siempre de los tipos «invisibles».
\n\n¿Por qué TypeScript exige una declaración?
\nTypeScript es una extensión de JavaScript que añade tipificación estática. Cuando escribes import * as _ from 'lodash', TypeScript necesita saber qué tipos tiene la variable _. Si no hay un archivo .d.ts para el módulo, el compilador no puede verificar los tipos y, por defecto, asigna al módulo el tipo any. Esto rompe la rigurosidad de la tipificación, por lo que TypeScript te advierte. En realidad, no es un error de ejecución, sino una advertencia de compilación, pero en proyectos estrictos (strict: true) puede bloquear la compilación.
Ahora pasemos a las soluciones. Veremos cuatro enfoques, desde el más simple hasta el más flexible.
\n\nSolución 1: Rápida y sucia — declare module
\nLa forma más sencilla es crear un archivo de declaración manualmente. Para ello, añade a tu proyecto un archivo global.d.ts (o types.d.ts) y escribe:
// global.d.ts\ndeclare module 'module-name';\nEsta línea le dice a TypeScript: «El módulo existe, pero su tipo es any». El problema está resuelto, pero pierdes todas las ventajas de la tipificación. Este enfoque es bueno para prototipos rápidos o cuando el módulo se usa en uno o dos lugares. Sin embargo, para proyectos en producción no es la mejor opción.
- \n
- Ventajas: Mínimo código, no requiere instalar paquetes. \n
- Desventajas: El tipo
anyanula el sentido de TypeScript; si el módulo se actualiza, no te enterarás de los cambios en la API. \n
Solución 2: Uso de paquetes @types
\nPara la mayoría de los módulos npm populares, existen paquetes separados con declaraciones. Por ejemplo, para lodash es @types/lodash. Instálalos a través de npm o yarn:
npm install --save-dev @types/lodash\nDespués de esto, TypeScript encontrará automáticamente las declaraciones y el error desaparecerá. Si usas TypeScript 2.0+, él mismo busca la carpeta @types. Esta es la forma estándar y recomendada.
- \n
- Ventajas: Tipificación completa, soporte de la comunidad, actualizaciones automáticas. \n
- Desventajas: No todos los módulos tienen
@types(por ejemplo, bibliotecas poco conocidas). \n
¿Cómo comprobar si existen tipos? Visita la página de npm o ejecuta npm info @types/nombre-del-módulo. Si el paquete no se encuentra, pasa a la siguiente solución.
Solución 3: Activar allowJs y checkJs
\nSi estás escribiendo un proyecto que mezcla TypeScript y JavaScript, puedes permitir que el compilador verifique los archivos JS. Para ello, en tsconfig.json añade:
{\n "compilerOptions": {\n "allowJs": true,\n "checkJs": false\n }\n}\nLa opción allowJs permite importar módulos JS en archivos TS. Con esto, TypeScript intentará