@joktec/mongo
Version:
JokTec - Mongo Service
93 lines • 3.63 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.ParanoidPlugin = void 0;
const utils_1 = require("@joktec/utils");
const lodash_1 = require("lodash");
function injectFilter(filter, key, paranoid = true) {
if (!paranoid)
return filter;
return Object.assign(filter, { [key]: null });
}
function injectMatchPipeline(pipelines, key, paranoid = true) {
const newPipelines = [];
for (const pipeline of (0, utils_1.toArray)(pipelines)) {
if ('$match' in pipeline) {
injectFilter(pipeline.$match, key, paranoid);
}
if ('$lookup' in pipeline) {
const subPipelines = injectMatchPipeline(pipeline.$lookup.pipeline, key, paranoid);
if (subPipelines.length) {
pipeline.$lookup.pipeline = subPipelines.map(subPipeline => subPipeline);
}
}
if ('$unionWith' in pipeline) {
const unionWith = (0, lodash_1.isString)(pipeline.$unionWith) ? { coll: pipeline.$unionWith } : pipeline.$unionWith;
const subPipelines = injectMatchPipeline(unionWith.pipeline, key, paranoid);
if (subPipelines.length) {
unionWith.pipeline = subPipelines.map(subPipeline => subPipeline);
pipeline.$unionWith = unionWith;
}
}
if ('$facet' in pipeline) {
const fields = Object.keys(pipeline.$facet);
for (const field of fields) {
const subPipelines = injectMatchPipeline(pipeline.$facet[field], key, paranoid);
if (subPipelines.length) {
pipeline.$facet[field] = subPipelines.map(subPipeline => subPipeline);
}
}
}
if ('$merge' in pipeline && (0, lodash_1.isObject)(pipeline['$merge'].whenMatched)) {
const subPipelines = injectMatchPipeline(pipeline['$merge'].whenMatched, key, paranoid);
if (subPipelines.length) {
pipeline['$merge'].whenMatched = subPipelines.map(subPipeline => subPipeline);
}
}
newPipelines.push(pipeline);
}
const match = injectFilter({}, key, paranoid);
if (!newPipelines.some(p => '$match' in p) && !(0, lodash_1.isEmpty)(match)) {
newPipelines.unshift({ $match: match });
}
return newPipelines;
}
const ParanoidPlugin = (schema, opts) => {
const deletedAtKey = opts?.deletedAt?.name || 'deletedAt';
schema.add({
[deletedAtKey]: {
type: opts?.deletedAt?.type || Date,
default: null,
deletedAt: deletedAtKey,
select: false,
},
});
schema.pre([
'find',
'findOne',
'findOneAndUpdate',
'countDocuments',
'estimatedDocumentCount',
'updateMany',
'updateOne',
'deleteOne',
'findOneAndDelete',
'deleteMany',
], function (next) {
const options = this.getOptions();
const filter = this.getFilter();
injectFilter(filter, deletedAtKey, options?.paranoid);
this.setQuery(filter);
next();
});
schema.pre('aggregate', function (next, options) {
const paranoid = (0, utils_1.toBool)(options?.paranoid, true);
const pipelines = injectMatchPipeline(this.pipeline(), deletedAtKey, paranoid);
while (this.pipeline().length)
this.pipeline().shift();
while (pipelines.length)
this.pipeline().push(pipelines.shift());
next();
});
};
exports.ParanoidPlugin = ParanoidPlugin;
//# sourceMappingURL=paranoid.plugin.js.map