Files
ENI-JSAdvanced_10/routes/index.js
2025-12-18 15:21:19 +01:00

109 lines
3.4 KiB
JavaScript

var express = require('express');
var router = express.Router();
var bcrypt = require('bcrypt');
var rateLimit = require('express-rate-limit');
// --- Base de données simulée ---
const db = {
users: [
{
id: 1,
username: 'admin',
password_vulnerable: 'password123',
hashedPassword: bcrypt.hashSync('password123', 12)
}
]
};
/* GET home page */
router.get('/', function(req, res, next) {
res.render('index', { title: 'Express' });
});
// ==========================================================
// ## 👎 DÉMONSTRATION VULNÉRABLE (A07)
// ==========================================================
router.post('/login-vulnerable', (req, res) => {
// !! REPOSE SUR express.json() et express.session() définis dans app.js !!
const { username, password } = req.body;
const user = db.users.find(u => u.username === username);
// FAILLE 1 : Énumération de comptes
if (!user) {
return res.status(404).send('Erreur : Utilisateur non trouvé.');
}
// FAILLE 2 : Stockage et comparaison en clair
if (user.password_vulnerable !== password) {
return res.status(400).send('Erreur : Mot de passe incorrect.');
}
// FAILLE 3 : Fixation de session
req.session.userId = user.id;
req.session.username = user.username;
console.log(`[VULNÉRABLE] Session AVANT login: ${req.sessionID}`);
console.log(`[VULNÉRABLE] Session APRÈS login: ${req.sessionID} (INCHANGÉE)`);
res.send(`Connexion (vulnérable) réussie pour ${user.username} !`);
});
// ==========================================================
// ## DÉMONSTRATION CORRIGÉE (A07)
// ==========================================================
// CORRECTION 4 : Limitation de tentatives (Rate Limiting)
const loginLimiter = rateLimit({
windowMs: 15 * 60 * 1000, // 15 minutes
max: 10, // Limite à 10 tentatives par IP par fenêtre de 15 min
message: 'Trop de tentatives de connexion. Réessayez dans 15 minutes.'
});
// Applique le limiteur uniquement à ce point de terminaison
router.use('/login-securise', loginLimiter);
router.post('/login-securise', async (req, res) => {
// !! REPOSE SUR express.json() et express.session() définis dans app.js !!
const { username, password } = req.body;
const user = db.users.find(u => u.username === username);
// CORRECTION 1 & 2 : Pas d'énumération + Hachage fort
const match = user ? await bcrypt.compare(password, user.hashedPassword) : false;
if (!match) {
return res.status(401).send('Identifiants invalides.');
}
// CORRECTION 3 : Régénération de la session
const oldSessionId = req.sessionID;
req.session.regenerate((err) => {
if (err) {
console.error(err);
return res.status(500).send('Erreur lors de la régénération de session.');
}
req.session.userId = user.id;
req.session.username = user.username;
console.log(`[SÉCURISÉ] Session AVANT login: ${oldSessionId}`);
console.log(`[SÉCURISÉ] Session APRÈS login: ${req.sessionID} (CHANGÉE)`);
res.send(`Connexion (sécurisée) réussie pour ${user.username} !`);
});
});
// --- Point de déconnexion ---
router.get('/logout', (req, res) => {
// !! REPOSE SUR express.session() défini dans app.js !!
req.session.destroy((err) => {
if (err) {
return res.status(500).send('Impossible de se déconnecter.');
}
res.clearCookie('connect.sid'); // Nom par défaut du cookie de session
res.send('Déconnecté avec succès.');
});
});
module.exports = router;