@koa/multer
该模块是koa-multer的一个分支,koa-multer是koa社区中使用最广泛的multer中间件。由于缺乏维护,因此已将其分叉给Koa官方组织
安装:
// @koa/multer 依赖于 multer,安装时要将 multer 一并安装上
npm i --save @koa/multer multer
使用:
const multer = require('@koa/multer') // 引入
const upload = multer() // 加载multer
文件信息:
每个传到后台的文件都有如下信息:
fieldname | Field name 由表单指定 | |
originalname | 用户计算机上的文件的名称 | |
encoding | 文件编码 | |
mimetype | 文件的 MIME 类型 content-type | |
size | 文件大小(字节单位) | |
destination | 保存路径 | |
filename | 保存在 destination 中的文件名 | |
path | 已上传文件的完整路径 | |
buffer | 一个存放了整个文件的 Buffer |
options:
multer(options)中的参数:
属性:
1、dest - 上传文件保存到哪,如果省略options,文件将保存在内存中,不会写入磁盘。
const upload = multer({
dest: './static/xxx'
})
2、storage - 与属性dest一样,但是强大一些。
如果你想在上传时进行更多的控制,你可以使用 storage
选项替代 dest
。Multer 具有 DiskStorage
和 MemoryStorage
两个存储引擎;另外还可以从第三方获得更多可用的引擎。
const multer = require('@koa/multer')
const storage = multer.diskStorage({ // multer调用diskStorage可控制磁盘存储引擎
destination: function(req, file, cb){
cb(null, './static/images')
},
filename: function(req, file, cb){
cb(null, file.fieldname + '-' + Date.now()) // 文件名使用cb回调更改,参数二是文件名,为了保证命名不重复,使用时间戳
}
})
const upload = multer({
storage
})
/*
上边file 输出:
{ fieldname: 'file',
originalname: 'xm.jpg',
encoding: '7bit',
mimetype: 'image/jpeg' }
*/
tips:
如果你未创建文件上传需要保存的文件夹或文件,使用dest时,会根据dest配置的路径自动创建,但是如果使用storage,必须确保文件夹或文件是否存在,否则会报错!
3、limits
指定一些数据大小(做限制的),object类型
const limits = {
fields: 10,//非文件字段的数量
fileSize: 500 * 1024,//文件大小 单位 b
files: 1//文件数量
}
const upload = multer({
storage,
limits
})
常用key如下:
Key | Description | Default |
---|---|---|
fieldNameSize | field 名字最大长度 | 100 bytes |
fieldSize | field 值的最大长度 | 1MB |
fields | 非文件 field 的最大数量 | 无限 |
fileSize | 在 multipart 表单中,文件最大长度 (字节单位) | 无限 |
files | 在 multipart 表单中,文件最大数量 | 无限 |
tips:
设置 limits 可以帮助保护你的站点抵御拒绝服务 (DoS) 攻击。
一个完整的例子:
单文件上传:
upload.single('file') 单文件上传的中间件,参数file是前端上传的文件字段名,文件信息存放在上下文中的file中。
const Koa = require('koa')
const Router = require('koa-router')
const bdparser = require('koa-bodyparser')
const multer = require('@koa/multer') // 引入
const app = new Koa()
const router = new Router()
app.use(router.routes())
// 配置上传的文件目录及文件名
const storage = multer.diskStorage({
destination: function(req, file, cb){
cb(null, './static/images')
},
filename: function(req, file, cb){
cb(null, file.fieldname + '-' + Date.now())
}
})
const upload = multer({ // 源码中multer是一个函数,所以需要执行
storage: storage
})
// 单文件上传中间件挂在到路由上,了解koa源码会知道执行顺序是至左向右
// upload.single('file') 参数file是前端上传的文件字段名 element上传组件中的name
// 注意,这个字段名前后端必须一致
router.post('/upload', upload.single('file'), ctx => {
ctx.body = 'success';
})
多文件上传:
1、upload.array('file', maxCount) 多文件上传的中间件,参数二是上传文件最大数量,文件信息存放在上下文中的files中。
// 配置上传的文件目录及文件名
const storage = multer.diskStorage({
destination: function(req, file, cb){
cb(null, './static/images')
},
filename: function(req, file, cb){
cb(null, file.fieldname + '-' + Date.now())
}
})
const upload = multer({ // 源码中multer是一个函数,所以需要执行
storage: storage
})
// upload.array(global.fileName, maxCount) 参数二为上传文件的最大数量
router.post('/upload', upload.array('file', maxCount), ctx => {
// ctx.files 可获取到上传的所有文件信息,type -> Array
ctx.body = 'success';
})
// ctx.files
[ { fieldname: 'file',
originalname: 'xm.jpg',
encoding: '7bit',
mimetype: 'image/jpeg',
destination: './static/images',
filename: 'file-1582378596464',
path: 'static\\images\\file-1582378596464',
size: 961027 } ]
2、upload.fields
([{name: 'xxx', maxCount: Number},{}, ··· ···])
多文件上传的中间件,参数是一个数组,里边可配置多个对象:
name -> 是前端上传的文件字段名(可以配置不同的字段名);
maxCount -> 上传文件的最大数量。
router.post('/upload', upload.fields([
{name: 'file', maxCount: 10},
{name: 'file1', maxCount: 10},
]), ctx => {
console.log('fileNames', ctx.files)
ctx.body = 'done';
})
// 输出结果
{
file:[ { fieldname: 'file',
originalname: 'uni-app登录账号和密码.txt',
encoding: '7bit',
mimetype: 'text/plain',
destination: './static/images',
filename: 'file-1582381660590',
path: 'static\\images\\file-1582381660590',
size: 26 }
]
}
封装上传组件:
const multer = require('@koa/multer')
// fileName 文件名,默认为文件字段名 + 时间戳
// filePath 文件存放路径,必填
function uploads(filePath, fileName) {
if(filePath){
const storage = multer.diskStorage({
destination: function(req, file, cb){
cb(null, filePath)
},
filename: function(req, file, cb){
const defaultFileName = fileName ? fileName : file.fieldname
cb(null, `${defaultFileName} - ${Date.now()}`)
}
})
return upload = multer({
storage: storage
})
}else{
throw new Error('上传文件的存放路径未设置!')
}
}
module.exports = {
uploads
}
// 调用
const upload = uploads('./static/images') // 导出配置好的文件路径及名
router.post('/upload', upload.fields([
{name: 'file', maxCount: 10},
{name: 'file1', maxCount: 10},
]), ctx => {
console.log(ctx.files)
ctx.body = 'done';
})