在用express开发时,有时候我们需要接收客户端上传的文件,express如果不借助第三方包处理上传文件比较复杂,所以我们使用formidable这个npm包。
formidable这个npm包是做什么用的呢?其官网解释如下:
A Node.js module for parsing form data, especially file uploads.
官网实例代码如下:
代码语言:javascript复制const express = require('express');
const formidable = require('formidable');
const path = require('path');
const fs = require('fs');
const app = express();
app.post('/api/upload', (req, res, next) => {
const form = formidable({ multiples: true,uploadDir: path.join(__dirname,'../..',"imgs") });
form.parse(req, (err, fields, files) => {
if (err) {
next(err);
return;
}
console.log(files);
const oldpath = files.img.path;
const newname = Date.now() files.img.name
const newpath = path.join(path.dirname(oldpath),newname);
console.log(files);
fs.rename(oldpath,newpath,(err)=>{
if(err) throw err;
res.send({src:`/img/${newname}`})
})
});
});
app.listen(3000, () => {
console.log('Server listening on http://localhost:3000 ...');
});
从代码中我们可以看出使用formidable非常简单,只需要如下几个步骤:
1、引入formidable包
2、在需要处理上传文件的路由回调函数中,new一个fromidable对象form,这里需要传递一些配置参数,后面再讲
3、调用from的parse方法解析req对象,因为客户端上传的文件全部在req对象上,我们需要将其解析出来
4、解析完成后我们得到了fields和files两个对象,fields是上传的文本信息,files是文件信息。
我么将files打印出来,观察一下其数据结构:
代码语言:javascript复制{
img: File {
_events: [Object: null prototype] {},
_eventsCount: 0,
_maxListeners: undefined,
size: 68074,
path: '/Users/admin/Documents/work4/aliyun_center/imgs/upload_318c312895efe1e179289e5d3c98c401',
name: '1.jpeg',
type: 'image/jpeg',
hash: null,
lastModifiedDate: 2020-08-07T01:14:42.716Z,
_writeStream: WriteStream {
_writableState: [WritableState],
writable: false,
_events: [Object: null prototype] {},
_eventsCount: 0,
_maxListeners: undefined,
path: '/Users/admin/Documents/work4/aliyun_center/imgs/upload_318c312895efe1e179289e5d3c98c401',
fd: null,
flags: 'w',
mode: 438,
start: undefined,
autoClose: true,
pos: undefined,
bytesWritten: 68074,
closed: false
}
}
}
我们看到files文件的一个属性是img,为什么是img呢?这是前端在上传文件时为这个文件设置的name值,这样的话后端根据这个name值获取对应的文件。
还有从这个文件中我们看出这个文件的路径path,观察path发现图片文件没有后缀名,如何解决呢?看第五步
5、利用fs模块的rename方法将文件重命名,新名称添加相应的后缀
6、用res.send将文件地址返回给前端用户。
至此完成文件上传。
formidable在实例化的时候可以设置对个参数,其中常用的几个简介如下:
代码语言:jsx复制options.encoding {string} - default 'utf-8'; sets encoding for incoming form fields,
options.uploadDir {string} - default os.tmpdir(); the directory for placing file uploads in. You can move them later by using fs.rename()
options.keepExtensions {boolean} - default false; to include the extensions of the original files or not
options.maxFileSize {number} - default 200 * 1024 * 1024 (200mb); limit the size of uploaded file.
options.maxFields {number} - default 1000; limit the number of fields that the Querystring parser will decode, set 0 for unlimited
options.maxFieldsSize {number} - default 20 * 1024 * 1024 (20mb); limit the amount of memory all fields together (except files) can allocate in bytes.
options.hash {boolean} - default false; include checksums calculated for incoming files, set this to some hash algorithm, see crypto.createHash for available algorithms
options.multiples {boolean} - default false; when you call the .parse method, the files argument (of the callback) will contain arrays of files for inputs which submit multiple files using the HTML5 multiple attribute. Also, the fields argument will contain arrays of values for fields that have names ending with '[]'.
这里面需要注意的是multiples这个属性,如果要上传多张文件,multiples必须设置为true,前端的input必须也同时这是multiples
这个属性,不然不会触发上传多张文件。
formidable还有好多其他好玩的功能,但是就上传文件来说,我文中的介绍基本就够了。
以上便是express和formidable简单的处理文件上传的案例,希望对你有所帮助。