在没有 GridFS 的 NodeJS 中使用 MongoDB 存储一些小(小于 1MB)文件
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/11442356/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Storing some small (under 1MB) files with MongoDB in NodeJS WITHOUT GridFS
提问by thisissami
I run a website that runs on a backend of nodeJS + mongoDB. Right now, I'm implementing a system to store some icons (small image files) that will need to be in the database.
我运行一个在 nodeJS + mongoDB 后端运行的网站。现在,我正在实施一个系统来存储一些需要在数据库中的图标(小图像文件)。
From my understanding, it makes more sense NOT to use GridFS, since that seems to be tailored for either large files or large numbers of files. Since every file that I need to save will be well under the BSON maximum file size, I should be able to save them directly into a regular document.
根据我的理解,不使用 GridFS 更有意义,因为它似乎是为大文件或大量文件量身定制的。由于我需要保存的每个文件都远低于 BSON 最大文件大小,因此我应该能够将它们直接保存到常规文档中。
I have 2 questions:
我有两个问题:
1) Is my reasoning correct? Is it ok to save image files within a regular mongo collection, as opposed to with GridFS? Is there anything I'm not considering here that I should be?
1)我的推理是否正确?与 GridFS 相比,可以将图像文件保存在常规 mongo 集合中吗?有什么我不应该在这里考虑的吗?
2) If my thought process is sound, how do I go about doing this? Could I do something like the following:
2)如果我的思维过程是健全的,我该如何去做?我可以做以下事情吗:
//assume 'things' is a mongoDB collection created properly using node-mongodb-driver
fs.readFile(pathToIconImage, function(err,image){
things.insert({'image':image}, function(err,doc){
if(err) console.log('you have an error! ' + err);
});
});
I'm guessing that there's probably a better way to do this, since mongoDB uses BSON and here I'm trying to save a file in JSON before I send it off to the database. I also don't know if this code will work (haven't tried it).
我猜可能有更好的方法来做到这一点,因为 mongoDB 使用 BSON,在这里我试图在将文件发送到数据库之前以 JSON 格式保存文件。我也不知道这段代码是否有效(没试过)。
UPDATE - New Question
更新 - 新问题
If I have a document within a collection that has three pieces of information saved: 1) a name, 2) a date, and 3) an image file (the above icon), and I want to send this document to a client in order to display all three, would this be possible? If not, I guess I'd need to use GridFS and save the fileID in place of the image itself. Thoughts/suggestions?
如果我在集合中保存了一个文档,其中保存了三个信息:1) 名称,2) 日期和 3) 图像文件(上面的图标),并且我想将此文档发送给客户显示所有三个,这可能吗?如果没有,我想我需要使用 GridFS 并保存 fileID 代替图像本身。想法/建议?
Best, and thanks for any responses,
Sami
最好的,感谢您的任何回应,
萨米
采纳答案by Tim Gautier
If your images truly are small enough to not be a problem with document size and you don't mind a little amount of extra processing, then it's probably fine to just store it directly in your collection. To do that you'll want to base64 encode the image, then store it using mongo's BinData type. As I understand it, that will then save it as a BSON bit array, not actually store the base64 string, so the size won't grow larger than your original binary image.
如果您的图像确实足够小,不会对文档大小造成问题,并且您不介意进行少量额外处理,那么将其直接存储在您的收藏中可能没问题。为此,您需要对图像进行 base64 编码,然后使用 mongo 的 BinData 类型存储它。据我了解,这会将其保存为 BSON 位数组,而不是实际存储 base64 字符串,因此大小不会比原始二进制图像大。
It will display in json queries as a base64 string, which you can use to get the binary image back.
它将在 json 查询中显示为 base64 字符串,您可以使用它来获取二进制图像。
回答by uajov6
I have been looking for the same thing. I know this post is old , but perhaps i can help someone out there.
我一直在寻找同样的东西。我知道这篇文章很旧,但也许我可以帮助那里的人。
var fs = require('fs');
var mongo = require('mongodb').MongoClient;
var Binary = require('mongodb').Binary;
var archivobin = fs.readFileSync("vc.exe");
// print it out so you can check that the file is loaded correctly
console.log("Loading file");
console.log(archivobin);
var invoice = {};
invoice.bin = Binary(archivobin);
console.log("largo de invoice.bin= "+ invoice.bin.length());
// set an ID for the document for easy retrieval
invoice._id = 12345;
mongo.connect('mongodb://localhost:27017/nogrid', function(err, db) {
if(err) console.log(err);
db.collection('invoices').insert(invoice, function(err, doc){
if(err) console.log(err);
// check the inserted document
console.log("Inserting file");
console.log(doc);
db.collection('invoices').findOne({_id : 12345}, function(err, doc){
if (err) {
console.error(err);
}
fs.writeFile('vcout.exe', doc.bin.buffer, function(err){
if (err) throw err;
console.log('Sucessfully saved!');
});
});
});
});

