何时在node.js上传脚本中检查文件大小/ mimetype? [英] when to check for file size/mimetype in node.js upload script?
问题描述
我使用express / formidable在node.js中创建了一个上传脚本。它基本上工作,但我想知道在什么时候检查上传的文件e。 G。对于最大文件大小或文件的mimetype是否被允许。
我的程序看起来像这样:
app.post(' /',function(req,res,next){
req.form.on('progress',function(bytesReceived,bytesExpected){
// ... do stuff
}) ;
req.form.complete(函数(err,fields,files){
console.log('\\\
uploaded%s到%s',files.image.filename,files .image.path);
// ...做东西
});
});
在我看来,检查mimetype /文件大小的唯一可行的地方是 complete
事件,我可以可靠地使用文件系统函数获取上载文件的大小 / tmp /
- 但是这似乎是一个不太好的主意,因为:
$ b $ ul
最佳做法是什么为了实现这个?我在node.js中发现了很多文件上传的例子,但似乎没有做我需要的安全检查。
在IRC节点和节点邮件列表的帮助下,
我使用强大的处理文件上传。使用 progress
事件,我可以检查最大文件大小是这样的:
如果(bytesReceived> MAX_UPLOAD_SIZE){
console.log('###错误:FILE TOO LARGE'); $ b $ form.on('progress',function(bytesReceived,bytesExpected){
b}
});
可靠地检查mimetype要困难得多。基本的想法是使用 progress
事件,然后如果足够的文件被上传,使用文件--mime-type $ c $调用并检查该外部命令的输出。简化它看起来像这样:
//包含上传文件的路径,
//被抓取fileBegin事件低于
var tmpPath;
$ b form.on('progress',function validateMimetype(bytesReceived,bytesExpected){
var percent =(bytesReceived / bytesExpected * 100)| 0;
/ /漂亮的基本检查是否有足够的文件字节写入磁盘,
//如果文件很小,可能太天真了!
if(tmpPath&& percent> 25){
var child = exec('file --mime-type'+ tmpPath,function(err,stdout,stderr){
var mimetype = stdout.substring(stdout.lastIndexOf(':')+ 2,stdout .lastIndexOf('\\\
'));
console.log('### file CALL OUTPUT',err,stdout,stderr);
if(err || stderr){
console.log('###错误:MIMETYPE不能被检测到);
} else if!!ALLOWED_MIME_TYPES [mimetype]){
console.log '###错误:INVALID MIMETYPE',mimetype);
} else {
console.log('### MIMETYPE VALIDA TION COMPLETE');
}
});
form.removeListener('progress',validateMimetype);
}
});
$ b form.on('fileBegin',function grabTmpPath(_,fileInfo){
if(fileInfo.path){
tmpPath = fileInfo.path;
form .removeListener('fileBegin',grabTmpPath);
}
});
I created an upload script in node.js using express/formidable. It basically works, but I am wondering where and when to check the uploaded file e. g. for the maximum file size or if the file´s mimetype is actually allowed.
My program looks like this:
app.post('/', function(req, res, next) {
req.form.on('progress', function(bytesReceived, bytesExpected) {
// ... do stuff
});
req.form.complete(function(err, fields, files) {
console.log('\nuploaded %s to %s', files.image.filename, files.image.path);
// ... do stuff
});
});
It seems to me that the only viable place for checking the mimetype/file size is the complete
event where I can reliably use the filesystem functions to get the size of the uploaded file in /tmp/
– but that seems like a not so good idea because:
- the possibly malicious/too large file is already uploaded on my server
- the user experience is poor – you watch the upload progress just to be told that it didnt work afterwards
Whats the best practice for implementing this? I found quite a few examples for file uploads in node.js but none seemed to do the security checks I would need.
With help from some guys at the node IRC and the node mailing list, here is what I do:
I am using formidable to handle the file upload. Using the progress
event I can check the maximum filesize like this:
form.on('progress', function(bytesReceived, bytesExpected) {
if (bytesReceived > MAX_UPLOAD_SIZE) {
console.log('### ERROR: FILE TOO LARGE');
}
});
Reliably checking the mimetype is much more difficult. The basic Idea is to use the progress
event, then if enough of the file is uploaded use a file --mime-type
call and check the output of that external command. Simplified it looks like this:
// contains the path of the uploaded file,
// is grabbed in the fileBegin event below
var tmpPath;
form.on('progress', function validateMimetype(bytesReceived, bytesExpected) {
var percent = (bytesReceived / bytesExpected * 100) | 0;
// pretty basic check if enough bytes of the file are written to disk,
// might be too naive if the file is small!
if (tmpPath && percent > 25) {
var child = exec('file --mime-type ' + tmpPath, function (err, stdout, stderr) {
var mimetype = stdout.substring(stdout.lastIndexOf(':') + 2, stdout.lastIndexOf('\n'));
console.log('### file CALL OUTPUT', err, stdout, stderr);
if (err || stderr) {
console.log('### ERROR: MIMETYPE COULD NOT BE DETECTED');
} else if (!ALLOWED_MIME_TYPES[mimetype]) {
console.log('### ERROR: INVALID MIMETYPE', mimetype);
} else {
console.log('### MIMETYPE VALIDATION COMPLETE');
}
});
form.removeListener('progress', validateMimetype);
}
});
form.on('fileBegin', function grabTmpPath(_, fileInfo) {
if (fileInfo.path) {
tmpPath = fileInfo.path;
form.removeListener('fileBegin', grabTmpPath);
}
});
这篇关于何时在node.js上传脚本中检查文件大小/ mimetype?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!