/**
 * @file Ce fichier définit le routage d'URL au sein de l'interface du _backend_.
 * Il définit la page de connexion `/`, le panneau administrateur `/admin` et l'API REST \(`/db/:table?`)
 * permettant de consulter la base de donnée interne à Sigma, via des requêtes construites avec Knex.
 * @author manifold
 * 
 * Les res.redirect() sont censes supporter les paths relatifs (et donc pas besoin de repreciser /adminview/* a chaque fois)
 * mais ca marche visiblement pas... Donc j'ai mis les paths absolus dans les res.redirect().
 */
import { Router } from 'express';
import knex from '../../db/knex_router';
import passport from 'passport';
import flash from 'connect-flash';
import { ensureLoggedIn } from 'connect-ensure-login';

import favicon from 'serve-favicon';

app.use(favicon(path.resolve('./', 'assets', 'favicon.ico')));
// specifies path to static assets. ......je comprends pas ce que c'est. TODO
app.use('/assets', express.static(path.resolve('./', 'assets')));

// router: an Express router. https://expressjs.com/en/4x/api.html#router
// = a "sub-middleware stack", a “mini-application" inside the main application
const router = Router();

router.use(flash());

let port = process.env.PORT || 3000;


/**
 * * @desc Le login se fait en POST. Faire un GET à la racine / renvoie sur
 * /login ou sur /admin selon que l'utilisateur est connecté ou non.
 */

router.get('/', function (req, res) {
    res.redirect('/adminview/admin');
});

router.get('/avlogin', function (req, res) {
    // lets pug render src/views/login.pug with specified attributes
    res.render('login', {
        title: 'Login', port: port,
        errorMessage: req.flash('error') //hawkspar->manifold VSCode râle ici pr moi ; un commentaire ?
    });
});

router.get('/admin',
    ensureLoggedIn('/adminview/avlogin'),
    function (req, res) {
        let userName;
        // Une erreur a ce stade peut etre triggered si req.user n'existe pas
        // mais pour autant on est assures que la personne est bien authentifiee
        // donc on laisse passer sans déclencher d'erreur 500
        try {
            let user = req.user;
            userName = user.uid;
        } catch (err) {
            userName = "No one";
        }
        res.render('home', { title: 'Home', port: port, userName: userName });
    }
);

router.post('/avlogin',
    passport.authenticate('ldapauth', {
        successRedirect: '/adminview/admin',
        failureRedirect: '/adminview/avlogin',
        failureFlash: true
    }
        // on a besoin de faire un callback apres le passport.authenticate car
        // on souhaite garde l'information user.dn et body.password qq part.
        // TODO: essayer de garder ces informations plus proprement...
        // EDIT: en fait apparemment on a pas besoin de ces informations du tout
        /*
        function (req, res) {
            req.session.dn = req.user.dn;
            req.session.password = req.body.password;
    
            if (req.session.returnTo !== undefined) {
                res.redirect(req.session.returnTo); //TODO: <- euh ok ca marche mais c'est quoi ca?
            } else {
                res.redirect("/admin");
            }
        }
        */
    )
);

router.post('/avlogout', function (req, res) {
    req.logout();
    res.redirect('/adminview');
});





// Je pense qu'on ferait mieux d'utiliser ca
// https://expressjs.com/en/4x/api.html#router.route
router.get('/db?', function (req, res) {
    let table_name = req.query.table;
    let columns = req.query.columns;

    res.redirect(`/adminview/db/${table_name}?columns=${columns}`);
});

/**
 * @function Knex API: Get table
 * @summary Effectue une requête pour une table dans la BDD
 * @argument {string} table_name - La table voulue par l'utilisateur.
 */
router.get('/db/:table_name?', function (req, res) {

    // get columns from query
    let columns;
    if (req.query.columns) {
        columns = req.query.columns.split(',');
    } else {
        columns = null;
    }
    console.log(columns);

    knex.select(columns).from(req.params.table_name).then(function (table) {
        res.setHeader("Content-Type", "application/json");
        res.write(JSON.stringify(table, null, 2));
        res.end();
    }, function () {
        res.status(400);
        res.render('error', {
            status: res.statusCode,
            error_message: "Bad request: can't find table " + req.params.table_name
        });
        res.end();
    }
    );
});

/**
 * @function Error_404_catcher
 * @summary Catche les requêtes en dehors des URL acceptées
 */
router.use((req, res, next) => {
    let err = new Error('Not found');
    res.status(404);
    next(err);
});

/**
 * @function Error_404_handler
 * @summary Gère les erreurs 404
 */
router.use((err, req, res, next) => {
    console.log("adminview: Entering error handler");
    res.locals.message = err.message;
    console.log(err.message);

    res.status(err.status || 500);
    let error_message = res.statusCode == 404 ? 'Not found.' : 'Internal server error.';
    res.render('error', {
        status: res.statusCode,
        error_message: error_message
    });
});

export default router;