Checkpoint: Correction complète du bug d'import Excel - Utilisation de $returningId() pour récupérer les IDs après insertion (formations et séquences), ajout de la colonne ordre obligatoire pour les dates de formation. L'import fonctionne maintenant correctement.
This commit is contained in:
58
.manus/db/db-query-1764099145203.json
Normal file
58
.manus/db/db-query-1764099145203.json
Normal file
@@ -0,0 +1,58 @@
|
||||
{
|
||||
"query": "SHOW COLUMNS FROM datesFormation;",
|
||||
"command": "mysql --batch --raw --column-names --default-character-set=utf8mb4 --host gateway02.us-east-1.prod.aws.tidbcloud.com --port 4000 --user 4CrrYuB5tme73Qo.root --database 7PAT67UmWoxv8vwp8Bbcv6 --execute SHOW COLUMNS FROM datesFormation;",
|
||||
"rows": [
|
||||
{
|
||||
"Field": "id",
|
||||
"Type": "int(11)",
|
||||
"Null": "NO",
|
||||
"Key": "PRI",
|
||||
"Default": "NULL",
|
||||
"Extra": "auto_increment"
|
||||
},
|
||||
{
|
||||
"Field": "sequenceId",
|
||||
"Type": "int(11)",
|
||||
"Null": "NO",
|
||||
"Key": "",
|
||||
"Default": "NULL",
|
||||
"Extra": ""
|
||||
},
|
||||
{
|
||||
"Field": "dateDebut",
|
||||
"Type": "datetime",
|
||||
"Null": "NO",
|
||||
"Key": "",
|
||||
"Default": "NULL",
|
||||
"Extra": ""
|
||||
},
|
||||
{
|
||||
"Field": "dateFin",
|
||||
"Type": "datetime",
|
||||
"Null": "NO",
|
||||
"Key": "",
|
||||
"Default": "NULL",
|
||||
"Extra": ""
|
||||
},
|
||||
{
|
||||
"Field": "ordre",
|
||||
"Type": "int(11)",
|
||||
"Null": "NO",
|
||||
"Key": "",
|
||||
"Default": "NULL",
|
||||
"Extra": ""
|
||||
},
|
||||
{
|
||||
"Field": "createdAt",
|
||||
"Type": "timestamp",
|
||||
"Null": "NO",
|
||||
"Key": "",
|
||||
"Default": "CURRENT_TIMESTAMP",
|
||||
"Extra": ""
|
||||
}
|
||||
],
|
||||
"messages": [],
|
||||
"stdout": "Field\tType\tNull\tKey\tDefault\tExtra\nid\tint(11)\tNO\tPRI\tNULL\tauto_increment\nsequenceId\tint(11)\tNO\t\tNULL\t\ndateDebut\tdatetime\tNO\t\tNULL\t\ndateFin\tdatetime\tNO\t\tNULL\t\nordre\tint(11)\tNO\t\tNULL\t\ncreatedAt\ttimestamp\tNO\t\tCURRENT_TIMESTAMP\t\n",
|
||||
"stderr": "",
|
||||
"execution_time_ms": 63
|
||||
}
|
||||
@@ -196,13 +196,13 @@ export async function importToDatabase(
|
||||
for (const formation of formations) {
|
||||
try {
|
||||
console.log(`[Import] Création formation: ${formation.nom}`);
|
||||
const result = await db.insert(formationsTable).values({
|
||||
const [result] = await db.insert(formationsTable).values({
|
||||
nom: formation.nom,
|
||||
description: formation.description,
|
||||
lienUnique: generateUniqueLien(),
|
||||
});
|
||||
}).$returningId();
|
||||
|
||||
const formationId = Number(result.insertId);
|
||||
const formationId = result.id;
|
||||
formationIdMap.set(formation.nom.toLowerCase(), formationId);
|
||||
console.log(`[Import] Formation créée avec ID ${formationId}, ajoutée à la map avec clé: "${formation.nom.toLowerCase()}"`);
|
||||
formationsCreated++;
|
||||
@@ -238,7 +238,7 @@ export async function importToDatabase(
|
||||
continue;
|
||||
}
|
||||
|
||||
const result = await db.insert(sequencesTable).values({
|
||||
const [result] = await db.insert(sequencesTable).values({
|
||||
formationId,
|
||||
nom: sequence.nom,
|
||||
lieu: sequence.lieu,
|
||||
@@ -246,16 +246,18 @@ export async function importToDatabase(
|
||||
capaciteMax: sequence.capaciteMax,
|
||||
dateBlocage: new Date(sequence.dateBlocage),
|
||||
statut: sequence.statut,
|
||||
});
|
||||
}).$returningId();
|
||||
|
||||
const sequenceId = Number(result.insertId);
|
||||
const sequenceId = result.id;
|
||||
|
||||
// Insérer les dates de formation
|
||||
for (const date of sequence.dates.slice(0, 4)) {
|
||||
for (let i = 0; i < Math.min(sequence.dates.length, 4); i++) {
|
||||
const date = sequence.dates[i];
|
||||
await db.insert(datesFormation).values({
|
||||
sequenceId,
|
||||
dateDebut: new Date(date.debut),
|
||||
dateFin: new Date(date.fin),
|
||||
ordre: i + 1,
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
46
test-import-direct.ts
Normal file
46
test-import-direct.ts
Normal file
@@ -0,0 +1,46 @@
|
||||
import { parseExcelFile, importToDatabase } from './server/importExcel';
|
||||
import { readFileSync } from 'fs';
|
||||
|
||||
async function testImport() {
|
||||
console.log('=== TEST IMPORT DIRECT ===\n');
|
||||
|
||||
const buffer = readFileSync('/home/ubuntu/upload/template_import_formations_test.xlsx');
|
||||
const { formations, sequences } = parseExcelFile(buffer);
|
||||
|
||||
console.log(`Formations parsées: ${formations.length}`);
|
||||
formations.forEach((f, i) => {
|
||||
console.log(` ${i}: "${f.nom}" - "${f.description}" - public: "${f.publicCible}"`);
|
||||
});
|
||||
|
||||
console.log(`\nSéquences parsées: ${sequences.length}`);
|
||||
sequences.forEach((s, i) => {
|
||||
console.log(` ${i}: formation="${s.formationNom}", nom="${s.nom}"`);
|
||||
});
|
||||
|
||||
console.log('\n=== DÉBUT IMPORT EN BASE ===\n');
|
||||
const result = await importToDatabase(formations, sequences);
|
||||
|
||||
console.log('\n=== RÉSULTAT ===');
|
||||
console.log(`Success: ${result.success}`);
|
||||
console.log(`Formations créées: ${result.formationsCreated}`);
|
||||
console.log(`Séquences créées: ${result.sequencesCreated}`);
|
||||
|
||||
if (result.errors.length > 0) {
|
||||
console.log('\nErreurs:');
|
||||
result.errors.forEach(e => console.log(` - ${e}`));
|
||||
}
|
||||
|
||||
if (result.warnings.length > 0) {
|
||||
console.log('\nAvertissements:');
|
||||
result.warnings.forEach(w => console.log(` - ${w}`));
|
||||
}
|
||||
}
|
||||
|
||||
testImport().then(() => {
|
||||
console.log('\n=== TEST TERMINÉ ===');
|
||||
process.exit(0);
|
||||
}).catch(err => {
|
||||
console.error('\n=== ERREUR FATALE ===');
|
||||
console.error(err);
|
||||
process.exit(1);
|
||||
});
|
||||
7
todo.md
7
todo.md
@@ -677,3 +677,10 @@
|
||||
- [x] Vérifier le schéma de la table formations en base de données (publicCible n'existe pas dans formations)
|
||||
- [x] Corriger le code d'import (retiré publicCible de l'insertion formations)
|
||||
- [x] Tester l'import après correction
|
||||
|
||||
## Bug import Excel - Problème persistant "Formation non trouvée"
|
||||
|
||||
- [x] Analyser les logs serveur pour voir si la formation est réellement créée (ID = NaN)
|
||||
- [x] Vérifier si l'erreur vient de la création ou de la recherche dans la map (problème de récupération ID)
|
||||
- [x] Corriger le problème identifié (utilisation de $returningId() pour formations et séquences, ajout ordre pour dates)
|
||||
- [x] Tester l'import et valider que tout fonctionne
|
||||
|
||||
Reference in New Issue
Block a user