Reputation: 135
This has been getting me all day. I can find the actual file with it's _id using gfs.exist(), but then when i run to the next line of code i get an error everytime and the mongoose connection crashes. This seems so simple yet nothing has worked so far.
my code:
/**
* Created by foolishklown on 10/2/2016.
*/
var Grid = require('gridfs-stream'),
User = require('../../models/user'),
mongoose = require('mongoose');
module.exports = function(id, ref, type, res) {
console.log(ref.green);
Grid.mongo = mongoose.mongo;
var conn = mongoose.createConnection('mongodb://localhost/media');
conn.once('open', function () {
var gfs = Grid(conn.db);
gfs.exist({_id: ref}, function(err, found) {
if(err) {
console.error('error finding file'.red);
} else {
console.info('found file', found);
gfs.files.remove({_id: ref }, function(err) {
if(err) {
console.error('error removing that file');
process.exit(1);
} else {
console.info('removed file: ', found.green);
deleteFromUserDb(id, type, ref);
res.status(200).send({id: id, type: type, ref: ref});
}
});
}
});
});
conn.close();
function deleteFromUserDb(userId, fileType, refId) {
var userConn = mongoose.createConnection('mongodb://localhost/mean-auth', (error) => {
if(error) {
console.error('Error connecting to the mean-auth instance'.red);
process.exit(1);
} else {
User.findById(userId, (err, doc) => {
if(err) {
console.error('Error finding user with id: ', uid);
process.exit(1);
} else {
console.log('original doc: ', doc);
doc.removeMedia(fileType, refId);
doc.save();
console.log('new doc: ', doc);
}
})
}
});
}
};
i have tried using gfs.files.remove({_id: ref}, function(.....) to no avail
i have also tried using gfs.files.remove({_id: ref}, {_id: 1}, function(....)
i have also tried both of the above using gfs.remove() without gfs.files.remove.....
it must be something simple but its been beating me up all day... thanks
new edit 10/15.......... i am now trying to use just the native mongodb driver. I can find the file both with the string, and casting it to an objectId. It seems like the operation completes no problem, but when i use the shell to see if the file has been deleted it still exists in both fs.files and fs.chunks. This one is killing me!
deleteFile: function(userId, fileType, objId, res) {
var ObjectId = require('mongodb');
var client = mongodb.MongoClient;
var _id = new ObjectId(objId);
client.connect(mediaUri, (err, db) => {
assert.equal(null, err);
db.collection('fs.files').find({_id: _id}, (err, doc) => {
if(err) {
console.error('error finding that document in files collection'.red);
} else {
console.info('found the document: ', doc);
console.info('the document type is: ', typeof(doc));
}
});
db.collection('fs.chunks').find({_id: _id }, (err, doc) => {
if(err) {
console.error('error finding that document in the chunks collection'.red);
} else {
console.info('found the document(s): ', doc);
console.info('the document type is: ', typeof(doc));
}
});
db.collection('fs.files').deleteOne({_id: _id}, (err, doc) => {
console.log('document returned for deletion is: ', doc);
});
db.collection('fs.chunks').deleteOne({_id: _id}, (err, doc) => {
console.log('documents deleted: ', doc);
res.status(200).send({id: userId, type: fileType, ref: objId});
});
db.close();
})
}
Upvotes: 1
Views: 2351
Reputation: 25
If you import the ObjectId
object as follows:
const ObjectId = mongoose.Types.ObjectId;
at the top of your file as with a normal import, you can write the delete as follows:
const mongoose = require('mongoose');
const Grid = require('gridfs-stream');
const ObjectId = mongoose.Types.ObjectId
Grid.mongo = mongoose.mongo // assign the mongo driver to the Grid
const mongooseURI = 'mongodb://localhost/media';
const conn = mongoose.createConnection(mongooseURI, {useNewUrlParser:true});
conn.once('open', () => {
const gfs = Grid(conn.db);
gfs.exist({_id: ref}, (err, found) => {
if(err) {
console.error('error finding file'.red);
} else {
console.info('found file', found);
gfs.files.deleteOne({_id:new ObjectId(ref)}, (err, result) => {
if(err) {
console.error('error removing that file');
process.exit(1);
} else {
console.info('removed file: ', found.green);
deleteFromUserDb(id, type, ref);
res.status(200).send({id: id, type: type, ref: ref});
}
});
}
});
Hope this helps!
Upvotes: 0
Reputation: 135
i was doing the cast wrong, and using the wrong methods. After using a new constructor for mongodb.ObjectID() instead of mongodb.ObjectiD(), i had some success, plus i was calling on a few of the wrong methods. I consulted the documentation and straightened things out.
My final code for CRUD operations is:
/**
* Created by foolishklown on 10/13/2016.
*/
var assert = require('assert'),
path = require('path'),
Grid = require('gridfs-stream'),
fs = require('fs'),
mongodb = require('mongodb'),
mongoose = require('mongoose'),
User = require('../../models/user'),
mediaUri = 'mongodb://localhost/media',
userUri = 'mongodb://localhost/mean-auth';
module.exports = {
writeFile: function (file, userId, fileType, fileInfo, res) {
var fileId;
var fileTitle = file.originalFilename;
var conn = mongoose.createConnection('mongodb://localhost/media', (error) => {
if (error) {
console.error('Error connecting to mongod media instance'.red);
process.exit(1);
} else {
console.info('Connected successfully to mongod media instance in the write file!'.blue);
}
});
// The following line is designating a file to grab/read, and save into mongo
// in our case it will be something from ng-file-upload that the user wants to upload
var myFile = file.path;
// Connect gridFs and mongo
Grid.mongo = mongoose.mongo;
conn.once('open', function () {
console.log('connection open, ready for I/O!');
var gfs = Grid(conn.db);
// This write stream is how well write to mongo
var writeStream = gfs.createWriteStream({
// Name the file the way you want it stored in mongo
filename: file.originalFilename,
type: fileType,
info: fileInfo
});
// Create a read stream, so that we can read its data, and then with that well use the
// write stream to write to the DB via piping the writestream
var readStream = fs.createReadStream(myFile)
.on('end', () => {
writeToUserDb(userId, fileType, readStream.id, fileInfo, fileTitle);
res.status(200).send(
{
ref: readStream.id,
type: fileType,
user: userId,
mediaInfo: fileInfo,
title: fileTitle
}
);
})
.on('error', () => {
res.status(500).send('error in writing with gridfs');
})
.pipe(writeStream);
writeStream.on('close', function (file) {
console.log(file.filename + 'written to DB');
fs.unlink(myFile);
myFile = null;
conn.close();
});
});
function writeToUserDb(uid, type, fileId, authInfo, title) {
console.info('called to write to user db without a \'this\' reference');
var userConn = mongoose.createConnection('mongodb://localhost/mean-auth', (error) => {
if (error) {
console.error('Error connecting to the mean-auth instance'.red);
process.exit(1);
} else {
User.findById(uid, (err, doc) => {
if (err) {
console.error('Error finding user with id: ', uid);
process.exit(1);
} else {
console.log('original doc: ', doc);
doc.addMedia(type, fileId, authInfo, title);
doc.save();
console.log('new doc: ', doc);
}
})
}
});
userConn.close();
}
},
downloadFile: function (userId, file, fileType, objId, location, res) {
console.info('called to download file');
var id = new mongodb.ObjectID(objId);
var conn = mongoose.createConnection(mediaUri, (error) => {
assert.ifError(error);
var gfs = Grid(conn.db, mongoose.mongo);
gfs.findOne({_id: id}, (err, result) => {
if (err) {
res.status(400).send(err);
} else if (!result) {
res.status(404).send('Error finding file')
} else {
res.set('Content-Type', result.contentType);
res.set('Content-Disposition', 'attachment; filename="' + result.filename + '"');
var readStream = gfs.createReadStream({
_id: id,
root: 'resume'
});
readStream.on('error', (err) => {
res.end();
});
readStream.pipe(res);
}
});
});
conn.close();
},
deleteFile: function (userId, fileType, objId, res) {
var client = mongodb.MongoClient;
var id = new mongodb.ObjectID(objId);
console.log('object id to find is: ', id);
client.connect('mongodb://localhost/media', (err, db) => {
db.collection('fs.files', {}, (err, files) => {
files.remove({_id: id}, (err, result) => {
if (err) {
console.log(err);
res.status(500);
}
console.log(result);
});
});
db.collection('fs.chunks', {}, (err, chunks) => {
chunks.removeMany({files_id: id}, (err, result) => {
if (err) {
console.log(err);
res.status(500);
}
console.log(result);
});
});
db.close();
});
res.status(200).send({id: userId, type: fileType, ref: id});
},
getAll: function (req, res) {
var uid = req.query.id;
var conn = mongoose.createConnection('mongodb://localhost/mean-auth', (err) => {
if (err) {
console.error('Error connecting to mean-auth instance to read all');
process.exit(1);
} else {
User.findById(uid, (err, doc) => {
if (err) {
console.error('Error finding user with id: ', uid);
process.exit(1);
} else {
if (doc) {
console.log('original doc: ', doc);
res.status(200).send({media: doc.media});
} else {
res.status(200);
}
}
})
}
});
}
};
Upvotes: 1