extensionSystem: Add canChange property to extensions

Whether or not an extension can be enabled/disabled depends on various
factors: Whether the extension is in error state, whether user extensions
are disabled and whether the underlying GSettings keys are writable.

This is complex enough to share the logic, so add it to the extension
properties that are exposed over D-Bus.

https://bugzilla.gnome.org/show_bug.cgi?id=789852
This commit is contained in:
Didier Roche 2018-12-04 09:31:27 +01:00 committed by Florian Müllner
parent 32e0b895a4
commit 4a3476266f
2 changed files with 40 additions and 7 deletions

View File

@ -30,7 +30,7 @@ var ExtensionState = {
UNINSTALLED: 99
};
const SERIALIZED_PROPERTIES = ['type', 'state', 'path', 'error', 'hasPrefs'];
const SERIALIZED_PROPERTIES = ['type', 'state', 'path', 'error', 'hasPrefs', 'canChange'];
// Maps uuid -> metadata object
var extensions = {};
@ -219,6 +219,7 @@ function createExtensionObject(uuid, dir, type) {
extension.path = dir.get_path();
extension.error = '';
extension.hasPrefs = dir.get_child('prefs.js').query_exists(null);
extension.canChange = false;
extensions[uuid] = extension;

View File

@ -189,6 +189,7 @@ var ExtensionManager = class {
}
}
this._updateCanChange(extension);
this.emit('extension-state-changed', extension);
}
@ -267,12 +268,28 @@ var ExtensionManager = class {
return true;
}
_getEnabledExtensions() {
let extensions;
_getModeExtensions() {
if (Array.isArray(Main.sessionMode.enabledExtensions))
extensions = Main.sessionMode.enabledExtensions;
else
extensions = [];
return Main.sessionMode.enabledExtensions;
return [];
}
_updateCanChange(extension) {
let hasError =
extension.state == ExtensionState.ERROR ||
extension.state == ExtensionState.OUT_OF_DATE;
let isMode = this._getModeExtensions().includes(extension.uuid);
let modeOnly = global.settings.get_boolean(DISABLE_USER_EXTENSIONS_KEY);
extension.canChange =
!hasError &&
global.settings.is_writable(ENABLED_EXTENSIONS_KEY) &&
(isMode || !modeOnly);
}
_getEnabledExtensions() {
let extensions = this._getModeExtensions();
if (global.settings.get_boolean(DISABLE_USER_EXTENSIONS_KEY))
return extensions;
@ -280,6 +297,11 @@ var ExtensionManager = class {
return extensions.concat(global.settings.get_strv(ENABLED_EXTENSIONS_KEY));
}
_onUserExtensionsEnabledChanged() {
this._onEnabledExtensionsChanged();
this._onSettingsWritableChanged();
}
_onEnabledExtensionsChanged() {
let newEnabledExtensions = this._getEnabledExtensions();
@ -305,6 +327,14 @@ var ExtensionManager = class {
this._enabledExtensions = newEnabledExtensions;
}
_onSettingsWritableChanged() {
for (let uuid in ExtensionUtils.extensions) {
let extension = ExtensionUtils.extensions[uuid];
this._updateCanChange(extension);
this.emit('extension-state-changed', extension);
}
}
_onVersionValidationChanged() {
// we want to reload all extensions, but only enable
// extensions when allowed by the sessionMode, so
@ -325,9 +355,11 @@ var ExtensionManager = class {
global.settings.connect(`changed::${ENABLED_EXTENSIONS_KEY}`,
this._onEnabledExtensionsChanged.bind(this));
global.settings.connect(`changed::${DISABLE_USER_EXTENSIONS_KEY}`,
this._onEnabledExtensionsChanged.bind(this));
this._onUserExtensionsEnabledChanged.bind(this));
global.settings.connect(`changed::${EXTENSION_DISABLE_VERSION_CHECK_KEY}`,
this._onVersionValidationChanged.bind(this));
global.settings.connect(`writable-changed::${ENABLED_EXTENSIONS_KEY}`,
this._onSettingsWritableChanged.bind(this));
this._enabledExtensions = this._getEnabledExtensions();