VulpesOS/gaia/shared/js/smart-screen/settings_cache.js
OverSu b38dea0597 Publish Vulpes Preview 15 sources for desktop, Android and Tundra
Share Gaia assets and adapters, keep private profiles and development documents local, and update both public READMEs.
2026-09-30 23:13:03 +02:00

154 lines
4.1 KiB
JavaScript
Executable file

/**
* SettingsCache is a singleton that caches mozSettings values for fast
* access.
*
* @module SettingsCache
*/
(function() {
'use strict';
var _settings = window.navigator.mozSettings;
// Cache of all current settings values. There's some large stuff
// in here, but not much useful can be done with the settings app
// without these, so we keep this around most of the time.
var _settingsCache = null;
// True when a request has already been made to fill the settings
// cache. When this is true, no further get("*") requests should be
// made; instead, pending callbacks should be added to
// _pendingSettingsCallbacks.
var _settingsCacheRequestSent = null;
// There can be race conditions in which we need settings values,
// but haven't filled the cache yet. This array tracks those
// listeners.
var _pendingSettingsCallbacks = [];
var _callbacks = [];
var _keyCallbacks = {};
var _onSettingsChange = function sc_onSettingsChange(event) {
var key = event.settingName;
var value = event.settingValue;
// Always update the cache if it's present, even if the DOM
// isn't loaded yet.
if (_settingsCache) {
_settingsCache[key] = value;
}
_callbacks.forEach(function(callback) {
callback(event);
});
if (_keyCallbacks[key]) {
_keyCallbacks[key].forEach(function(callback) {
callback(value);
});
}
};
if (_settings) {
_settings.onsettingchange = _onSettingsChange;
}
/**
* Event reporting that a setting value is changed.
*
* @event module:SettingsCache#settingsChange
* @property {MozSettingsEvent} event
*/
var SettingsCache = {
init: function sc_init() {
// Make a request for settings to warm the cache, since we need it
// very soon in startup after the DOM is available.
this.getSettings();
},
// the reset function is for unit tests
reset: function sc_reset() {
_settings = window.navigator.mozSettings;
if (_settings) {
_settings.onsettingchange = _onSettingsChange;
}
_settingsCache = null;
_settingsCacheRequestSent = null;
_pendingSettingsCallbacks = [];
_callbacks = [];
},
get cache() {
return _settingsCache;
},
/**
* Where callback is a function to be called with a request object for a
* successful fetch of settings values, when those values are ready.
*
* @alias module:SettingsCache#getSettings
* @param {Function} callback
*/
getSettings: function sc_getSettings(callback) {
if (!_settings) {
return;
}
if (_settingsCache && callback) {
// Fast-path that we hope to always hit: our settings cache is
// already available, so invoke the callback now.
callback(_settingsCache);
return;
}
if (!_settingsCacheRequestSent && !_settingsCache) {
_settingsCacheRequestSent = true;
var lock = _settings.createLock();
var request = lock.get('*');
request.onsuccess = function(e) {
var result = request.result;
var cachedResult = {};
for (var attr in result) {
cachedResult[attr] = result[attr];
}
_settingsCache = cachedResult;
var cbk;
while ((cbk = _pendingSettingsCallbacks.pop())) {
cbk(result);
}
};
}
if (callback) {
_pendingSettingsCallbacks.push(callback);
}
},
observe: function sc_observe(name, defaultValue, callback) {
if (!callback) {
return;
}
this.getSettings(function(cache) {
if (callback) {
callback((typeof cache[name]) === 'undefined' ?
defaultValue : cache[name]);
}
});
if (!_keyCallbacks[name]) {
_keyCallbacks[name] = [];
}
_keyCallbacks[name].push(function(v) {
callback((typeof v) === 'undefined' ? defaultValue : v);
});
},
get: function sc_get(name, callback) {
this.getSettings(function(cache) {
callback(cache[name]);
});
}
};
SettingsCache.init();
window.SettingsCache = SettingsCache;
})();