Fix two backend correctness issues

- Wrap setThesisJury() in a transaction: the method did a DELETE then multiple
  INSERTs with no atomicity guarantee. A partial failure (e.g. findOrCreateSupervisor
  throwing) would leave the jury table with orphaned rows. The fix uses
  pdo->inTransaction() to avoid nesting when called from within an outer transaction,
  and performs beginTransaction/commit/rollBack otherwise.

- Replace raw PDO query in admin/thanks.php with db->getThesisFiles(): the file
  listing after TFE submission was manually preparing a SELECT on thesis_files
  instead of calling the existing Database::getThesisFiles() method. Removes the
  getPDO() call entirely from that file.
This commit is contained in:
Pontoporeia
2026-03-28 13:28:24 +01:00
parent 69e161ada3
commit 20e5f71634
3 changed files with 30 additions and 25 deletions

View File

@@ -812,19 +812,33 @@ class Database {
* $juryMembers: array of ['name' => string, 'role' => string, 'is_external' => int]
*/
public function setThesisJury(int $thesisId, array $juryMembers): void {
$this->pdo->prepare("DELETE FROM thesis_supervisors WHERE thesis_id = ?")->execute([$thesisId]);
$stmt = $this->pdo->prepare("
INSERT INTO thesis_supervisors (thesis_id, supervisor_id, role, is_external, supervisor_order)
VALUES (?, ?, ?, ?, ?)
");
foreach ($juryMembers as $order => $member) {
$name = trim($member['name'] ?? '');
if ($name === '') continue;
$supervisorId = $this->findOrCreateSupervisor($name);
$role = in_array($member['role'], ['president', 'promoteur', 'lecteur'])
? $member['role'] : 'promoteur';
$isExternal = isset($member['is_external']) ? (int)$member['is_external'] : 0;
$stmt->execute([$thesisId, $supervisorId, $role, $isExternal, $order + 1]);
$alreadyInTransaction = $this->pdo->inTransaction();
if (!$alreadyInTransaction) {
$this->pdo->beginTransaction();
}
try {
$this->pdo->prepare("DELETE FROM thesis_supervisors WHERE thesis_id = ?")->execute([$thesisId]);
$stmt = $this->pdo->prepare("
INSERT INTO thesis_supervisors (thesis_id, supervisor_id, role, is_external, supervisor_order)
VALUES (?, ?, ?, ?, ?)
");
foreach ($juryMembers as $order => $member) {
$name = trim($member['name'] ?? '');
if ($name === '') continue;
$supervisorId = $this->findOrCreateSupervisor($name);
$role = in_array($member['role'], ['president', 'promoteur', 'lecteur'])
? $member['role'] : 'promoteur';
$isExternal = isset($member['is_external']) ? (int)$member['is_external'] : 0;
$stmt->execute([$thesisId, $supervisorId, $role, $isExternal, $order + 1]);
}
if (!$alreadyInTransaction) {
$this->pdo->commit();
}
} catch (\Throwable $e) {
if (!$alreadyInTransaction && $this->pdo->inTransaction()) {
$this->pdo->rollBack();
}
throw $e;
}
}