Sails中的Waterline很酷,而且这个抽象层非常有用。我的问题是:如何使用水线存储图像?有一种称为二进制的类型。我应该使用那种类型吗?我应该像任何其他数据类型一样处理图像吗?如何验证图像,说确保其格式是少数给定的选项,如png,jpeg等。
答案 0 :(得分:4)
我不建议使用二进制文件直接在您的数据库中存储图像。如果您的用户想要上传图片,那就太麻烦了,我不认为waterline支持流式传输到数据库。虽然有另一种选择!
Mongodb有一个名为gridfs的功能,可以将大文件拆分成块并存储起来。
Sails的文件上传库skipper具有适配器(如水线)的概念,允许您将适配器插入文件上载过程。有一个名为skipper-gridfs的适配器可以为您完成此操作!我用过这个,它非常容易使用。你做的是:
定义一个sails模型,让我们称之为Image,它有属性filename和filedescriptor
filedescriptor是mongo用来引用块的ID。基本上,你要将你的文件(任何类型的文件)存储在gridfs中并接收文件描述符。您将在模型(图像模型)中保存它,然后使用该模型从gridfs下载文件。
以下是一些上传代码:
var adapter = require('skipper-gridfs');
upload : function (req, res, next) {
var params = req.params.all();
var gf = _gridfs;
//upload file to gridfs
req.file('file').upload(
{
adapter:adapter,
uri:constring
},
function (err,uploadedFiles){
if (err) {return res.send(err);}
var imagePromiseArray = [];
//loop over the files uploaded to gridfs and store references to their IDs in your Image model
_.each(uploadedFiles,function(file){
var imageParams = {
filename:file.filename,
fileDescriptor:file.fd
};
imagePromiseArray.push(Image.create(imageParams));
});
Promise
.all(imagePromiseArray)
.then(function(results){
res.status(200);
return res.send(results);
})
.catch(function(err){
res.status(500);
res.send(err);
});
});
},
这里是一些下载代码:
var mime = require('mime');
download: function (req, res, next) {
var params = req.params.all();
Image
.findOne(params.id)
.then(function (image) {
debugger;
_gridfs.read(image.fileDescriptor, function (err, data) {
if (err) {
res.status(500);
res.json(err);
}
if (!data) {
res.status(404);
res.json({error: 'image not found'});
} else {
res.setHeader('Content-disposition', 'attachment; filename=' + image.filename);
var type = mime.lookup(image.filename);
res.setHeader('Content-type', type);
res.send(data);
}
});
})
.catch(function (err) {
res.json(err);
});
},