diff --git a/core/server/services/settings/index.js b/core/server/services/settings/index.js index eb209d2bef..e4ef0b6551 100644 --- a/core/server/services/settings/index.js +++ b/core/server/services/settings/index.js @@ -12,11 +12,19 @@ module.exports = { }, async reinit() { + const oldSettings = SettingsCache.getAll(); + SettingsCache.shutdown(); const settingsCollection = await models.Settings.populateDefaults(); - SettingsCache.init(settingsCollection); + const newSettings = SettingsCache.init(settingsCollection); + for (const model of settingsCollection.models) { - model.emitChange(model.attributes.key + '.' + 'edited', {}); + const key = model.attributes.key; + + // The type of setting is object. That's why we need to compare the value of the `value` property. + if (newSettings[key].value !== oldSettings[key].value) { + model.emitChange(key + '.' + 'edited', {}); + } } }, diff --git a/test/unit/server/settings_spec.js b/test/unit/server/settings_spec.js new file mode 100644 index 0000000000..d521d896d6 --- /dev/null +++ b/test/unit/server/settings_spec.js @@ -0,0 +1,106 @@ +const sinon = require('sinon'); +const should = require('should'); +const rewire = require('rewire'); +const settings = rewire('../../../core/server/services/settings'); + +describe('UNIT: server settings', function () { + afterEach(function () { + sinon.restore(); + }); + + describe('reinit', function () { + function setupSettings(oldSettings, newSettings) { + const spy = sinon.spy(); + const models = { + Settings: { + populateDefaults: sinon.stub() + } + }; + models.Settings.populateDefaults.resolves({ + models: [{ + attributes: { + key: 'db_hash' + }, + emitChange: spy + }] + }); + + const cache = { + getAll: sinon.stub(), + init: sinon.stub(), + shutdown: sinon.stub() + }; + + cache.getAll.returns(oldSettings); + cache.init.returns(newSettings); + + settings.__set__({ + models, + SettingsCache: cache + }); + + return spy; + } + + it('emit is not fired when the settings value is same', async function () { + const oldSettings = { + db_hash: { + id: '5f4e32961c5a161b10dbff99', + group: 'core', + key: 'db_hash', + value: '342c470a-d4e2-4aa1-9dd3-fb5f11d82db6', + type: 'string', + flags: null, + created_at: '2020-09-01T11:37:58.000Z', + created_by: '1', + updated_at: '2020-09-01T11:37:58.000Z', + updated_by: '1' + } + }; + const newSettings = oldSettings; + + const spy = setupSettings(oldSettings, newSettings); + + await settings.reinit(); + + spy.calledWith('db_hash.edited', {}).should.not.be.true(); + }); + + it('emit is fired when the settings value is changed', async function () { + const oldSettings = { + db_hash: { + id: '5f4e32961c5a161b10dbff99', + group: 'core', + key: 'db_hash', + value: '342c470a-d4e2-4aa1-9dd3-fb5f11d82db6', + type: 'string', + flags: null, + created_at: '2020-09-01T11:37:58.000Z', + created_by: '1', + updated_at: '2020-09-01T11:37:58.000Z', + updated_by: '1' + } + }; + const newSettings = { + db_hash: { + id: '5f4e32961c5a161b10dbff99', + group: 'core', + key: 'db_hash', + value: '12345', // changed + type: 'string', + flags: null, + created_at: '2020-09-01T11:37:58.000Z', + created_by: '1', + updated_at: '2020-09-01T11:37:58.000Z', + updated_by: '1' + } + }; + + const spy = setupSettings(oldSettings, newSettings); + + await settings.reinit(); + + spy.calledWith('db_hash.edited', {}).should.be.true(); + }); + }); +});