- Catálogo de obligaciones fiscales expandido a 30 entradas con campo requierePago. - Soporte de frecuencia cuatrimestral en obligaciones y declaraciones. - Automatización de cierre de obligaciones fiscales desde Documentos › Declaraciones. - Nuevas tablas obligacion_evidencias, obligacion_periodos estados y declaracion_obligaciones. - Nuevo servicio obligacion-evidencias.service.ts y endpoints REST. - Refactor de declaraciones.service.ts para vincular obligaciones y crear evidencias. - Notificaciones por email para evidencias de obligaciones. - Adjuntar PDFs en correo de declaración subida. - Fix drill-down de CFDIs: carga completa al visualizar. - Fix sincronización SAT: tipos P/N, UUID case-insensitive, no reutilizar requestId. - Fix suscripciones pending en /configuracion/planes-despacho. - Fix sugerencias de Clave Producto SAT: importar catálogo y robustecer autocomplete. - Quitar toggle manual de completado en Configuración › Obligaciones fiscales › Tareas. - Scripts de soporte para Demo Ventas y utilerías (change-user-email, resend-welcome, import-clave-prod-serv). - Documentación de cambios en docs/CAMBIOS-2026-05-04.md.
57 lines
1.6 KiB
TypeScript
57 lines
1.6 KiB
TypeScript
import fs from 'fs';
|
|
import readline from 'readline';
|
|
import { prisma } from '../src/config/database.js';
|
|
|
|
const BATCH_SIZE = 2000;
|
|
const CSV_PATH = process.argv[2] || '/tmp/claves_prod_serv.csv';
|
|
|
|
async function main() {
|
|
if (!fs.existsSync(CSV_PATH)) {
|
|
console.error(`Archivo no encontrado: ${CSV_PATH}`);
|
|
console.error('Uso: npx tsx scripts/import-clave-prod-serv.ts [ruta/al/csv]');
|
|
process.exit(1);
|
|
}
|
|
|
|
const existing = await prisma.catClaveProdServ.count();
|
|
console.log(`Registros existentes: ${existing}`);
|
|
if (existing > 0) {
|
|
console.log('El catálogo ya tiene datos. No se importará nada.');
|
|
process.exit(0);
|
|
}
|
|
|
|
const fileStream = fs.createReadStream(CSV_PATH, { encoding: 'utf-8' });
|
|
const rl = readline.createInterface({ input: fileStream, crlfDelay: Infinity });
|
|
|
|
let batch: { clave: string; descripcion: string }[] = [];
|
|
let total = 0;
|
|
|
|
for await (const line of rl) {
|
|
const idx = line.indexOf(',');
|
|
if (idx === -1) continue;
|
|
const clave = line.slice(0, idx).trim();
|
|
const descripcion = line.slice(idx + 1).trim();
|
|
if (!clave || !descripcion) continue;
|
|
batch.push({ clave, descripcion });
|
|
|
|
if (batch.length >= BATCH_SIZE) {
|
|
await prisma.catClaveProdServ.createMany({ data: batch, skipDuplicates: true });
|
|
total += batch.length;
|
|
console.log(`Importados: ${total}`);
|
|
batch = [];
|
|
}
|
|
}
|
|
|
|
if (batch.length > 0) {
|
|
await prisma.catClaveProdServ.createMany({ data: batch, skipDuplicates: true });
|
|
total += batch.length;
|
|
}
|
|
|
|
console.log(`Importación completada. Total: ${total}`);
|
|
process.exit(0);
|
|
}
|
|
|
|
main().catch((err) => {
|
|
console.error(err);
|
|
process.exit(1);
|
|
});
|