Subir y procesar archivos CSV mediante una REST API
Subir y procesar archivos CSV mediante una REST API es un requisito común en las aplicaciones web modernas. En esta guía, te mostraremos cómo crear una REST API segura con Node.js y Express que gestione las subidas de archivos CSV, analice el contenido de los archivos con csv-parser y almacene los datos para recuperarlos más tarde. Usamos Multer para gestionar las subidas de archivos con comprobaciones de seguridad robustas.
Requisitos previos
Antes de comenzar, asegúrate de tener instalado lo siguiente:
- Node.js (versión 22.x LTS o superior)
- npm (Node Package Manager)
Configurar un servidor Node.js y Express
-
Crea un nuevo directorio para tu proyecto e inicialízalo:
mkdir csv-upload-api cd csv-upload-api npm init -y -
Instala las dependencias necesarias con números de versión explícitos para garantizar la compatibilidad:
npm install express@4.22.2 multer@2.3.0 csv-parser@3.2.0 -
Crea un archivo llamado
server.jsy agrega el siguiente código para configurar un servidor Express básico:const express = require('express') const app = express() const port = process.env.PORT || 3000 app.use(express.json()) app.listen(port, () => { console.log(`Server is running on port ${port}`) })
Implementar el endpoint de subida de archivos
Agrega el siguiente código a server.js antes de app.listen. Configura Multer con un límite de tamaño
de archivo y un filtro de nombre de archivo/MIME para CSV. Ambas etiquetas provienen del cliente,
por lo que este filtro solo es una comprobación inicial; el análisis y la validación de filas
específica de la aplicación siguen siendo necesarios.
const multer = require('multer')
const path = require('path')
const fs = require('fs')
const csv = require('csv-parser')
const { pipeline } = require('node:stream/promises')
const upload = multer({
dest: 'uploads/',
limits: { fileSize: 1024 * 1024 * 5, files: 1, fields: 0 }, // 5 MiB limit
fileFilter: (req, file, cb) => {
if (file.mimetype !== 'text/csv' || path.extname(file.originalname).toLowerCase() !== '.csv') {
return cb(Object.assign(new Error('Unsupported file type'), { code: 'UNSUPPORTED_FILE_TYPE' }))
}
cb(null, true)
},
})
Analizar y almacenar los datos CSV
En esta sección, construimos el endpoint /upload para analizar el archivo CSV y almacenar su contenido.
Una variable global guarda los datos analizados y se proporciona un endpoint GET para recuperarlos.
Esta es una demostración acotada y de un solo proceso: una subida exitosa reemplaza el conjunto de
datos anterior y un reinicio lo borra. Las aplicaciones en producción necesitan autorización por
usuario y almacenamiento duradero.
let storedData = []
async function parseUpload(filePath) {
try {
const results = []
await pipeline(
fs.createReadStream(filePath),
csv({ strict: true, maxRowBytes: 1024 * 1024 }),
async (rows) => {
for await (const row of rows) {
results.push(row)
}
},
)
return results
} finally {
await fs.promises.unlink(filePath)
}
}
app.post('/upload', upload.single('file'), async (req, res, next) => {
if (!req.file) {
return res.status(400).send('No file uploaded.')
}
try {
const results = await parseUpload(req.file.path)
storedData = results
res.json({ recordsStored: results.length })
} catch (error) {
next(error)
}
})
app.get('/data', (req, res) => {
res.json(storedData)
})
// Error middleware must follow every route whose errors it handles.
app.use((error, req, res, next) => {
if (res.headersSent) return next(error)
if (error.code === 'UNSUPPORTED_FILE_TYPE') {
return res.status(415).json({ error: 'Only CSV files are accepted.' })
}
if (error instanceof multer.MulterError) {
const status = error.code === 'LIMIT_FILE_SIZE' ? 413 : 400
return res.status(status).json({ error: 'Upload rejected.' })
}
console.error('CSV processing failed')
res.status(500).json({ error: 'Unable to process the upload.' })
})
pipeline propaga los errores de lectura y del analizador a un único manejador de errores. La subida
temporal se elimina tanto en caso de éxito como de error, y un análisis fallido nunca reemplaza el
conjunto de datos anterior. Mantén Multer actualizado con parches; la versión 2.3.0 incluye las
correcciones de seguridad de agosto de 2026.
Probar la API
Puedes probar la API con los siguientes comandos cURL o con Postman.
Prueba una subida exitosa:
curl --fail-with-body -F "file=@data.csv;type=text/csv" http://localhost:3000/upload
Prueba con un tipo de archivo no válido:
curl -X POST -F "file=@image.jpg" http://localhost:3000/upload
Prueba superar el límite de tamaño de archivo:
curl --fail-with-body -F "file=@large.csv;type=text/csv" http://localhost:3000/upload
Recupera los datos almacenados:
curl http://localhost:3000/data
Como alternativa, usa Postman: establece el método de la solicitud en POST, la URL en
http://localhost:3000/upload y selecciona la opción «form-data» en la pestaña Body. Agrega una clave
llamada file de tipo File, elige tu archivo CSV y envía tu solicitud.
Consideraciones para producción
Antes de desplegar, ten en cuenta estas buenas prácticas importantes:
- Usa variables de entorno para la configuración (como números de puerto y límites de subida).
- Implementa un registro adecuado con un logger de nivel de producción.
- Agrega limitación de tasa a los endpoints de subida para evitar abusos.
- Considera usar servicios de almacenamiento en la nube (por ejemplo, AWS S3 o Google Cloud Storage) en lugar del sistema de archivos local.
- Implementa autenticación y autorización robustas para mayor seguridad.
- Usa HTTPS para proteger todas las comunicaciones en producción.
- Monitorea los recursos del servidor y planifica estrategias de escalado adecuadas.
Conclusión
Esta guía mostró cómo crear una REST API segura para subir y procesar archivos CSV con Node.js y Express. Al combinar Multer para el manejo seguro de archivos con csv-parser para la extracción de datos, la API procesa las subidas de CSV de forma eficiente e incorpora una gestión de errores robusta. Para soluciones de escalabilidad adicionales, considera explorar los servicios de manejo de archivos disponibles en Transloadit.
