const moment = require('moment');

jwt = require("jsonwebtoken");

const roles = [
    'ADMIN',
    'PARENT',
    'ELEVE',
    'ADMINISTRATION',
    'ENSEIGNANT',
    'SECRETARIAT'
]
module.exports = async function (req, res, next) {
    let ouestDate = moment.utc(new Date()).utcOffset('+01:00');
    let date = ouestDate.format('YYYY-MM-DD');
    let heure = ouestDate.format('HH:mm:ss');
    let username = null;
    let log = async (status, errorMessage) => {
        await ActivityLogs.create({
            date,
            heure,
            username,
            action: "API_ACCESS",
            status,
            errorMessage,
            device: "API",
            location: req.originalUrl
        });
    };
    //console.log('isAuthorize', req.headers.authorization || req.headers.Authorization || req.headers['authorization'])
    let api_key = req.headers.authorization || req.headers.Authorization || req.headers['authorization']
    //Check if authorization header is present
    if (!api_key) {
        if (req.headers.adminkey === 'PERLENE@GESTION') {
            await log("success", null);
            return next();
        }
        await log("failed", "No Authorization header was found");
        return res.status(401)
            .json({
                code: 'authorizationIsRequired',
                message: 'No Authorization header was found'
            });
    }

    //authorization header is present
    let parts = req.headers.authorization.split(' ');
    if (parts.length !== 2 || !/^Bearer$/i.test(parts[0])) {
        await log("failed", "Format is Authorization: Bearer [token]");
        return res.status(401)
            .json({
                code: 'invalidFormatTokenError',
                message: 'Format is Authorization: Bearer [token]'
            });
    }
    let scheme = parts[0];
    let credentials = parts[1];
    if (!credentials) {
        await log("failed", "Token is missing");
        return res.status(401).json({
            code: 'invalidToken',
            message: 'Token is missing'
        });
    }
    let token = await Token.find({
        token_salt: credentials
    }).then(_.first)
    if (!token) {
        await log("failed", "Token not found in database");
    }
    if (!token) {
        await log("failed", "Authentification du token échoué");
        return res.status(401)
            .json({
                code: 'tokenNOtMatch',
                message: 'Authentification du token échoué'
            });
    }
    // Avant la vérification JWT, ajoutez :
    console.log("Verifying token:", {
        // received: credentials,
        //stored: token.token_salt,
        match: credentials === token.token_salt
    });

    if (credentials !== token.token_salt) {
        await log("failed", "Token does not match stored value");
        return res.status(401).json({
            code: 'tokenMismatch',
            message: 'Token does not match stored value'
        });
    }

    try {
        const decoded = jwt.verify(credentials, sails.config.custom.secret);
        let token = await Token.findOne({ token_salt: credentials });
        if (!token) {
            await log("failed", "Token not found in database (after JWT verify)");
            return res.status(401).json({
                code: 'tokenNOtMatch',
                message: 'Authentification du token échoué'
            });
        }
        let user = await Utilisateurs.findOne(decoded.data.id);
        if (!user) {
            await log("failed", "User not found");
            return res.status(401).json({
                code: 'ACCESS_DENIED',
                message: 'User not found'
            });
        }
        username = user.login;
        roles.forEach(role => {
            req[`${role}`] = (role === user.typeUser);
        });
        req.isAutenticated = true;
        req.token = {
            id: user.id,
            user,
            role: user.typeUser,
            permissions: []
        };
        await log("success", null);
        return next();
    } catch (err) {
        console.error("Erreur vérification token:", err);
        let errorMessage = (err && err.message) || 'Erreur lors de la vérification du token';
        if (err.name === "TokenExpiredError") {
            await log("failed", "Token expiré");
            return res.status(498).json({
                code: 'tokenExpiredError',
                message: 'Le token est expiré veuillez vous reconnecter'
            });
        }
        await log("failed", errorMessage);
        return res.status(500).json({
            code: 'internalError',
            message: 'Erreur lors de la vérification du token',
            error: err.message
        });
    }
};
