diff --git a/src/database/mongo/sets.js b/src/database/mongo/sets.js index eacf60ed7a..784b6acd70 100644 --- a/src/database/mongo/sets.js +++ b/src/database/mongo/sets.js @@ -94,44 +94,31 @@ module.exports = function (module) { }; module.setRemove = async function (key, value) { - if (!Array.isArray(value)) { - value = [value]; - } - - value = value.map(v => helpers.valueToString(v)); - - const coll = module.client.collection('objects'); - await coll.updateMany({ - _key: Array.isArray(key) ? { $in: key } : key, - }, { - $pullAll: { members: value }, - }); - - await coll.deleteMany({ - _key: Array.isArray(key) ? { $in: key } : key, - members: { $size: 0 }, - }); + await bulkSetRemove(key, value); }; module.setsRemove = async function (keys, value) { if (!Array.isArray(keys) || !keys.length) { return; } - value = helpers.valueToString(value); - - const coll = module.client.collection('objects'); - await coll.updateMany({ - _key: { $in: keys }, - }, { - $pull: { members: value }, - }); - - await coll.deleteMany({ - _key: { $in: keys }, - members: { $size: 0 }, - }); + await bulkSetRemove(keys, value); }; + async function bulkSetRemove(key, values) { + const isKeyArray = Array.isArray(key); + if (!key || (isKeyArray && !key.length)) return; + + const filterKey = isKeyArray ? { $in: key } : key; + const update = Array.isArray(values) ? + { $pullAll: { members: values.map(helpers.valueToString) } } : + { $pull: { members: helpers.valueToString(values) } }; + + await module.client.collection('objects').bulkWrite([ + { updateMany: { filter: { _key: filterKey }, update: update } }, + { deleteMany: { filter: { _key: filterKey, members: { $size: 0 } } } }, + ], { ordered: true }); + } + module.isSetMember = async function (key, value) { if (!key) { return false; diff --git a/src/database/redis/sets.js b/src/database/redis/sets.js index 861bf275ea..141bc46919 100644 --- a/src/database/redis/sets.js +++ b/src/database/redis/sets.js @@ -57,6 +57,9 @@ module.exports = function (module) { }; module.setsRemove = async function (keys, value) { + if (!Array.isArray(keys) || !keys.length) { + return; + } const batch = module.client.batch(); keys.forEach(k => batch.sRem(String(k), String(value))); await helpers.execBatch(batch); diff --git a/test/database/sets.js b/test/database/sets.js index 05d969353f..4d017b640b 100644 --- a/test/database/sets.js +++ b/test/database/sets.js @@ -278,20 +278,21 @@ describe('Set methods', () => { }); describe('setsRemove()', () => { - before((done) => { - db.setsAdd(['set1', 'set2'], 'value', done); + it('should remove a element from multiple sets', async () => { + await db.setsAdd(['set1', 'set2'], 'value'); + await db.setRemove(['set1', 'set2'], 'value'); + const members = await db.isMemberOfSets(['set1', 'set2'], 'value'); + assert.deepStrictEqual(members, [false, false]); }); - it('should remove a element from multiple sets', (done) => { - db.setsRemove(['set1', 'set2'], 'value', function (err) { - assert.equal(err, null); - assert.equal(arguments.length, 1); - db.isMemberOfSets(['set1', 'set2'], 'value', (err, members) => { - assert.equal(err, null); - assert.deepEqual(members, [false, false]); - done(); - }); - }); + it('should remove the sets if they are empty', async () => { + await db.setAdd('setsRemoveSet3', ['a']); + await db.setAdd('setsRemoveSet4', ['a']); + await db.setsRemove(['setsRemoveSet3', 'setsRemoveSet4'], 'a'); + assert.deepStrictEqual( + await db.exists(['setsRemoveSet3', 'setsRemoveSet4']), + [false, false] + ); }); });