1 | "use strict";
|
2 |
|
3 |
|
4 |
|
5 |
|
6 |
|
7 |
|
8 |
|
9 |
|
10 |
|
11 |
|
12 |
|
13 |
|
14 |
|
15 |
|
16 |
|
17 | var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
18 | var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
19 | if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
20 | else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
21 | return c > 3 && r && Object.defineProperty(target, key, r), r;
|
22 | };
|
23 | var __metadata = (this && this.__metadata) || function (k, v) {
|
24 | if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
25 | };
|
26 | Object.defineProperty(exports, "__esModule", { value: true });
|
27 | exports.PreferenceServiceImpl = exports.PreferenceProviderProvider = exports.PreferenceService = exports.PreferenceChangeImpl = exports.PreferenceScope = void 0;
|
28 |
|
29 | const inversify_1 = require("inversify");
|
30 | const common_1 = require("../../common");
|
31 | const promise_util_1 = require("../../common/promise-util");
|
32 | const preference_provider_1 = require("./preference-provider");
|
33 | const preference_contribution_1 = require("./preference-contribution");
|
34 | const uri_1 = require("../../common/uri");
|
35 | const preference_scope_1 = require("./preference-scope");
|
36 | Object.defineProperty(exports, "PreferenceScope", { enumerable: true, get: function () { return preference_scope_1.PreferenceScope; } });
|
37 | const preference_configurations_1 = require("./preference-configurations");
|
38 | const json_1 = require("@phosphor/coreutils/lib/json");
|
39 | const preference_language_override_service_1 = require("./preference-language-override-service");
|
40 | class PreferenceChangeImpl {
|
41 | constructor(change) {
|
42 | this.change = (0, common_1.deepFreeze)(change);
|
43 | }
|
44 | get preferenceName() {
|
45 | return this.change.preferenceName;
|
46 | }
|
47 | get newValue() {
|
48 | return this.change.newValue;
|
49 | }
|
50 | get oldValue() {
|
51 | return this.change.oldValue;
|
52 | }
|
53 | get scope() {
|
54 | return this.change.scope;
|
55 | }
|
56 | get domain() {
|
57 | return this.change.domain;
|
58 | }
|
59 |
|
60 | affects(resourceUri) {
|
61 | const resourcePath = resourceUri && new uri_1.default(resourceUri).path;
|
62 | const domain = this.change.domain;
|
63 | return !resourcePath || !domain || domain.some(uri => new uri_1.default(uri).path.relativity(resourcePath) >= 0);
|
64 | }
|
65 | }
|
66 | exports.PreferenceChangeImpl = PreferenceChangeImpl;
|
67 | exports.PreferenceService = Symbol('PreferenceService');
|
68 |
|
69 |
|
70 |
|
71 |
|
72 | exports.PreferenceProviderProvider = Symbol('PreferenceProviderProvider');
|
73 | let PreferenceServiceImpl = class PreferenceServiceImpl {
|
74 | constructor() {
|
75 | this.onPreferenceChangedEmitter = new common_1.Emitter();
|
76 | this.onPreferenceChanged = this.onPreferenceChangedEmitter.event;
|
77 | this.onPreferencesChangedEmitter = new common_1.Emitter();
|
78 | this.onPreferencesChanged = this.onPreferencesChangedEmitter.event;
|
79 | this.toDispose = new common_1.DisposableCollection(this.onPreferenceChangedEmitter, this.onPreferencesChangedEmitter);
|
80 | this.preferenceProviders = new Map();
|
81 | this._ready = new promise_util_1.Deferred();
|
82 | this._isReady = false;
|
83 | }
|
84 | async initializeProviders() {
|
85 | try {
|
86 | for (const scope of preference_scope_1.PreferenceScope.getScopes()) {
|
87 | const provider = this.providerProvider(scope);
|
88 | this.preferenceProviders.set(scope, provider);
|
89 | this.toDispose.push(provider.onDidPreferencesChanged(changes => this.reconcilePreferences(changes)));
|
90 | await provider.ready;
|
91 | }
|
92 | this._ready.resolve();
|
93 | this._isReady = true;
|
94 | }
|
95 | catch (e) {
|
96 | this._ready.reject(e);
|
97 | }
|
98 | }
|
99 | init() {
|
100 | this.toDispose.push(common_1.Disposable.create(() => this._ready.reject(new Error('preference service is disposed'))));
|
101 | this.initializeProviders();
|
102 | }
|
103 | dispose() {
|
104 | this.toDispose.dispose();
|
105 | }
|
106 | get ready() {
|
107 | return this._ready.promise;
|
108 | }
|
109 | get isReady() {
|
110 | return this._isReady;
|
111 | }
|
112 | reconcilePreferences(changes) {
|
113 | const changesToEmit = {};
|
114 | const acceptChange = (change) => this.getAffectedPreferenceNames(change, preferenceName => changesToEmit[preferenceName] = new PreferenceChangeImpl(Object.assign(Object.assign({}, change), { preferenceName })));
|
115 | for (const preferenceName of Object.keys(changes)) {
|
116 | let change = changes[preferenceName];
|
117 | if (change.newValue === undefined) {
|
118 | const overridden = this.overriddenPreferenceName(change.preferenceName);
|
119 | if (overridden) {
|
120 | change = Object.assign(Object.assign({}, change), { newValue: this.doGet(overridden.preferenceName) });
|
121 | }
|
122 | }
|
123 | if (this.schema.isValidInScope(preferenceName, preference_scope_1.PreferenceScope.Folder)) {
|
124 | acceptChange(change);
|
125 | continue;
|
126 | }
|
127 | for (const scope of preference_scope_1.PreferenceScope.getReversedScopes()) {
|
128 | if (this.schema.isValidInScope(preferenceName, scope)) {
|
129 | const provider = this.getProvider(scope);
|
130 | if (provider) {
|
131 | const value = provider.get(preferenceName);
|
132 | if (scope > change.scope && value !== undefined) {
|
133 |
|
134 | break;
|
135 | }
|
136 | else if (scope === change.scope && change.newValue !== undefined) {
|
137 |
|
138 | acceptChange(change);
|
139 | }
|
140 | else if (scope < change.scope && change.newValue === undefined && value !== undefined) {
|
141 |
|
142 | change = Object.assign(Object.assign({}, change), { newValue: value, scope });
|
143 | acceptChange(change);
|
144 | }
|
145 | }
|
146 | }
|
147 | else if (change.newValue === undefined && change.scope === preference_scope_1.PreferenceScope.Default) {
|
148 |
|
149 | acceptChange(change);
|
150 | break;
|
151 | }
|
152 | }
|
153 | }
|
154 |
|
155 | const changedPreferenceNames = Object.keys(changesToEmit);
|
156 | if (changedPreferenceNames.length > 0) {
|
157 | this.onPreferencesChangedEmitter.fire(changesToEmit);
|
158 | }
|
159 | changedPreferenceNames.forEach(preferenceName => this.onPreferenceChangedEmitter.fire(changesToEmit[preferenceName]));
|
160 | }
|
161 | getAffectedPreferenceNames(change, accept) {
|
162 | accept(change.preferenceName);
|
163 | for (const overridePreferenceName of this.schema.getOverridePreferenceNames(change.preferenceName)) {
|
164 | if (!this.doHas(overridePreferenceName)) {
|
165 | accept(overridePreferenceName);
|
166 | }
|
167 | }
|
168 | }
|
169 | getProvider(scope) {
|
170 | return this.preferenceProviders.get(scope);
|
171 | }
|
172 | has(preferenceName, resourceUri) {
|
173 | return this.get(preferenceName, undefined, resourceUri) !== undefined;
|
174 | }
|
175 | get(preferenceName, defaultValue, resourceUri) {
|
176 | return this.resolve(preferenceName, defaultValue, resourceUri).value;
|
177 | }
|
178 | resolve(preferenceName, defaultValue, resourceUri) {
|
179 | const { value, configUri } = this.doResolve(preferenceName, defaultValue, resourceUri);
|
180 | if (value === undefined) {
|
181 | const overridden = this.overriddenPreferenceName(preferenceName);
|
182 | if (overridden) {
|
183 | return this.doResolve(overridden.preferenceName, defaultValue, resourceUri);
|
184 | }
|
185 | }
|
186 | return { value, configUri };
|
187 | }
|
188 | async set(preferenceName, value, scope, resourceUri) {
|
189 | const resolvedScope = scope !== null && scope !== void 0 ? scope : (!resourceUri ? preference_scope_1.PreferenceScope.Workspace : preference_scope_1.PreferenceScope.Folder);
|
190 | if (resolvedScope === preference_scope_1.PreferenceScope.Folder && !resourceUri) {
|
191 | throw new Error('Unable to write to Folder Settings because no resource is provided.');
|
192 | }
|
193 | const provider = this.getProvider(resolvedScope);
|
194 | if (provider && await provider.setPreference(preferenceName, value, resourceUri)) {
|
195 | return;
|
196 | }
|
197 | throw new Error(`Unable to write to ${preference_scope_1.PreferenceScope[resolvedScope]} Settings.`);
|
198 | }
|
199 | getBoolean(preferenceName, defaultValue, resourceUri) {
|
200 | const value = resourceUri ? this.get(preferenceName, defaultValue, resourceUri) : this.get(preferenceName, defaultValue);
|
201 |
|
202 | return value !== null && value !== undefined ? !!value : defaultValue;
|
203 | }
|
204 | getString(preferenceName, defaultValue, resourceUri) {
|
205 | const value = resourceUri ? this.get(preferenceName, defaultValue, resourceUri) : this.get(preferenceName, defaultValue);
|
206 |
|
207 | if (value === null || value === undefined) {
|
208 | return defaultValue;
|
209 | }
|
210 | return value.toString();
|
211 | }
|
212 | getNumber(preferenceName, defaultValue, resourceUri) {
|
213 | const value = resourceUri ? this.get(preferenceName, defaultValue, resourceUri) : this.get(preferenceName, defaultValue);
|
214 |
|
215 | if (value === null || value === undefined) {
|
216 | return defaultValue;
|
217 | }
|
218 | if (typeof value === 'number') {
|
219 | return value;
|
220 | }
|
221 | return Number(value);
|
222 | }
|
223 | inspect(preferenceName, resourceUri, forceLanguageOverride) {
|
224 | var _a, _b;
|
225 | const defaultValue = this.inspectInScope(preferenceName, preference_scope_1.PreferenceScope.Default, resourceUri, forceLanguageOverride);
|
226 | const globalValue = this.inspectInScope(preferenceName, preference_scope_1.PreferenceScope.User, resourceUri, forceLanguageOverride);
|
227 | const workspaceValue = this.inspectInScope(preferenceName, preference_scope_1.PreferenceScope.Workspace, resourceUri, forceLanguageOverride);
|
228 | const workspaceFolderValue = this.inspectInScope(preferenceName, preference_scope_1.PreferenceScope.Folder, resourceUri, forceLanguageOverride);
|
229 | const valueApplied = (_b = (_a = workspaceFolderValue !== null && workspaceFolderValue !== void 0 ? workspaceFolderValue : workspaceValue) !== null && _a !== void 0 ? _a : globalValue) !== null && _b !== void 0 ? _b : defaultValue;
|
230 | return { preferenceName, defaultValue, globalValue, workspaceValue, workspaceFolderValue, value: valueApplied };
|
231 | }
|
232 | inspectInScope(preferenceName, scope, resourceUri, forceLanguageOverride) {
|
233 | const value = this.doInspectInScope(preferenceName, scope, resourceUri);
|
234 | if (value === undefined && !forceLanguageOverride) {
|
235 | const overridden = this.overriddenPreferenceName(preferenceName);
|
236 | if (overridden) {
|
237 | return this.doInspectInScope(overridden.preferenceName, scope, resourceUri);
|
238 | }
|
239 | }
|
240 | return value;
|
241 | }
|
242 | getScopedValueFromInspection(inspection, scope) {
|
243 | switch (scope) {
|
244 | case preference_scope_1.PreferenceScope.Default:
|
245 | return inspection.defaultValue;
|
246 | case preference_scope_1.PreferenceScope.User:
|
247 | return inspection.globalValue;
|
248 | case preference_scope_1.PreferenceScope.Workspace:
|
249 | return inspection.workspaceValue;
|
250 | case preference_scope_1.PreferenceScope.Folder:
|
251 | return inspection.workspaceFolderValue;
|
252 | }
|
253 | (0, common_1.unreachable)(scope, 'Not all PreferenceScope enum variants handled.');
|
254 | }
|
255 | async updateValue(preferenceName, value, resourceUri) {
|
256 | const inspection = this.inspect(preferenceName, resourceUri);
|
257 | if (inspection) {
|
258 | const scopesToChange = this.getScopesToChange(inspection, value);
|
259 | const isDeletion = value === undefined
|
260 | || (scopesToChange.length === 1 && scopesToChange[0] === preference_scope_1.PreferenceScope.User && json_1.JSONExt.deepEqual(value, inspection.defaultValue));
|
261 | const effectiveValue = isDeletion ? undefined : value;
|
262 | await Promise.all(scopesToChange.map(scope => this.set(preferenceName, effectiveValue, scope, resourceUri)));
|
263 | }
|
264 | }
|
265 | getScopesToChange(inspection, intendedValue) {
|
266 | var _a;
|
267 | if (json_1.JSONExt.deepEqual(inspection.value, intendedValue)) {
|
268 | return [];
|
269 | }
|
270 |
|
271 | const allScopes = preference_scope_1.PreferenceScope.getReversedScopes();
|
272 |
|
273 | allScopes.pop();
|
274 | const isScopeDefined = (scope) => this.getScopedValueFromInspection(inspection, scope) !== undefined;
|
275 | if (intendedValue === undefined) {
|
276 | return allScopes.filter(isScopeDefined);
|
277 | }
|
278 | return [(_a = allScopes.find(isScopeDefined)) !== null && _a !== void 0 ? _a : preference_scope_1.PreferenceScope.User];
|
279 | }
|
280 | overridePreferenceName(options) {
|
281 | return this.preferenceOverrideService.overridePreferenceName(options);
|
282 | }
|
283 | overriddenPreferenceName(preferenceName) {
|
284 | return this.preferenceOverrideService.overriddenPreferenceName(preferenceName);
|
285 | }
|
286 | doHas(preferenceName, resourceUri) {
|
287 | return this.doGet(preferenceName, undefined, resourceUri) !== undefined;
|
288 | }
|
289 | doInspectInScope(preferenceName, scope, resourceUri) {
|
290 | const provider = this.getProvider(scope);
|
291 | return provider && provider.get(preferenceName, resourceUri);
|
292 | }
|
293 | doGet(preferenceName, defaultValue, resourceUri) {
|
294 | return this.doResolve(preferenceName, defaultValue, resourceUri).value;
|
295 | }
|
296 | doResolve(preferenceName, defaultValue, resourceUri) {
|
297 | const result = {};
|
298 | for (const scope of preference_scope_1.PreferenceScope.getScopes()) {
|
299 | if (this.schema.isValidInScope(preferenceName, scope)) {
|
300 | const provider = this.getProvider(scope);
|
301 | if (provider) {
|
302 | const { configUri, value } = provider.resolve(preferenceName, resourceUri);
|
303 | if (value !== undefined) {
|
304 | result.configUri = configUri;
|
305 | result.value = preference_provider_1.PreferenceProvider.merge(result.value, value);
|
306 | }
|
307 | }
|
308 | }
|
309 | }
|
310 | return {
|
311 | configUri: result.configUri,
|
312 | value: result.value !== undefined ? (0, common_1.deepFreeze)(result.value) : defaultValue
|
313 | };
|
314 | }
|
315 | getConfigUri(scope, resourceUri, sectionName = this.configurations.getConfigName()) {
|
316 | const provider = this.getProvider(scope);
|
317 | if (!provider || !this.configurations.isAnyConfig(sectionName)) {
|
318 | return undefined;
|
319 | }
|
320 | const configUri = provider.getConfigUri(resourceUri, sectionName);
|
321 | if (configUri) {
|
322 | return configUri;
|
323 | }
|
324 | return provider.getContainingConfigUri && provider.getContainingConfigUri(resourceUri, sectionName);
|
325 | }
|
326 | };
|
327 | __decorate([
|
328 | (0, inversify_1.inject)(preference_contribution_1.PreferenceSchemaProvider),
|
329 | __metadata("design:type", preference_contribution_1.PreferenceSchemaProvider)
|
330 | ], PreferenceServiceImpl.prototype, "schema", void 0);
|
331 | __decorate([
|
332 | (0, inversify_1.inject)(exports.PreferenceProviderProvider),
|
333 | __metadata("design:type", Function)
|
334 | ], PreferenceServiceImpl.prototype, "providerProvider", void 0);
|
335 | __decorate([
|
336 | (0, inversify_1.inject)(preference_configurations_1.PreferenceConfigurations),
|
337 | __metadata("design:type", preference_configurations_1.PreferenceConfigurations)
|
338 | ], PreferenceServiceImpl.prototype, "configurations", void 0);
|
339 | __decorate([
|
340 | (0, inversify_1.inject)(preference_language_override_service_1.PreferenceLanguageOverrideService),
|
341 | __metadata("design:type", preference_language_override_service_1.PreferenceLanguageOverrideService)
|
342 | ], PreferenceServiceImpl.prototype, "preferenceOverrideService", void 0);
|
343 | __decorate([
|
344 | (0, inversify_1.postConstruct)(),
|
345 | __metadata("design:type", Function),
|
346 | __metadata("design:paramtypes", []),
|
347 | __metadata("design:returntype", void 0)
|
348 | ], PreferenceServiceImpl.prototype, "init", null);
|
349 | PreferenceServiceImpl = __decorate([
|
350 | (0, inversify_1.injectable)()
|
351 | ], PreferenceServiceImpl);
|
352 | exports.PreferenceServiceImpl = PreferenceServiceImpl;
|
353 |
|
\ | No newline at end of file |