Kostas Drak
Kostas Drak

Reputation: 3260

Check dynamic route express js

I have some routes for example /login/:provider/:id and when the request is executed it gets something like /login/provider1/123. Everything fine so far but the problem arise when I want to have certain routes without authentication for my middleware.

So far I have tried like this:

public static getString(value: String): String {
        let values = value.split('/');
        if (values.length <= 2) return value;
        return values.slice(0, values.length - 1).reduce(((previousValue, currentValue) => {
            return previousValue + "/" + currentValue;
        }));
    }

but it is not very generic and does not catch all the cases.

What it should match the original route is:

/login/anything/anything

So I take this route: /login/:provider/:id that has 3 segments: [login, provider, id] so anything that starts from /login and has same number of segments should match.

and it should not match anything without same length of segments.

My question is: Is there any specific way of getting the original route without looping after the request made? Is what I am asking possible through regexp?

Upvotes: 1

Views: 586

Answers (2)

Kostas Drak
Kostas Drak

Reputation: 3260

The only dirty solution that I came up with is this:

public static doesNotRequireAuth(value: String): boolean {
        let delimiter = "/";
        let segments = value.split(delimiter);
        let conditionMet = false;
        getNoAuthRoutes().forEach((item) => {
            let itemSegments = item.split(delimiter);
            if (segments[1] === itemSegments[1] && segments.length === itemSegments.length) {
                conditionMet = true;
                return;
            }
        });
        return conditionMet;
    }

where the getNoAuthRoutes() is a Set<String>.

Hope it helps someone!!!

Upvotes: 0

Ahmet Can G&#252;ven
Ahmet Can G&#252;ven

Reputation: 5462

I think you need custom validators for your route.

You can create routers.

var app = express();
var router = express.Router();

router.param(function(param, validator) {
    return function(req, res, next, val) {
        // You have full access to req. So you can get anything from it.
        if (validator(val)) {
            next(); //validator success no need for authorization.
        } else {
            if (req.headers.Authentication) {
                next() //Validator failed but we have token in header and it is valid.
            } else {
                res.sendStatus(403); //Validator failed and token does not exists.
            }
        }
    }
});


router.param('provider', function(candidate) {
    return candidate === 'myprovider' //Provider condition that will bypass authorization.
});

router.get('/login/:provider/:id', function (req, res) { //register the route
  res.send('OK');
});

app.use(router);

Edit 2 (Another try):

app.all('/:id/:name', (req, res, next) => {
  console.log(req.params);
  next();
});

This will match only this type of routes. And it will work before them so you have access to every param you need.

Upvotes: 1

Related Questions