ProgramaciónDesarrollador Backend

¿Qué es la tipificación Generics en TypeScript y cómo utilizarla para escribir funciones y clases universales? ¿Cuáles son los posibles escollos?

Supere entrevistas con el asistente de IA Hintsage

Respuesta.

Generics (tipos genéricos) permiten escribir código universal que funciona con diferentes tipos, manteniendo la estricta seguridad de tipos.

Sintaxis de uso:

function identity<T>(value: T): T { return value; } const x = identity<string>('test'); // T = string

Dónde se aplican:

  • Funciones universales de colecciones (map, filter, etc.)
  • Clases (por ejemplo, Repository<Entity>)
  • Interfaces (por ejemplo, respuesta de API de tipo genérico)

Ejemplo con restricción de tipo:

function getFirst<T extends { length: number }>(arr: T): T { return arr[0]; }

Pregunta capciosa.

Pregunta: ¿Es obligatorio especificar un tipo concreto al llamar a una función con un parámetro Genérico?

Respuesta:

No es obligatorio. TypeScript infiere los tipos a partir de los valores pasados, si es posible. Pero a veces es conveniente especificarlo explícitamente, por ejemplo, si el tipo no se puede inferir o hay varias opciones.

function identity<T>(value: T): T { return value; } identity(5); // T = number (auto) identity<string>('s'); // T = string (explícito)

Ejemplos de errores reales debido al desconocimiento de los matices del tema.


Historia

En un proyecto de e-commerce, se escribió un repositorio genérico para diferentes entidades, pero se olvidaron de la restricción de tipo. Como resultado, cualquier objeto podía ser pasado al genérico, y una vez se guardó una entidad con campos incompatibles. Los tipos no protegieron contra el error.


Historia

Se pasó una matriz a una función plantilla, esperando obtener una matriz con un tipo de elementos. Pero la función devolvió any[], ya que el genérico no fue especificado explícitamente y TypeScript no pudo inferir el tipo. El error solo se notó en producción.


Historia

Un desarrollador principiante creó una clase genérica sin restricción de tipo, utilizó un campo que no existía en todos los tipos. El compilador no dio errores, pero al acceder a una propiedad inexistente, toda la funcionalidad se rompía.