Skip to content

Commit bd86c6e

Browse files
committed
Send only explicitly set ada.* VS Code settings
1 parent 20c7867 commit bd86c6e

File tree

1 file changed

+59
-4
lines changed

1 file changed

+59
-4
lines changed

integration/vscode/ada/src/clients.ts

Lines changed: 59 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
import { existsSync } from 'fs';
22
import * as vscode from 'vscode';
33
import {
4+
DidChangeConfigurationNotification,
45
LanguageClient,
56
LanguageClientOptions,
67
MessageSignature,
78
ServerOptions,
9+
State,
810
} from 'vscode-languageclient/node';
911
import { logger } from './extension';
1012
import { logErrorAndThrow, setTerminalEnvironment } from './helpers';
@@ -124,16 +126,69 @@ export function createClient(
124126
// Register the server for ada sources documents
125127
documentSelector: [{ scheme: 'file', language: id }],
126128
synchronize: {
127-
// Synchronize the setting section 'ada' to the server
128-
configurationSection: 'ada',
129129
// Notify the server about file changes to Ada files contain in the workspace
130130
fileEvents: vscode.workspace.createFileSystemWatcher(pattern),
131131
},
132-
// Include the ada.* settings in the initialize request sent to the server
133-
initializationOptions: () => ({ ada: vscode.workspace.getConfiguration('ada') }),
132+
initializationOptions: () =>
133+
/**
134+
* Only include the settings that are explicitly set in one of the
135+
* VS Code scopes to avoid unintentionally overriding ALS settings
136+
* from .als.json or other applicable configuration files.
137+
*/
138+
({ ada: getExplicitlySetConfiguration() }),
134139
};
140+
135141
// Create the language client
136142
const client = new AdaLanguageClient(id, name, serverOptions, clientOptions);
143+
144+
context.subscriptions.push(
145+
vscode.workspace.onDidChangeConfiguration(async (e) => {
146+
if (e.affectsConfiguration('ada') && client.state === State.Running) {
147+
await client.sendNotification(DidChangeConfigurationNotification.type, {
148+
settings: {
149+
ada: getExplicitlySetConfiguration(),
150+
},
151+
});
152+
}
153+
}),
154+
);
155+
137156
client.serverEnv = serverEnv;
138157
return client;
139158
}
159+
160+
/**
161+
* ALS settings can come from configuration files (e.g. .als.json) and from VS
162+
* Code.
163+
*
164+
* Settings from config files are loaded first. To avoid overwriting them
165+
* unintentionally, settings from VS Code should only be sent if they were
166+
* explicitly set in one of the VS Code configuration scopes.
167+
*
168+
* This function returns that set of settings.
169+
*
170+
* @returns a dictionary of ada.* settings that have been explicitly set in one
171+
* of the VS Code configuration scopes.
172+
*/
173+
function getExplicitlySetConfiguration(): { [k: string]: unknown } {
174+
// Get all ada.* settings
175+
const adaConfig = vscode.workspace.getConfiguration('ada');
176+
const explicitSettings = Object.fromEntries(
177+
Object.entries(adaConfig).filter(([key]) => {
178+
// Filter to settings that are explicitly set
179+
const info = adaConfig.inspect(key);
180+
return (
181+
info &&
182+
[
183+
info.globalValue,
184+
info.workspaceValue,
185+
info.workspaceFolderValue,
186+
info.globalLanguageValue,
187+
info.workspaceLanguageValue,
188+
info.workspaceFolderLanguageValue,
189+
].some((v) => v !== undefined)
190+
);
191+
}),
192+
);
193+
return explicitSettings;
194+
}

0 commit comments

Comments
 (0)