繁体   English   中英

在 express.js 中使用一组中间件

[英]Use an array of middlewares at express.js

我正在尝试使用一系列中间件。 好吧,更像是函数名和数组的组合。

而不是:

router.post('/editPassword', validate, changePassword, sendConfirmation);

我想要类似的东西:

router.post('/editPassword', validate, [changePassword, sendConfirmation] ); 

那看起来像:

router.post('/editPassword', validate, doAction ); 

其中doAction将是这样的数组:

var doAction = [
   //equivalent of changePassword
   function(req, res, next){
      //whatever
      next();
   },

   //equivalent to the previous sendConfirmation
   function(req, res, next){
      //whatever
   }
]

但它似乎失败并在doAction的第一个函数中的next()之后返回到validate步骤。

我正在寻找一种简化中间件链接的方法,包括一些同名的中间件步骤。

我认为您希望它看起来那样的原因不仅是为了让它看起来像样,而且是为了能够重用其他中间件。 在这种情况下,您可以创建一个中间件来运行所有其他中间件来为您进行检查,并且只有在所有验证都成功时才调用下一个函数。

var express = require('express');
var app = express();

function middleware1(req, res, next) {
    if(req.query.num >= 1) {
        next();
    } else {
        res.json({message: "failed validation 1"});
    }
}

function middleware2(req, res, next) {
    if(req.query.num >= 2) {
        next();
    } else {
        res.json({message: "failed validation 2"});
    }
}

function middleware3(req, res, next) {
    if(req.query.num >= 3) {
        next();
    } else {
        res.json({message: "failed validation 3"});
    }
}

function combination(req, res, next) {
    middleware1(req, res, function () {
        middleware2(req, res, function () {
            middleware3(req, res, function () {
                next();
            })
        })
    })
}


app.get('/', combination, function (req, res) {
  res.send('Passed All Validation!');
})

app.listen(3000, function () {
  console.log('Example app listening on port 3000!')
})

您可以通过运行它然后查看http://localhost:3000/?num=3来测试这个应用程序,将值 3 更改为较小的数字,或删除 num 参数。

我不确定这是否是正确的方法,但这就是我处理其他项目的方式。 让我知道你的想法。

注意:请参阅用例的注释。 @robertklep 可能有更好的解决方案,具体取决于您希望如何使用中间件

最新版本的 Express 可以处理这个问题:

function logOriginalUrl (req, res, next) {
  console.log('Request URL:', req.originalUrl)
  next()
}

function logMethod (req, res, next) {
  console.log('Request Type:', req.method)
  next()
}

var logStuff = [logOriginalUrl, logMethod]
app.get('/user/:id', logStuff, function (req, res, next) {
  res.send('User Info')
})

您可以从此链接查看更多信息

多搜索一下^^:比以前的答案不那么难看,更容易理解

https://github.com/blakeembrey/compose-middleware

请注意,您没有在validate中间件中执行此操作(相当于):

function middleware(req, res, next) {
  if (someCondition) {
    console.log('some condition is true');
    next();
  }
  console.log('some condition is false');
  res.status(400).end();
}

这里的目的是在调用next之后其余的代码不会被执行,但它会。 next没有什么特别的,所以当你调用它时,它返回后中间件代码继续运行(导致“某些条件为真”“某些条件为假”都被记录)。

这就是为什么你经常看到这个:

  if (someCondition) {
    console.log('some condition is true');
    return next();
    // Or, alternatively:
    // next();
    // return;
  }

return导致中间件函数在调用next后返回,所以函数中的其余代码不会被执行。

此功能已作为数组或中间件内置在 express 中:

let combined = express.Router()
    .use(
        [
            middleware1,
            middleware2,
            middleware3,
        ],
    );
let combined = express.Router()
    .use(
        middleware1,
        middleware2,
        middleware3,
    );

完整示例

"use strict";

let Http = require("http");
let Express = require("express");

let server = Express();
let app = Express.Router();
let combined = Express.Router();

combined.use(
    function (req, res, next) {
        console.log("huzzah!");
        next();
    },
    function (req, res, next) {
        res.json({ success: true });
    }
);

function middleware0(req, res, next) {
    console.log('ground zero');
    next();
}

app.get("/combined", middleware0, combined);
server.use("/", app);

Http.createServer(server).listen(3000);

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM