Cómo crear nuestra primera API en Node.js con TypeScript y TypeORM
En este artículo vamos a construir paso a paso una API sencilla usando Node.js, TypeScript y TypeORM con MySQL. Veremos desde la configuración inicial hasta resolver errores comunes que pueden aparecer en el proceso.
Índice:
Crear una API con Node.js, TypeScript y TypeORM es bastante directo si seguimos estos pasos:
- ✅ Configurar proyecto con TypeScript y dependencias.
- ✅ Importar reflect-metadata al inicio.
- ✅ Definir entidades con decoradores y sin errores en propiedades.
- ✅ Configurar y initialize() el DataSource.
- ✅ Crear endpoints usando repositorios.
- ✅ Controlar errores comunes y revisar logs.
1. Configuración inicial del proyecto
Primero, iniciamos un proyecto Node.js con TypeScript y añadimos las dependencias necesarias:
npm init -y
npm install typescript ts-node typeorm reflect-metadata mysql2 express
npm install --save-dev @types/node @types/express
Configuramos nuestro tsconfig.json
con el target es2016
para que el código sea compatible:
{
"compilerOptions": {
"target": "es2016",
"module": "commonjs",
"outDir": "dist",
"strict": true,
"esModuleInterop": true,
"emitDecoratorMetadata": true,
"experimentalDecorators": true
}
}
2. Importar reflect-metadata
Para que TypeORM funcione correctamente con decoradores, debemos importar reflect-metadata
al inicio del punto de entrada (por ejemplo, index.ts
):
import 'reflect-metadata';
3. Definir la entidad Project
Vamos a definir una entidad llamada Project
que representa la tabla proyectos
en MySQL. Importante usar el decorador @Entity('proyectos')
y definir correctamente las columnas:
import { Entity, PrimaryGeneratedColumn, Column } from 'typeorm';
@Entity('proyectos')
export class Project {
@PrimaryGeneratedColumn()
id: number;
@Column({ length: 100 })
nombre: string;
@Column({ type: 'text', nullable: true })
description?: string;
}
Nota: Para columnas de tipotext
, no uses la propiedadlength
, ya que da error. Paravarchar
sí puedes usarlength
.
4. Configurar la conexión con TypeORM
Configuramos el DataSource
con las credenciales de MySQL y registramos las entidades:
import { DataSource } from 'typeorm';
import { Project } from './entities/Project';
export const AppDataSource = new DataSource({
type: 'mysql',
host: 'localhost',
port: 3306,
username: 'tu_usuario',
password: 'tu_password',
database: 'tu_base_de_datos',
entities: [Project],
synchronize: true,
logging: false
});
5. Inicializar la conexión y crear un endpoint básico
Antes de usar repositorios, hay que llamar a initialize()
. Así arrancamos la app y hacemos una consulta:
import 'reflect-metadata';
import express from 'express';
import { AppDataSource } from './data-source';
import { Project } from './entities/Project';
AppDataSource.initialize()
.then(() => {
const app = express();
const projectRepo = AppDataSource.getRepository(Project);
app.get('/projects', async (req, res) => {
try {
const projects = await projectRepo.find();
res.json(projects);
} catch (error) {
res.status(500).json({ message: 'Error interno' });
}
});
app.listen(3000, () => {
console.log('Server running on http://localhost:3000');
});
})
.catch(error => console.error('Error al inicializar DataSource:', error));
6. Manejo de errores comunes
Durante el desarrollo puede aparecer este error:
TypeORMError: Column description of Entity Project does not support length property.
Este error ocurre porque se intenta usar length
en una columna tipo text
, que no lo soporta. La solución es eliminar length
de esas columnas o cambiar el tipo a varchar
.
7. Consejos para despliegue en servidor
- Para que funcione en producción, primero compila con
tsc
y luego ejecuta el código JavaScript generado en la carpetadist
. - Para evitar problemas con dependencias, siempre ejecuta
npm install
en el servidor. - Configura tu repositorio git con una deploy key para hacer pull directamente en servidor sin contraseñas.
- Ejecuta tu app con PM2 para mantenerla activa y poder ver logs fácilmente.
Si quieres, puedes descargar este artículo y usarlo como base para tu API. ¡Mucho éxito con tu desarrollo!