@deinossrl/dgp-agent 1.5.11 → 1.5.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/CHANGELOG.md +21 -0
  2. package/index.mjs +115 -89
  3. package/package.json +2 -2
package/CHANGELOG.md CHANGED
@@ -1,5 +1,26 @@
1
1
  # Changelog - DGP Agent
2
2
 
3
+ ## [1.5.13] - 2026-01-13
4
+
5
+ ### Changed
6
+ - **Logs en tiempo real mejorados**: Desacoplado el log local del log web. Ahora la consola muestra *toda* la actividad de pg_dump/pg_restore inmediatamente (conectando, leyendo schemas, etc.), no solo cuando procesa tablas.
7
+ - Los mensajes repetitivos (bulk data) siguen limitados a uno cada 2 segundos para no saturar, pero los mensajes de estado iniciales son instantáneos.
8
+
9
+ ## [1.5.12] - 2026-01-13
10
+
11
+ ### Added
12
+ - **Progreso en consola local**: Ahora `pg_dump` y `pg_restore` muestran el progreso detallado también en la terminal local del agente, además de enviarlo a la web.
13
+ - Feedback visual inmediato en la terminal para operaciones de backup y restore.
14
+
15
+ ## [1.5.11] - 2026-01-12
16
+
17
+ ### Added
18
+ - CHANGELOG actualizado con historial completo de versiones 1.5.7 a 1.5.10
19
+
20
+ ### Documentation
21
+ - Tooltips mejorados en la UI de backup/restore con información detallada
22
+ - Mejor documentación para entender qué hace cada opción
23
+
3
24
  ## [1.5.10] - 2026-01-12
4
25
 
5
26
  ### Changed
package/index.mjs CHANGED
@@ -261,7 +261,7 @@ function saveSshKeyLocally(sshPrivateKey) {
261
261
  if (process.platform === 'win32') {
262
262
  try {
263
263
  shellSync(`icacls "${keyPath}" /inheritance:r /grant:r "%USERNAME%:RW"`);
264
- } catch {}
264
+ } catch { }
265
265
  }
266
266
  }
267
267
 
@@ -513,7 +513,7 @@ function getRepoContext() {
513
513
  context.project.scripts = Object.keys(pkg.scripts || {});
514
514
  context.project.dependencies = Object.keys(pkg.dependencies || {});
515
515
  context.project.devDependencies = Object.keys(pkg.devDependencies || {});
516
- } catch (e) {}
516
+ } catch (e) { }
517
517
  }
518
518
 
519
519
  if (context.files.includes('requirements.txt') || context.files.includes('setup.py')) {
@@ -1531,11 +1531,66 @@ async function findOrInstallPgDump() {
1531
1531
  const extractCmd = `powershell -command "Expand-Archive -Path '${zipPath}' -DestinationPath '${BIN_DIR}' -Force"`;
1532
1532
  execSync(extractCmd);
1533
1533
 
1534
- // Los binarios estarán en BIN_DIR/pgsql/bin/
1534
+ // Los binarios estarán en BIN_DIR/pgsql/bin/
1535
+ const extractedPgDump = join(BIN_DIR, 'pgsql', 'bin', 'pg_dump.exe');
1536
+
1537
+ if (existsSync(extractedPgDump)) {
1538
+ // Copiar pg_dump.exe, pg_restore.exe y TODAS las DLLs al BIN_DIR raíz
1539
+ const binSrcDir = join(BIN_DIR, 'pgsql', 'bin');
1540
+
1541
+ // Copiar pg_dump.exe, pg_restore.exe y psql.exe
1542
+ execSync(`copy "${extractedPgDump}" "${localPgDump}"`, { shell: 'cmd.exe' });
1543
+
1544
+ const extractedPgRestore = join(BIN_DIR, 'pgsql', 'bin', 'pg_restore.exe');
1545
+ const localPgRestore = join(BIN_DIR, 'pg_restore.exe');
1546
+ if (existsSync(extractedPgRestore)) {
1547
+ execSync(`copy "${extractedPgRestore}" "${localPgRestore}"`, { shell: 'cmd.exe' });
1548
+ }
1549
+
1550
+ const extractedPsql = join(BIN_DIR, 'pgsql', 'bin', 'psql.exe');
1551
+ const localPsql = join(BIN_DIR, 'psql.exe');
1552
+ if (existsSync(extractedPsql)) {
1553
+ execSync(`copy "${extractedPsql}" "${localPsql}"`, { shell: 'cmd.exe' });
1554
+ }
1555
+
1556
+ // Copiar TODAS las DLLs (no solo algunas específicas)
1557
+ execSync(`copy "${binSrcDir}\\*.dll" "${BIN_DIR}\\"`, { shell: 'cmd.exe' });
1558
+
1559
+ // Limpiar archivos temporales
1560
+ unlinkSync(zipPath);
1561
+ // Eliminar carpeta pgsql para ahorrar espacio
1562
+ try {
1563
+ execSync(`rmdir /s /q "${join(BIN_DIR, 'pgsql')}"`, { shell: 'cmd.exe' });
1564
+ } catch (e) {
1565
+ // Ignorar si falla el borrado
1566
+ }
1567
+
1568
+ logSuccess('pg_dump instalado correctamente con todas las dependencias');
1569
+ resolve(localPgDump);
1570
+ } else {
1571
+ reject(new Error('No se pudo extraer pg_dump del archivo'));
1572
+ }
1573
+ } catch (extractError) {
1574
+ reject(new Error(`Error al extraer: ${extractError.message}`));
1575
+ }
1576
+ }, 3000); // Esperar 3 segundos para que Windows libere el archivo
1577
+ });
1578
+ }).on('error', reject);
1579
+ } else {
1580
+ response.pipe(file);
1581
+ file.on('finish', () => {
1582
+ file.close();
1583
+ logInfo('Descarga completada. Extrayendo...');
1584
+
1585
+ // Dar tiempo a Windows para liberar el handle del archivo
1586
+ setTimeout(() => {
1587
+ try {
1588
+ const extractCmd = `powershell -command "Expand-Archive -Path '${zipPath}' -DestinationPath '${BIN_DIR}' -Force"`;
1589
+ execSync(extractCmd);
1590
+
1535
1591
  const extractedPgDump = join(BIN_DIR, 'pgsql', 'bin', 'pg_dump.exe');
1536
1592
 
1537
1593
  if (existsSync(extractedPgDump)) {
1538
- // Copiar pg_dump.exe, pg_restore.exe y TODAS las DLLs al BIN_DIR raíz
1539
1594
  const binSrcDir = join(BIN_DIR, 'pgsql', 'bin');
1540
1595
 
1541
1596
  // Copiar pg_dump.exe, pg_restore.exe y psql.exe
@@ -1553,16 +1608,16 @@ async function findOrInstallPgDump() {
1553
1608
  execSync(`copy "${extractedPsql}" "${localPsql}"`, { shell: 'cmd.exe' });
1554
1609
  }
1555
1610
 
1556
- // Copiar TODAS las DLLs (no solo algunas específicas)
1611
+ // Copiar TODAS las DLLs
1557
1612
  execSync(`copy "${binSrcDir}\\*.dll" "${BIN_DIR}\\"`, { shell: 'cmd.exe' });
1558
1613
 
1559
- // Limpiar archivos temporales
1560
1614
  unlinkSync(zipPath);
1561
- // Eliminar carpeta pgsql para ahorrar espacio
1615
+
1616
+ // Eliminar carpeta pgsql
1562
1617
  try {
1563
1618
  execSync(`rmdir /s /q "${join(BIN_DIR, 'pgsql')}"`, { shell: 'cmd.exe' });
1564
1619
  } catch (e) {
1565
- // Ignorar si falla el borrado
1620
+ // Ignorar
1566
1621
  }
1567
1622
 
1568
1623
  logSuccess('pg_dump instalado correctamente con todas las dependencias');
@@ -1570,61 +1625,6 @@ async function findOrInstallPgDump() {
1570
1625
  } else {
1571
1626
  reject(new Error('No se pudo extraer pg_dump del archivo'));
1572
1627
  }
1573
- } catch (extractError) {
1574
- reject(new Error(`Error al extraer: ${extractError.message}`));
1575
- }
1576
- }, 3000); // Esperar 3 segundos para que Windows libere el archivo
1577
- });
1578
- }).on('error', reject);
1579
- } else {
1580
- response.pipe(file);
1581
- file.on('finish', () => {
1582
- file.close();
1583
- logInfo('Descarga completada. Extrayendo...');
1584
-
1585
- // Dar tiempo a Windows para liberar el handle del archivo
1586
- setTimeout(() => {
1587
- try {
1588
- const extractCmd = `powershell -command "Expand-Archive -Path '${zipPath}' -DestinationPath '${BIN_DIR}' -Force"`;
1589
- execSync(extractCmd);
1590
-
1591
- const extractedPgDump = join(BIN_DIR, 'pgsql', 'bin', 'pg_dump.exe');
1592
-
1593
- if (existsSync(extractedPgDump)) {
1594
- const binSrcDir = join(BIN_DIR, 'pgsql', 'bin');
1595
-
1596
- // Copiar pg_dump.exe, pg_restore.exe y psql.exe
1597
- execSync(`copy "${extractedPgDump}" "${localPgDump}"`, { shell: 'cmd.exe' });
1598
-
1599
- const extractedPgRestore = join(BIN_DIR, 'pgsql', 'bin', 'pg_restore.exe');
1600
- const localPgRestore = join(BIN_DIR, 'pg_restore.exe');
1601
- if (existsSync(extractedPgRestore)) {
1602
- execSync(`copy "${extractedPgRestore}" "${localPgRestore}"`, { shell: 'cmd.exe' });
1603
- }
1604
-
1605
- const extractedPsql = join(BIN_DIR, 'pgsql', 'bin', 'psql.exe');
1606
- const localPsql = join(BIN_DIR, 'psql.exe');
1607
- if (existsSync(extractedPsql)) {
1608
- execSync(`copy "${extractedPsql}" "${localPsql}"`, { shell: 'cmd.exe' });
1609
- }
1610
-
1611
- // Copiar TODAS las DLLs
1612
- execSync(`copy "${binSrcDir}\\*.dll" "${BIN_DIR}\\"`, { shell: 'cmd.exe' });
1613
-
1614
- unlinkSync(zipPath);
1615
-
1616
- // Eliminar carpeta pgsql
1617
- try {
1618
- execSync(`rmdir /s /q "${join(BIN_DIR, 'pgsql')}"`, { shell: 'cmd.exe' });
1619
- } catch (e) {
1620
- // Ignorar
1621
- }
1622
-
1623
- logSuccess('pg_dump instalado correctamente con todas las dependencias');
1624
- resolve(localPgDump);
1625
- } else {
1626
- reject(new Error('No se pudo extraer pg_dump del archivo'));
1627
- }
1628
1628
  } catch (extractError) {
1629
1629
  reject(new Error(`Error al extraer: ${extractError.message}`));
1630
1630
  }
@@ -1809,7 +1809,8 @@ async function executePgDump(command) {
1809
1809
 
1810
1810
  let stderrBuffer = '';
1811
1811
  let stdoutBuffer = '';
1812
- let lastLogTime = Date.now();
1812
+ let lastLogTime = 0; // Para consola local
1813
+ let lastLogTimeWeb = 0; // Para web
1813
1814
  let objectCount = 0;
1814
1815
  let totalEstimated = 0;
1815
1816
 
@@ -1826,32 +1827,44 @@ async function executePgDump(command) {
1826
1827
  const message = data.toString();
1827
1828
  stderrBuffer += message;
1828
1829
 
1829
- // Contar objetos procesados
1830
1830
  const lines = message.split('\n');
1831
1831
  for (const line of lines) {
1832
- if (line.includes('processing') || line.includes('dumping data for table') || line.includes('creating') || line.includes('setting owner')) {
1832
+ const trimmed = line.trim();
1833
+ if (!trimmed) continue;
1834
+
1835
+ // LOGICA LOCAL: Mostrar actividad en consola
1836
+ // Si es un mensaje de "loop" (procesando datos), solo mostrar si pasó tiempo
1837
+ const isLoopMessage = trimmed.includes('dumping data') || trimmed.includes('processing data');
1838
+ const now = Date.now();
1839
+
1840
+ if (!isLoopMessage || now - lastLogTime > 2000) {
1841
+ console.log(`${colors.gray}[pg_dump] ${trimmed}${colors.reset}`);
1842
+ if (isLoopMessage) lastLogTime = now;
1843
+ }
1844
+
1845
+ // LOGICA WEB: Filtrar y contar para la UI
1846
+ if (trimmed.includes('processing') || trimmed.includes('dumping data for table') || trimmed.includes('creating') || trimmed.includes('setting owner')) {
1833
1847
  objectCount++;
1834
1848
  }
1835
1849
  }
1836
1850
 
1837
- // Enviar log cada 2 segundos para no saturar
1851
+ // Enviar log a la WEB cada 2 segundos para no saturar
1838
1852
  const now = Date.now();
1839
- if (now - lastLogTime > 2000) {
1840
- const relevantLine = lines[lines.length - 1].trim();
1841
- if (relevantLine && (relevantLine.includes('processing') || relevantLine.includes('dumping') || relevantLine.includes('table') || relevantLine.includes('creating'))) {
1853
+ if (now - lastLogTimeWeb > 2000) {
1854
+ // ... lógica web existente ...
1855
+ const relevantLine = lines.reverse().find(l => l.includes('processing') || l.includes('dumping') || l.includes('table'));
1856
+ if (relevantLine) {
1857
+ // Solo enviamos a la web, local ya se mostró arriba
1842
1858
  let progressMsg = '';
1843
-
1844
- // Si tenemos estimación, mostrar porcentaje
1845
1859
  if (totalEstimated > 0 && objectCount > 0) {
1846
1860
  const percentage = Math.min(Math.round((objectCount / totalEstimated) * 100), 100);
1847
- progressMsg = `Progreso: ${percentage}% (${objectCount}/${totalEstimated}) - `;
1848
- } else if (objectCount > 0) {
1849
- progressMsg = `Objetos procesados: ${objectCount} - `;
1861
+ progressMsg = `Progreso: ${percentage}% (${objectCount}/${totalEstimated})`;
1862
+ } else {
1863
+ progressMsg = `Objetos procesados: ${objectCount}`;
1850
1864
  }
1851
-
1852
- progressMsg += relevantLine.substring(0, 80);
1853
- addCommandLog('info', progressMsg).catch(() => {});
1854
- lastLogTime = now;
1865
+ progressMsg += ` - ${relevantLine.substring(0, 50)}...`;
1866
+ addCommandLog('info', progressMsg).catch(() => { });
1867
+ lastLogTimeWeb = now;
1855
1868
  }
1856
1869
  }
1857
1870
  });
@@ -1874,7 +1887,7 @@ async function executePgDump(command) {
1874
1887
  } else {
1875
1888
  // Log final con total de objetos procesados
1876
1889
  if (objectCount > 0) {
1877
- addCommandLog('success', `Backup completado: ${objectCount} objetos exportados`).catch(() => {});
1890
+ addCommandLog('success', `Backup completado: ${objectCount} objetos exportados`).catch(() => { });
1878
1891
  }
1879
1892
  resolve();
1880
1893
  }
@@ -2314,7 +2327,8 @@ async function executePgRestore(command) {
2314
2327
  let stdout = '';
2315
2328
  let stderr = '';
2316
2329
  let processedObjects = 0;
2317
- let lastLogTime = Date.now();
2330
+ let lastLogTime = 0;
2331
+ let lastLogTimeWeb = 0;
2318
2332
 
2319
2333
  child.stdout.on('data', (data) => {
2320
2334
  stdout += data.toString();
@@ -2324,15 +2338,26 @@ async function executePgRestore(command) {
2324
2338
  const message = data.toString();
2325
2339
  stderr += message;
2326
2340
 
2327
- // Contar objetos procesados buscando patrones como "processing item" o nombres de tablas
2328
2341
  const lines = message.split('\n');
2329
2342
  for (const line of lines) {
2330
- if (line.includes('processing') || line.includes('creating') || line.includes('restoring')) {
2343
+ const trimmed = line.trim();
2344
+ if (!trimmed) continue;
2345
+
2346
+ // LOGICA LOCAL: Mostrar actividad en consola
2347
+ const isLoopMessage = trimmed.includes('processing item') || trimmed.includes('processing data');
2348
+ const now = Date.now();
2349
+
2350
+ if (!isLoopMessage || now - lastLogTime > 2000) {
2351
+ console.log(`${colors.gray}[pg_restore] ${trimmed}${colors.reset}`);
2352
+ if (isLoopMessage) lastLogTime = now;
2353
+ }
2354
+
2355
+ // LOGICA WEB
2356
+ if (trimmed.includes('processing') || trimmed.includes('creating') || trimmed.includes('restoring')) {
2331
2357
  processedObjects++;
2332
2358
 
2333
- // Enviar log cada 2 segundos para no saturar
2334
- const now = Date.now();
2335
- if (now - lastLogTime > 2000) {
2359
+ // Enviar log WEB cada 2 segundos para no saturar
2360
+ if (now - lastLogTimeWeb > 2000) {
2336
2361
  let progressMsg = '';
2337
2362
 
2338
2363
  if (totalObjects > 0) {
@@ -2343,13 +2368,14 @@ async function executePgRestore(command) {
2343
2368
  }
2344
2369
 
2345
2370
  // Agregar detalle de lo que se está procesando
2346
- const relevantLine = line.substring(0, 100).trim();
2371
+ const relevantLine = trimmed.substring(0, 100);
2347
2372
  if (relevantLine) {
2348
2373
  progressMsg += ` - ${relevantLine}`;
2349
2374
  }
2350
2375
 
2351
- addCommandLog('info', progressMsg).catch(() => {});
2352
- lastLogTime = now;
2376
+ // logInfo(progressMsg); // Ya mostramos raw stderr arriba
2377
+ addCommandLog('info', progressMsg).catch(() => { });
2378
+ lastLogTimeWeb = now;
2353
2379
  }
2354
2380
  }
2355
2381
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@deinossrl/dgp-agent",
3
- "version": "1.5.11",
3
+ "version": "1.5.13",
4
4
  "description": "Agente local para Despliegue-GPT - Reporta el estado del repositorio Git a la plataforma TenMinute IA",
5
5
  "main": "index.mjs",
6
6
  "bin": {
@@ -33,4 +33,4 @@
33
33
  "dependencies": {
34
34
  "@supabase/supabase-js": "^2.39.0"
35
35
  }
36
- }
36
+ }