feat: sincronização total blindada JSON -> Postgres (Alunos, Turmas, Provas, Frequências)
This commit is contained in:
parent
bb268b61e0
commit
1d761200f5
|
|
@ -0,0 +1,53 @@
|
|||
|
||||
import pkg from 'pg';
|
||||
const { Pool } = pkg;
|
||||
|
||||
const DATABASE_URL = 'postgresql://edumanager:EduManager2026!Seguro@localhost:5432/edumanager';
|
||||
const pool = new Pool({ connectionString: DATABASE_URL });
|
||||
|
||||
async function runDiag() {
|
||||
try {
|
||||
const { rows } = await pool.query('SELECT data FROM school_data WHERE id = 1');
|
||||
const data = rows[0]?.data || {};
|
||||
|
||||
console.log('--- DIAGNÓSTICO DE SINCRONIZAÇÃO ---');
|
||||
|
||||
// 1. Verificar Alunos
|
||||
const jsonStudents = data.students || [];
|
||||
const { rows: dbStudents } = await pool.query('SELECT id, nome FROM alunos');
|
||||
console.log(`JSON: ${jsonStudents.length} alunos | DB: ${dbStudents.length} alunos`);
|
||||
|
||||
if (jsonStudents.length > 0) {
|
||||
const sample = jsonStudents[0];
|
||||
const inDb = dbStudents.find(s => s.id === sample.id);
|
||||
console.log(`Exemplo Aluno [${sample.name}]: ${inDb ? '✅ No DB' : '❌ NÃO ESTÁ NO DB'}`);
|
||||
|
||||
// Verificar campos específicos do primeiro aluno
|
||||
if (inDb) {
|
||||
const { rows: fullStudent } = await pool.query('SELECT * FROM alunos WHERE id = $1', [sample.id]);
|
||||
const dbS = fullStudent[0];
|
||||
console.log('--- Comparação de Campos (Exemplo) ---');
|
||||
console.log(`CPF: JSON[${sample.cpf || '?'}] vs DB[${dbS.cpf || '?'}]`);
|
||||
console.log(`Telefone: JSON[${sample.phone || '?'}] vs DB[${dbS.telefone || '?'}]`);
|
||||
console.log(`Status: JSON[${sample.status || '?'}] vs DB[${dbS.status || '?'}]`);
|
||||
}
|
||||
}
|
||||
|
||||
// 2. Verificar Turmas
|
||||
const jsonClasses = data.classes || [];
|
||||
const { rows: dbClasses } = await pool.query('SELECT COUNT(*) FROM turmas');
|
||||
console.log(`JSON: ${jsonClasses.length} turmas | DB: ${dbClasses[0].count} turmas`);
|
||||
|
||||
// 3. Verificar Provas
|
||||
const jsonExams = data.exams || [];
|
||||
const { rows: dbExams } = await pool.query('SELECT COUNT(*) FROM provas');
|
||||
console.log(`JSON: ${jsonExams.length} provas | DB: ${dbExams[0].count} provas`);
|
||||
|
||||
} catch (err) {
|
||||
console.error('Erro no diagnóstico:', err.message);
|
||||
} finally {
|
||||
await pool.end();
|
||||
}
|
||||
}
|
||||
|
||||
runDiag();
|
||||
|
|
@ -283,7 +283,7 @@ export async function syncJsonToRelationalTables() {
|
|||
const data = await getSchoolData();
|
||||
if (!data) return;
|
||||
|
||||
console.log('[Sincronização] 🔄 Iniciando espelhamento total JSON -> Tabelas Relacionais...');
|
||||
console.log('[Sincronização] 🔄 Iniciando espelhamento TOTAL (Modo Blindado)...');
|
||||
await client.query('BEGIN');
|
||||
|
||||
// 1. Sincronizar Cursos
|
||||
|
|
@ -303,7 +303,33 @@ export async function syncJsonToRelationalTables() {
|
|||
}
|
||||
}
|
||||
|
||||
// 2. Sincronizar Turmas
|
||||
// 2. Sincronizar Disciplinas (Subjects)
|
||||
if (data.subjects && Array.isArray(data.subjects)) {
|
||||
for (const sub of data.subjects) {
|
||||
if (!sub.id || !sub.name) continue;
|
||||
await client.query(
|
||||
`INSERT INTO disciplinas (id, nome)
|
||||
VALUES ($1, $2)
|
||||
ON CONFLICT (id) DO UPDATE SET nome = EXCLUDED.nome`,
|
||||
[sub.id, sub.name]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// 3. Sincronizar Períodos (Bimestres)
|
||||
if (data.periods && Array.isArray(data.periods)) {
|
||||
for (const p of data.periods) {
|
||||
if (!p.id || !p.name) continue;
|
||||
await client.query(
|
||||
`INSERT INTO periodos (id, nome)
|
||||
VALUES ($1, $2)
|
||||
ON CONFLICT (id) DO UPDATE SET nome = EXCLUDED.nome`,
|
||||
[p.id, p.name]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// 4. Sincronizar Turmas
|
||||
if (data.classes && Array.isArray(data.classes)) {
|
||||
for (const t of data.classes) {
|
||||
if (!t.id || !t.name) continue;
|
||||
|
|
@ -320,7 +346,7 @@ export async function syncJsonToRelationalTables() {
|
|||
}
|
||||
}
|
||||
|
||||
// 3. Sincronizar Alunos
|
||||
// 5. Sincronizar Alunos (Mapeamento Completo de Campos)
|
||||
if (data.students && Array.isArray(data.students)) {
|
||||
for (const s of data.students) {
|
||||
if (!s.id || !s.name) continue;
|
||||
|
|
@ -353,61 +379,41 @@ export async function syncJsonToRelationalTables() {
|
|||
}
|
||||
}
|
||||
|
||||
// 4. Sincronizar Frequências
|
||||
// 6. Sincronizar Provas (Corrigindo vínculo com disciplinas)
|
||||
if (data.exams && Array.isArray(data.exams)) {
|
||||
for (const e of data.exams) {
|
||||
if (!e.id || !e.title) continue;
|
||||
await client.query(
|
||||
`INSERT INTO provas (id, turma_id, disciplina_id, periodo_id, titulo, duracao_minutos, status)
|
||||
VALUES ($1, $2, $3, $4, $5, $6, $7)
|
||||
ON CONFLICT (id) DO UPDATE SET
|
||||
turma_id = EXCLUDED.turma_id, disciplina_id = EXCLUDED.disciplina_id, periodo_id = EXCLUDED.periodo_id,
|
||||
titulo = EXCLUDED.titulo, duracao_minutos = EXCLUDED.duracao_minutos, status = EXCLUDED.status`,
|
||||
[e.id, e.classId || null, e.subjectId || null, e.periodId || null, e.title, e.durationMinutes || 60, e.status || 'draft']
|
||||
).catch(err => console.warn(`[Sync:Provas] Erro na prova ${e.id}:`, err.message));
|
||||
}
|
||||
}
|
||||
|
||||
// 7. Sincronizar Frequências (Baseado na estrutura real do JSON)
|
||||
if (data.attendance && Array.isArray(data.attendance)) {
|
||||
for (const f of data.attendance) {
|
||||
if (!f.id || !f.studentId || !f.classId) continue;
|
||||
await client.query(
|
||||
`INSERT INTO frequencias (id, aluno_id, turma_id, data, foto, verificado, tipo, justificativa, justificativa_aceita)
|
||||
VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9)
|
||||
`INSERT INTO frequencias (id, aluno_id, turma_id, data, foto, verificado, tipo)
|
||||
VALUES ($1, $2, $3, $4, $5, $6, $7)
|
||||
ON CONFLICT (id) DO UPDATE SET
|
||||
aluno_id = EXCLUDED.aluno_id, turma_id = EXCLUDED.turma_id, data = EXCLUDED.data,
|
||||
foto = EXCLUDED.foto, verificado = EXCLUDED.verificado, tipo = EXCLUDED.tipo,
|
||||
justificativa = EXCLUDED.justificativa, justificativa_aceita = EXCLUDED.justificativa_aceita`,
|
||||
[f.id, f.studentId, f.classId, f.date, f.photo || '', f.verified || false, f.type || 'presence', f.justification || '', f.justificationAccepted || false]
|
||||
foto = EXCLUDED.foto, verificado = EXCLUDED.verificado, tipo = EXCLUDED.tipo`,
|
||||
[f.id, f.studentId, f.classId, f.date, f.photo || '', f.verified || false, f.type || 'presence']
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// 5. Sincronizar Disciplinas (Subjects)
|
||||
if (data.subjects && Array.isArray(data.subjects)) {
|
||||
for (const sub of data.subjects) {
|
||||
if (!sub.id || !sub.name) continue;
|
||||
await client.query(`INSERT INTO cursos (id, nome) VALUES ($1, $2) ON CONFLICT (id) DO NOTHING`, [sub.id, sub.name]);
|
||||
}
|
||||
}
|
||||
|
||||
// 6. Sincronizar Períodos (Bimestres)
|
||||
if (data.periods && Array.isArray(data.periods)) {
|
||||
for (const p of data.periods) {
|
||||
if (!p.id || !p.name) continue;
|
||||
// Se houver tabela de períodos, inserimos. Se não, garantimos ao menos o ID.
|
||||
await client.query(`INSERT INTO school_data (id) VALUES (1) ON CONFLICT (id) DO NOTHING`);
|
||||
}
|
||||
}
|
||||
|
||||
// 7. Sincronizar Provas/Avaliações
|
||||
if (data.exams && Array.isArray(data.exams)) {
|
||||
for (const e of data.exams) {
|
||||
if (!e.id || !e.title) continue;
|
||||
try {
|
||||
await client.query(
|
||||
`INSERT INTO provas (id, titulo, disciplina_id)
|
||||
VALUES ($1, $2, $3)
|
||||
ON CONFLICT (id) DO UPDATE SET titulo = EXCLUDED.titulo, disciplina_id = EXCLUDED.disciplina_id`,
|
||||
[e.id, e.title, e.subjectId || null]
|
||||
);
|
||||
} catch(err) {
|
||||
// Fallback se a tabela provas não estiver pronta
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
await client.query('COMMIT');
|
||||
console.log('[Sincronização] 🚀 Sincronização COMPLETA (Alunos, Turmas, Provas, Frequência) concluída!');
|
||||
console.log('[Sincronização] 🚀 Espelhamento TOTAL concluído com sucesso!');
|
||||
} catch (err) {
|
||||
await client.query('ROLLBACK');
|
||||
console.error('[Sincronização] ❌ Erro crítico ao sincronizar:', err.message);
|
||||
console.error('[Sincronização] ❌ Erro Crítico:', err.message);
|
||||
} finally {
|
||||
client.release();
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue