Need english README 馃嚞馃嚙 馃嚭馃嚫? No worries, click here
Un ETL Node.js con base de datos local de RUCs de Paraguay 馃彚
- El gobierno de Paraguay no ofrece un webservice para obtener datos de contribuyentes.
- Encontr茅 repos en GitHub con soluciones para esto, pero ninguno en Javascript.
As铆 que decid铆 crear la versi贸n en Javascript. 馃
La aplicaci贸n ejecuta una tarea al iniciarse y la repite todos los d铆as a una hora programada. Puedes programarla seg煤n lo que mejor te convenga. 馃攧
El ETL obtiene la informaci贸n del sitio web del gobierno, extrae los datos de archivos zip, los parsea y los guarda en una base de datos SQLite. 馃捑
- Node 馃殌 (Testeado con node 18)
- Clona el repositorio
- CD al directorio
- Copia el archivo
.env.example
a.env
y realiza los ajustes necesarios - Ejecuta
npm install
- Ejecuta
npm run migrate --name init
- Ejecuta
npm run build
- Ejecuta
npm start
...o, si quieres disparar el proceso ETL inmediatamente, ejecutanpm run start -- startmeup
Si has seguido los pasos correctamente, deber铆as ver el proceso inici谩ndose en el horario programado (o inmediatamente si lo iniciaste con el flag startmeup), y en la salida deber铆a verse algo as铆:
Downloading zip, and parsing data for ending digit: 0
173995 contribuyentes found
Storing data...
Y, despu茅s de un tiempo, deber铆as ver:
Done with ending digit: 0
El proceso se repetir谩 para todos los d铆gitos finales (0-9).
Una vez que tu base de datos contenga datos, puedes usar la API REST para consultarlos.
La aplicaci贸n expone una API REST simple con los siguientes endpoints:
GET /ruc/:ruc
- Retorna los datos del contribuyente para el RUC dado
e.g. /ruc/80000001
retorna
{
"ruc": "80000001",
"razonSocial": "NAVIERA CONOSUR SOCIEDAD ANONIMA",
"digitoVerificador": "3",
"rucAnterior": "NCOA905190H",
"estado": "BLOQUEADO",
"fechaHoraImportacion": "2023-12-07T11:31:51.496Z"
}
GET /razon-social/:term
- Retorna un array de contribuyentes que contienen el t茅rmino dado en su nombre (Razon Social)
e.g. /razon-social/MARTINETTI LOPEZ
retorna
[
{
"ruc": "2509803",
"razonSocial": "MARTINETTI LOPEZ, VICTOR ALEJANDRO",
"digitoVerificador": "9",
"rucAnterior": "MALV813370R",
"estado": "ACTIVO",
"fechaHoraImportacion": "2023-12-07T11:38:31.248Z"
},
{
"ruc": "2509804",
"razonSocial": "MARTINETTI LOPEZ, JUAN RAFAEL",
"digitoVerificador": "7",
"rucAnterior": "CAVI712851Z",
"estado": "ACTIVO",
"fechaHoraImportacion": "2023-12-07T11:42:02.729Z"
},
{
"ruc": "3187875",
"razonSocial": "MARTINETTI LOPEZ, FABIOLA GRACIELA",
"digitoVerificador": "0",
"rucAnterior": "MALF901730L",
"estado": "ACTIVO",
"fechaHoraImportacion": "2023-12-07T11:45:13.706Z"
}
]
Hay que saber que el gobierno puede cambiar cualquier cosa en cualquier momento (por ejemplo, la URL, el formato de los archivos zip, etc.), por lo que el ETL poder铆a dejar de funcionar. Obviamente, eso tambi茅n me afectar铆a a m铆, as铆 que tratar茅 de mantener este repositorio actualizado tanto como pueda.
TSConfig de Total Typescript
https://www.totaltypescript.com/tsconfig-cheat-sheet
驴Por qu茅 usar SQLite?
Primera motivaci贸n:
https://kentcdodds.com/blog/i-migrated-from-a-postgres-cluster-to-distributed-sqlite-with-litefs
Eso me llev贸 a esto:
https://fly.io/blog/all-in-on-sqlite-litestream/
- [鉁匽 Agregar una API simple
- Agregar pruebas
- Agregar un logger configurado para enviar notificaciones por correo electr贸nico en caso de errores
- Agregar un crawler para intentar detectar cambios en el sitio web del gobierno
MIT