我想在我的服务器上传文件并根据其内容命名。这应该很简单(它在python中),但我很难弄清楚如何在Node.js中做到这一点。
我正在使用express和connect-form,really just uses formidable。我还看到该节点有一个名为crypto的库,它与python的hashlib非常相似。现在我只需要了解如何流式传输临时文件connect-form给我并哈希它。
这是我想要做的Python / Flask(ish)实现。
import hashlib
from Flask import request
def upload():
file = request.files['file']
hash = hashlib.sha256()
name, ext = file.filename.rsplit('.', 1)
try:
for chunk in file.chunks()
hash.update(chunk)
finally:
file.seek(0)
new_name = "%s.%s" % (hash.hexdigest(),ext)
file.save(os.path.join(UPLOAD_DIR, new_name))
我见过很多这些toy answers that just print out the file's name,但实际上并没有读取和写入数据。
答案 0 :(得分:3)
这里充满了咖啡脚本。
app.post '/upload', (request, response, next) ->
request.form.complete (error, fields, files) ->
if error
next error
else
file = files.file
[kind, extension] = file.type.split '/'
hash = crypto.createHash 'sha256'
stream = fs.createReadStream file.path,
encoding:'binary'
stream.addListener 'data', (chunk) ->
hash.update chunk
stream.addListener 'close', ->
digest = hash.digest 'hex'
new_filename = "#{digest}.#{extension}"
new_path = "#{UPLOAD_DIR}/#{new_filename}"
fs.rename file.path, new_path
response.end new_filename
我没有将哈希计算破解成强大的,这可能更有效但更复杂,我选择从其临时位置重新读取文件并散列。然后,不像其他示例中那样抽取它,我只是将临时文件重命名为新位置。
答案 1 :(得分:1)
你可以保存这样的文件:
var fs = require('fs'),
util = require('util'),
crypto = require('crypto');
// ...
req.form.complete(function (err, fields, files) {
// ...
var ext = files['content[media]']['filename'].split('.');
ext = ext[ext.length-1];
ext = ext.toLowerCase();
var newFileName = req['connection']['remoteAddress'] + req['connection']['remotePort'] + Date.now();
newFileName = crypto.createHash('md5').update(newFileName).digest("hex");
newFileName += '.' + ext;
var is = fs.createReadStream(files['content[media]']['path']);
var os = fs.createWriteStream(app.set('dataDir') + '/' + newFileName);
// copy file to public folder
util.pump(is, os, function(error) {
if (error) {
console.log("Error copying file to public ... " + error);
res.redirect("back");
return;
}
else {
// delete temp file
fs.unlinkSync(files['content[media]']['path']);
res.redirect('....');
}
});
});