当多条路径匹配时,Express如何知道使用哪条路由器路径?

人气:711 发布:2022-10-16 标签: angularjs node.js mean-stack express mongodb

问题描述

假设有2个router.route(),例如:

router.route('/app/:id').get(funtion(req, res, next){
    console.log("id route")
});

router.route('/app/:username').get(funtion(req, res, next){
    console.log("user route")
});

当调用GET /app/nsuzuki时,它使用哪个router.route(),为什么?

推荐答案

要完全理解这一点,请阅读文档:http://expressjs.com/api.html#router.METHOD

快速路由如何捕获路径

当您使用:param作为路径的一部分时,它与/*之类的所有内容匹配,捕获的值存储在req.params.param中。

当您有多个规则时,第一个注册的规则是第一个选中的规则。它根据每个规则检查每个调用,直到找到匹配项。如果调用next()时未向其传递任何值,则它将查找下一个匹配项(要么在同一路由中,要么继续到下一个中间件)。

因此这三个规则都将运行

var handleRoute = function(req, res, next){
   console.log(req.path + ' ' + req.params.id + ' ' + req.params.user + ' ' + req.params[0]);
   next();
}

route.route('/user/:id').get(handleRoute);
route.route('/user/:user').get(handleRoute);
route.route('/user/*').get(handleRoute);

当我请求/user/foobar时,我将看到以下输出(作为客户端可能会出现错误,因为我从未响应:p)

/user/foobar foobar undefined undefined
/user/foobar undefined foobar undefined
/user/foobar undefined undefined foobar

它将同时命中这三个参数,但每个参数的上下文不同。

如何使用正则表达式捕获路径模式

如果您想为id(假设为所有数字)和用户名(所有字母)捕获单独的路由,您可以执行以下操作:

var handleRoute = function(tag) {
  return function(req, res, next) {
    console.log(tag + ' ' + req.path + ' -> ' + req.params[0]);
    res.status(200)
      .json({
        success: 'yay!'
      });
  };
};

route.route(/^/user/([0-9]+)$/i)
  .get(handleRoute('id'));
route.route(/^user/([A-Za-z]+)$/i)
  .get(handleRoute('user'));
route.route('/user/*')
  .get(handleRoute('catch all'));

注意我的捕获组周围的截肢。如果没有此参数,params将为空。它自动捕获字符串中只有*的内容,因为他们是好人。当我对这三种不同的类型运行时,我将获得以下输出。

id /user/123 -> 123
user /user/user -> user
catch all /user/user.1 -> user.1

所有这些都解释了,您正在为一些错误侵扰您的系统的媒介敞开大门。可能需要考虑您的URL模式。

457