auth/middleware/KeyAction.js

/**
 * @module flitter-auth/middleware/KeyAction
 */

const Middleware = require('libflitter/middleware/Middleware')

/**
 * Middleware for processing key actions.
 * @extends module:libflitter/middleware/Middleware~Middleware
 */
class KeyAction extends Middleware {
    /**
     * Defines the services required by this middleware.
     * @returns {Array<string>}
     */
    static get services() {
        return [...super.services, 'models']
    }

    /**
     * Looks up the key action from the request params' "key"
     * property and injects it into the session. If necessary,
     * authenticates the user and injects them as well.
     *
     * Will send a 401 denial if the key action or user are invalid.
     *
     * @param {express/request} req - the request
     * @param {express/response} res - the response
     * @param {function} next - the next function in the stack
     * @param {*} [args = {}] - optional arguments
     * @returns {Promise<void>}
     */
    async test(req, res, next, args = {}){
        const KeyAction = this.models.get('auth:KeyAction')

        const lookup_key = req.params.key ? req.params.key : (req.session.key_action_key ? req.session.key_action_key : false)
        if ( !lookup_key ) return req.security.deny()

        const action = await KeyAction.lookup({ key: lookup_key })
        if ( !action ) return req.security.deny()

        if ( action.user_id ) {
            const user = await action.user()
            if ( req.user && String(req.user._id) !== String(user._id) ) return req.security.kickout()
            if ( action.auto_login ) {
                if ( req.user ) {
                    action.did_auto_login = false
                } else {
                    const provider = await req.security.provider()
                    await provider.session(req, user)
                    action.did_auto_login = true
                }
            }
        }

        action.used = true
        await action.save()

        req.key_action = action
        req.session.key_action_key = String(action.key)

        /*
         * Call the next function in the stack.
         */
        next()
    }
}

module.exports = exports = KeyAction