Express 官网文档翻译-3.3-使用中间件
使用中间件#
Express 框架是一个由路由和中间件构成的 web 开发框架,它内置的功能很少:Express 应用程序本质上是一系列中间件函数调用。
中间件 函数本质上是一些可以在应用的请求 - 响应周期内,访问 请求对象 (req
),响应对象 (res
),和 下一个中间件函数的函数。下一个中间件函数通常由变量 next
表示。
中间件函数可以执行下面这些任务:
- 执行一些逻辑代码。
- 改变请求和响应对象。
- 结束请求 - 响应周期。
- 在执行栈中调用下一个中间件。
如果当前的中间件函数没有结束掉请求 - 响应周期,它必须调用 next()
把控制权传递给下一个中间件函数。否则,请求将会被一直处于挂起状态。
Express 应用程序可以使用以下类型的中间件:
你可以在可选的路径上加载应用级和路由级中间件。您还可以在某个装载点通过创建子堆栈的形式同时加载一系列中间件。
应用级中间件#
通过使用 app.use()
和 app.METHOD()
可以在 app 对象 的一个实例上绑定应用级中间件,其中 METHOD
是指 HTTP 请求的方法,中间件的处理器函数对应是小写形式。
下面这个例子是一个没有装载路径的中间件函数。应用每接受到一个请求,这个中间件都会执行一次。
var app = express()
app.use(function (req, res, next) {
console.log('Time:', Date.now())
next()
})
下面这个例子是一个装载在路径 /user/:id
上的中间件函数。指向路径 /user/:id
的任何 HTTP 请求都会触发并执行这个中间件函数。
app.use('/user/:id', function (req, res, next) {
console.log('Request Type:', req.method)
next()
})
下面这个例子是一个路由和它的处理器函数(中间件系统)。这个中间件处理指向路径 /user/:id
的 GET 请求。
app.get('/user/:id', function (req, res, next) {
res.send('USER')
})
下面的例子是关于如何在一个路径下加载一系列中间件函数。它展示了一个中间件子堆栈,发送到 /user/:id
路径下的任何类型的 HTTP 请求信息都会被打印出来。
app.use('/user/:id', function (req, res, next) {
console.log('Request URL:', req.originalUrl)
next()
}, function (req, res, next) {
console.log('Request Type:', req.method)
next()
})
路由处理器允许你在同一个路径上定义多个路由。下面的例子中在 /user/:id
路径上为 GET 请求定义了两个路由。定义第二个路由不会引起任何问题,但是它永远不会被调用,因为第一个路由结束了请求 - 响应周期。
这个例子展示了 /user/:id
路径下 GET 请求的中间件子执行栈。
app.get('/user/:id', function (req, res, next) {
console.log('ID:', req.params.id)
next()
}, function (req, res, next) {
res.send('User Info')
})
// ` /user/:id` 路径的处理器,会打印用户 ID
app.get('/user/:id', function (req, res, next) {
res.end(req.params.id)
})
通过调用 next('route')
来传递控制权给下一个路由,可以跳过当前路由中间件执行栈的剩余中间件函数。注意: next('route')
将仅在 app.METHOD()
或 router.METHOD()
函数加载的中间件函数中有效。
这个例子展示了 /user/:id
路径下 GET 请求的中间件子执行栈。
app.get('/user/:id', function (req, res, next) {
// 如果用户 ID 是0,跳转下一个路由
if (req.params.id === '0') next('route')
// 否则传递控制权到执行栈的下一个中间件函数
else next()
}, function (req, res, next) {regula
//发送一个规则的响应
res.send('regular')
})
// ` /user/:id ` 路由的处理器,发送一个特殊的响应
app.get('/user/:id', function (req, res, next) {
res.send('special')
})
路由级中间件#
路由级中间件的用法和应用级中间件相同,只是它绑定到了一个 express.Router()
实例上。
var router = express.Router()
通过使用 router.use () 和 router.METHOD () 函数来加载路由级中间件。
下面例子中的代码使用路由级中间件,复制了上面的应用级中间件系统:
var app = express()
var router = express.Router()
//中间件函数没有路由装载点。下面的代码会在每一个请求下执行。
router.use(function (req, res, next) {
console.log('Time:', Date.now())
next()
})
//这个中中间件的子执行栈会显示发送到 /user/:id 路径下的任何类型的 HTTP 请求信息。
router.use('/user/:id', function (req, res, next) {
console.log('Request URL:', req.originalUrl)
next()
}, function (req, res, next) {
console.log('Request Type:', req.method)
next()
})
// `/user/:id` 路径下 GET 请求的中间件子执行栈
router.get('/user/:id', function (req, res, next) {
// 如果用户 ID 是0,跳转下一个路由
if (req.params.id === '0') next('route')
// 否则传递控制权到执行栈的下一个中间件函数
else next()
}, function (req, res, next) {
//渲染一个规则的页面
res.render('regular')
})
// ` /user/:id ` 路由的处理器,渲染一个特殊的页面
router.get('/user/:id', function (req, res, next) {
console.log(req.params.id)
res.render('special')
})
//在应用上装载路由
app.use('/', router)
如果要跳过当前路由剩余的中间件函数,可以通过调用 next('router')
将控制权从路由器实例中传递回来。
这个例子展示了 /user/:id
路径下处理 GET 请求的中间件子执行栈。
var app = express()
var router = express.Router()
//在路由中检查,并在需要时进行跳出操作
router.use(function (req, res, next) {
if (!req.headers['x-auth']) return next('router')
next()
})
router.get('/', function (req, res) {
res.send('hello, user!')
})
//使用路由中间件和401来处理匹配的路径
app.use('/admin', router, function (req, res) {
res.sendStatus(401)
})
错误处理中间件#
错误处理中间件总是需要 4 个 参数。你必须提供四个参数才能标识它为错误处理中间件函数。即使你不需要
next
对象,也必须指定它来维护签名。否则,next
对象将会被解释为一个普通的中间件,并且无法处理错误。
定义错误处理中间件和定义其他中间件函数的方式一样,除了用四个参数代替三个参数,即使用签名 (err, req, res, next)
:
app.use(function (err, req, res, next) {
console.error(err.stack)
res.status(500).send('Something broke!')
})
想要了解关于错误处理中间件的详细信息,请查看:错误处理。
内置中间件#
从版本 4.x 开始, Express 不再依赖 Connect。之前包含在 Express 中的中间件函数现在剥离为独立模块。请查看 中间件函数列表。
Express 有下列内置的中间件函数:
- express.static 处理静态资源,如 HTML 文件、图像等。
- express.json 解析传入的 content-type 为 application/json 的请求。注意:适用于 Express 4.16.0+
- express.urlencoded 解析传入的 content-type 为 application/x-www-form-urlencoded 的请求。注意:适用于 Express 4.16.0+
第三方中间件#
使用第三方中间件为 Express 应用程序添加功能。
为所需功能安装 Node.js 模块,然后作为应用级中间件或路由级中间件加载到应用程序中。
下面的例子中安装和加载了用于解析 cookie 的中间件函数 cookie-parser
。
$ npm install cookie-parser
var express = require('express')
var app = express()
var cookieParser = require('cookie-parser')
// 加载解析 cookie 的中间件
app.use(cookieParser())
了解更多 Express 常用的中间件,请查看 第三方中间件。
本文中的所有译文仅用于学习和交流目的,转载请务必注明文章译者、出处、和本文链接
我们的翻译工作遵照 CC 协议,如果我们的工作有侵犯到您的权益,请及时联系我们。