auth/middleware/ProviderRoute.js

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

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

/**
 * Many auth routes specify the name of a particular auth provider to use.
 * This middleware looks up the provider by name and injects it into the request.
 * @extends module:libflitter/middleware/Middleware~Middleware
 */
class ProviderRoute extends Middleware {
    /**
     * Defines the services required by this middleware.
     * @returns {Array<string>}
     */
    static get services() {
        return [...super.services, 'configs', 'auth']
    }

    /**
     * Runs the middleware test. If the session is authenticated, injects
     * the user's associated auth provider into 'request.auth_provider'.
     *
     * Otherwise, if there is a string in 'request.params.provider', the corresponding
     * auth provider will be injected. If all else fails, the default auth provider is
     * used.
     *
     * @param {express/request} req - the request
     * @param {express/response} res - the response
     * @param {function} next - the next function in the stack
     * @param {string} [provider_name] - optionally, the base provider name
     * @returns {Promise<*>}
     */
    async test(req, res, next, provider_name) {

        // If a user is signed in, the provider should always be the one associated
        // with their user, regardless of overrides
        if ( req.is_auth ) provider_name = req.user.provider
        else provider_name = req.params.provider ? req.params.provider : false

        const provider = this.auth.get_provider(provider_name)
        
        if ( !provider ) {
            return res.error(404, {reason: 'An auth provider with that name could not be found.'})
        }
        
        req.auth_provider = provider

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

}

module.exports = ProviderRoute