我们相信:世界是美好的,你是我也是。平行空间的世界里面,不同版本的生活也在继续...

express是基于node的容器,它必然也是可以接收浏览器发来的数据的。那么,本文就描述一下,如何解析这些表单数据。使用的是express自带的body-parser中间件。当然,本文的结论是:body-parser存在着天然的缺陷,所以,它可能并不是好的表单处理选择。

苏南大叔:express教程,如何理解post表单解析body-parser中间件? - express-body-parser
express教程,如何理解post表单解析body-parser中间件?(图3-1)

大家好,这里是苏南大叔的平行空间笔记本博客,记录苏南大叔和程序代码的故事。本文描述的是express里面,使用body-parser中间件处理表单数据。测试环境:node@16.14.2express@4.18.2body-parser@1.20.1

表单的几种类型

回顾文章:

可能的表单类型有以下几种类型:

  • application/x-www-form-urlencoded【默认】
  • multipart/form-data 【body-parser不能处理】
  • text/plain【合法不常见】
  • application/json【不合法但常见】
  • text/xml等其他

body-parser

express是如何使用body-parser处理这些类型的数据的呢?body-parser的官方文档:

官方文档里面,强调了并不会处理multipart/form-data类型,因为“due to their complex and typically large nature”,这个就非常尴尬了。

数据类型parser匹配处理方式code
application/x-www-form-urlencodedURL-encoded form body parser.urlencoded({ extended: false })
multipart/form-data缺失不存在
application/jsonJSON body parser.json()
text/plainText body parser.text()
application/octet-streamRaw body parser.raw()

.urlencodedextended参数官方都推荐修改为false。但是却不直接设置为默认。官方这也是很纠结啊,是被谁威胁了么?

苏南大叔:express教程,如何理解post表单解析body-parser中间件? - extend-false
express教程,如何理解post表单解析body-parser中间件?(图3-2)

The extended option allows to choose between parsing the URL-encoded data with the querystring library (when false) or the qs library (when true). The "extended" syntax allows for rich objects and arrays to be encoded into the URL-encoded format, allowing for a JSON-like experience with URL-encoded. For more information, please see the qs library.

Defaults to true, but using the default has been deprecated. Please research into the difference between qs and querystring and choose the appropriate setting.

这些中间件处理的结果,放在客户端的requestbody里面。例如:

req.body

全局引入中间件【不推荐】【请根据实际情况引入】

虽然各大教程和官方文档里面,都在推荐你使用app.use()引入body-parser。但是,鉴于body-parser并不能处理所有的数据类型。引入其它中间件的时候,可能会出现冲突的情况。所以,苏南大叔并不建议您使用下面的代码:

var express = require('express')
var bodyParser = require('body-parser')
var app = express()
// parse application/x-www-form-urlencoded
app.use(bodyParser.urlencoded({ extended: false }))

// parse application/json
app.use(bodyParser.json())

app.use(bodyParser.text())
app.use(bodyParser.raw())

路由引入中间件【个人推荐】【请根据实际情况引入】

中间件可以全局引入,也可以在路由中引入。所以,个人觉得在路由中引入,会更加具有明确的目标性。毕竟处理确定的url的时候,大概率会很明确的知晓提交的数据类型。

var express = require('express')
var bodyParser = require('body-parser')
var app = express()
// create application/json parser
var jsonParser = bodyParser.json()

// create application/x-www-form-urlencoded parser
var urlencodedParser = bodyParser.urlencoded({ extended: false })

// POST /login gets urlencoded bodies
app.post('/login', urlencodedParser, function (req, res) {
  res.send('welcome, ' + req.body.username)
})

// POST /api/users gets JSON bodies
app.post('/api/users', jsonParser, function (req, res) {
  // create user in req.body
})

苏南大叔:express教程,如何理解post表单解析body-parser中间件? - body-parser-middlewares
express教程,如何理解post表单解析body-parser中间件?(图3-3)

处理未知type类型

官方提供了处理未知类型的能力,直接修改type参数即可。当然,前提是你有这个需要。

var express = require('express')
var bodyParser = require('body-parser')
var app = express()
// parse various different custom JSON types as JSON
app.use(bodyParser.json({ type: 'application/*+json' }))

// parse some custom thing into a Buffer
app.use(bodyParser.raw({ type: 'application/vnd.custom-type' }))

// parse an HTML body into a string
app.use(bodyParser.text({ type: 'text/html' }))

结束语

根据官方文档提示,这个官方的body-parser,似乎有很多难言之隐。如果你的要求不高,并且不处理multipart/form-data类型(不上传文件)的话,这个body-parser就足够了。

如果本文对您有帮助,或者节约了您的时间,欢迎打赏瓶饮料,建立下友谊关系。
本博客不欢迎:各种镜像采集行为。请尊重原创文章内容,转载请保留作者链接。

 【福利】 腾讯云最新爆款活动!1核2G云服务器首年50元!

 【源码】本文代码片段及相关软件,请点此获取更多信息

 【绝密】秘籍文章入口,仅传授于有缘之人   express