Infraestructura y Red:
- Tailscale v1.94.2 instalado en srv-dasu (IP: 100.116.210.36)
- Configurado como subnet router para 10.0.100.0/24
- Fix: Repositorios enterprise de Proxmox deshabilitados (.sources → .bak)
Despliegue del Sistema (pcv-dasu0):
- Transferencia SCP de runSysDasuten.zip via SSH puerto 7022
- Extracción en C:\Dasuten\runSysDasuten- Kermet.ini configurado: SERVER=sql-dasuten
- InstaladorComponentesKermet.exe (silent install)
- Fuentes TrueType registradas en Windows (Code39, I2OF5)
- Firewall TCP 1433 abierto en sql-dasuten
- Test-NetConnection: TcpTestSucceeded=True
- Login exitoso con usuario aalmiron ✅
ADN y Contexto:
- 05_ia.md: Regla 13 Auto-Contextualización Topológica
- 07_proyectos.md: Sección 'Topología y Red' obligatoria en manifiestos
- P2601_dasuten.md: Contexto de red documentado
- nodos/pcv-dasu0.md: Puerto SSH actualizado a 7022
Dashboard P2601:
- Hitos completados: 8 → 11 (P02.APP, NET01, TEST03)
- Progreso: 67% → 79%
- pcv-dasu0: Testing → Online
- Nuevo hito activo: UAT (verificación presencial)
Bitácoras y Documentación:
- Bitácora 04/03 y 05/03 completas
- Plan de despliegue en docs/plan/260305-1017
- Investigación de ingeniería inversa documentada
- ns8-candados: Instrucciones de uso para IA agregadas
- dtic-BITACORAs: CRUD completo, Dashboard P2601 integrado
Herramientas:
- w-zombi: Mejora anti-loop (max 5 ciclos)
- Payloads de despliegue SQL y sistema generados
95 lines
3.2 KiB
JavaScript
95 lines
3.2 KiB
JavaScript
const fs = require('fs');
|
|
const { Pool } = require('pg');
|
|
|
|
const pool = new Pool({
|
|
connectionString: "postgres://dtic_user:dtic_pass_2026@localhost:5433/dtic_bitacoras"
|
|
});
|
|
|
|
async function syncFile(filePath) {
|
|
const content = fs.readFileSync(filePath, 'utf8');
|
|
const lines = content.split('\n');
|
|
const dateStr = filePath.match(/(\d{4}-\d{2}-\d{2})\.md/)[1];
|
|
|
|
console.log(`Sincronizando bitácora: ${dateStr}`);
|
|
|
|
// Asegurar bitácora
|
|
const bResult = await pool.query(
|
|
'INSERT INTO bitacoras.bitacoras (fecha) VALUES ($1) ON CONFLICT (fecha) DO UPDATE SET fecha = EXCLUDED.fecha RETURNING id',
|
|
[dateStr]
|
|
);
|
|
const bitacoraId = bResult.rows[0].id;
|
|
|
|
// Obtener mapeo de nodos
|
|
const { rows: nodos } = await pool.query('SELECT id, nombre FROM bitacoras.nodos');
|
|
const nodoMap = {};
|
|
nodos.forEach(n => { nodoMap[n.nombre] = n.id; });
|
|
|
|
// Limpiar entradas previas
|
|
await pool.query('DELETE FROM bitacoras.entradas WHERE bitacora_id = $1', [bitacoraId]);
|
|
|
|
let currentNodoId = null;
|
|
let inDetailedActivities = false;
|
|
let entriesFound = 0;
|
|
|
|
for (let line of lines) {
|
|
// Detectar inicio de sección de actividades detalladas
|
|
if (line.includes('Actividades Detalladas')) {
|
|
inDetailedActivities = true;
|
|
continue;
|
|
}
|
|
|
|
if (!inDetailedActivities) continue;
|
|
|
|
// Detectar cambio de nodo
|
|
if (line.startsWith('### ')) {
|
|
const nodoName = line.replace('### ', '').trim().split(' ')[0];
|
|
currentNodoId = nodoMap[nodoName] || null;
|
|
if (currentNodoId) console.log(`Cambiando a nodo: ${nodoName} (ID: ${currentNodoId})`);
|
|
continue;
|
|
}
|
|
|
|
if (!currentNodoId) continue;
|
|
|
|
// Detectar entrada de tabla
|
|
const regex = /\|\s*(\d{2}:\d{2})\s*\|\s*(\d{2}:\d{2})\s*\|\s*(.*?)\s*\|\s*(.*?)\s*\|/;
|
|
const match = line.match(regex);
|
|
|
|
if (match) {
|
|
let inicio = match[1];
|
|
let fin = match[2];
|
|
let descRaw = match[3];
|
|
let estadoRaw = match[4];
|
|
|
|
const esIA = descRaw.includes('(IA)');
|
|
let descripcion = descRaw.replace('(IA)', '').replace(/\*\*/g, '').replace(/__/g, '').trim();
|
|
// A veces el MD tiene ** al principio
|
|
if (descripcion.startsWith('**')) descripcion = descripcion.substring(2);
|
|
|
|
const statusMatch = estadoRaw.match(/\[([A-Z])\] (.*)/);
|
|
const modo = statusMatch ? statusMatch[1] : 'P';
|
|
const estado = statusMatch ? statusMatch[2] : estadoRaw;
|
|
|
|
await pool.query(
|
|
`INSERT INTO bitacoras.entradas (inicio, fin, descripcion, estado, modo, es_ia, bitacora_id, nodo_id)
|
|
VALUES ($1, $2, $3, $4, $5, $6, $7, $8)`,
|
|
[inicio, fin, descripcion, estado, modo, esIA, bitacoraId, currentNodoId]
|
|
);
|
|
entriesFound++;
|
|
}
|
|
}
|
|
|
|
console.log(`Sincronización finalizada. Entradas cargadas: ${entriesFound}`);
|
|
await pool.end();
|
|
}
|
|
|
|
const file = process.argv[2];
|
|
if (!file) {
|
|
console.error('Uso: node sync_bitacora.js <path_to_md>');
|
|
process.exit(1);
|
|
}
|
|
|
|
syncFile(file).catch(err => {
|
|
console.error(err);
|
|
process.exit(1);
|
|
});
|