diff --git a/lib/mongo.js b/lib/mongo.js index 7d2a2a6..d1794c2 100644 --- a/lib/mongo.js +++ b/lib/mongo.js @@ -9,6 +9,7 @@ import { Mongo } from 'meteor/mongo'; import { MongoID } from 'meteor/mongo-id'; import { DDP } from 'meteor/ddp-client'; import { includesOnly, createProjection, extractIds, isObjectIdCollection, convertObjectId } from './utils/server'; +const { SoftDelete } = Package['jam:soft-delete'] || {}; const originalInsert = Mongo.Collection.prototype.insertAsync; const originalUpdate = Mongo.Collection.prototype.updateAsync; @@ -165,8 +166,12 @@ Mongo.Collection.prototype.updateAsync = async function (selector, mod, options send({ msg: 'changed', _id, fields, collection: this._name }); } else { - const finalFilter = hasId ? filter : insertedId ? { _id: insertedId } : docIds ? {_id: numberAffected === 1 ? docIds[0] : { $in: docIds }} : undefined; - const { projection, unsets = [] } = finalFilter && createProjection(modifier); + let finalFilter = hasId ? filter : insertedId ? { _id: insertedId } : docIds ? {_id: numberAffected === 1 ? docIds[0] : { $in: docIds }} : undefined; + const { projection, unsets = [], softDeleted } = finalFilter && createProjection(modifier); + if (softDeleted) { + finalFilter ={ ...finalFilter, [SoftDelete.config.deleted]: true} + } + const items = finalFilter ? await this.find(finalFilter, { projection }).fetchAsync() : []; for (const { _id, ...fields } of items) { diff --git a/lib/utils/server.js b/lib/utils/server.js index f92fda6..7f056a4 100644 --- a/lib/utils/server.js +++ b/lib/utils/server.js @@ -1,6 +1,7 @@ import { Mongo, MongoInternals } from 'meteor/mongo'; import { MongoID } from 'meteor/mongo-id'; import { isEmpty, omit } from './shared'; +const { SoftDelete } = Package['jam:soft-delete'] || {}; const { ObjectId } = MongoInternals?.NpmModules.mongodb.module || {}; @@ -179,6 +180,11 @@ export const buildProjection = projection => { export const createProjection = modifier => { const projection = {}; const unsets = []; // keep track of the $unsets so we can make them undefined when returning to the client + let softDeleted = false + let softDeletedField = null + if (Package['jam:soft-delete']) { + softDeletedField = SoftDelete.config.deleted; + } for (const key in modifier) { if (!key.startsWith('$')) { @@ -186,13 +192,16 @@ export const createProjection = modifier => { continue; } - for (const field in modifier[key]) { + for (const [field, value] of Object.entries(modifier[key])) { if (key === '$unset') unsets.push(field); projection[field.split('.')[0]] = 1; // top level field only + if (softDeletedField && field.split('.')[0] === softDeletedField && value === true) { + softDeleted = true; + } } } - return { projection, unsets }; + return { projection, unsets, softDeleted }; }; // used to merge documents added by the low-level publish API into the final fetch result set