Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

For workspace.getConfiguration: how do I get a setting from the Multi Root Workspace file (.code-workspace)

With WorkspaceConfiguration.update(...) you can specify that the setting needs to be written to the ConfigurationTarget.Workspace. This updates the Workspace .code-workspace file if Multi Root or it updates the WorkspaceFolder .vscode/settings.json if opened a single folder.

Now I want to get the current setting from the Workspace (.code-workspace or .vscode/settings.json).

What is the ConfigurationScope I need to set in the call to workspace.getConfiguration?

What is the URI I need to use? The TextDocument and WorkspaceFolder will always get me the value from .vscode/settings.json

like image 965
rioV8 Avatar asked Oct 15 '25 17:10

rioV8


2 Answers

I found the method WorkspaceConfiguration.inspect. It shows the unmerged parts of the setting.

In my extension I have setup a configuration setting with "scope": "resource"

      "configuration": {
        "title": "Test Config",
        "properties": {
          "extension.someconfig": {
            "type": "string",
            "scope": "resource",
            "description": "some test configuration setting",
            "default": "default-value"
          }
        }
      }

Defined a value for the Global/User level: "extension.someconfig": "user-value"

Setup a command to log a few things depending on the current file. I don't log the language parts of inspect because I don't use them (and where do you define them).

    let uri = vscode.window.activeTextEditor.document.uri;
    let config = vscode.workspace.getConfiguration('extension', uri);
    console.log('---------');
    console.log('someconfig:', config.get('someconfig'));
    let inspect = config.inspect('someconfig');
    console.log('inspect.key:', inspect.key);
    console.log('inspect.defaultValue:', inspect.defaultValue);
    console.log('inspect.globalValue:', inspect.globalValue);
    console.log('inspect.workspaceValue:', inspect.workspaceValue);
    console.log('inspect.workspaceFolderValue:', inspect.workspaceFolderValue);

I have setup a test MR Workspace:

testconfig
  + project1
  |   + .vscode
  |   |   + settings.json    // "extension.someconfig": "project1-value"
  |   + main.py
  + project2
  |   + .vscode
  |   |   + settings.json    // "extension.someconfig": "project2-value"
  |   + main.py
  + project3
  |   + .vscode
  |   |   + settings.json    // "extension.someconfig": "project3-value"
  |   + main.py
  + testconfig.code-workspace      // "extension.someconfig": "workspace-value"

When I log the setting for a non-scoped getConfiguration:

let config = vscode.workspace.getConfiguration('extension');
All 3 main.py files give:

someconfig: workspace-value
inspect.key: extension.someconfig
inspect.defaultValue: default-value
inspect.globalValue: user-value
inspect.workspaceValue: workspace-value
inspect.workspaceFolderValue: undefined

When using the scoped getConfiguration:

let config = vscode.workspace.getConfiguration('extension', uri);
Common for all 3 main.py files:
inspect.key: extension.someconfig
inspect.defaultValue: default-value
inspect.globalValue: user-value
inspect.workspaceValue: workspace-value

--------- project1/main.py:
someconfig: project1-value
inspect.workspaceFolderValue: project1-value
--------- project2/main.py:
someconfig: project2-value
inspect.workspaceFolderValue: project2-value
--------- project3/main.py:
someconfig: project3-value
inspect.workspaceFolderValue: project3-value

When scoped to the WorkspaceFolder

let uri = vscode.window.activeTextEditor.document.uri;
let workspaceFolder = vscode.workspace.getWorkspaceFolder(uri);
let config = vscode.workspace.getConfiguration('extension', workspaceFolder);

The results are the same as for file scoped.


When the merged setting is determined the workspaceFolderValue is undefined for the non-scoped getConfiguration call.

The inspect call uses the same scope as the getConfiguration call that returned the WorkspaceConfiguration

like image 128
rioV8 Avatar answered Oct 18 '25 12:10

rioV8


I'll try to explain my limited understanding of what is going on here (as a relative rookie to extension coding).

Say I have these two commands:

const codeWorkspaceConfigs = vscode.workspace.getConfiguration('launch'); // no scope argument

const launchConfigs = vscode.workspace.getConfiguration('launch', workSpace.uri);

with no scope argument I get the launch settings from that *.code-workspace file only. Even if the <someName>.code-workspace file is in some weird unrelated place from the project's code. So that I believe is the short answer to your question. But it is more interesting.

Say I do have a 'launch.json ' file in a workspaceFolder, then on calling the second workspaced-scope getConfiguration() I get only that workspaceFolder's launch.json settings. Whether there is a code-workspace with launch settings or not.

But if there is a .code-workspace but no workspaceFolder launch.json then the second workspaced-scoped call gets me the .code-workspace settings!

As it should, since now there are no local settings anymore to override the more global .code-workspace settings.

Initially I misunderstand that ConfigurationScope parameter.

ConfigurationScope: Uri | TextDocument | WorkspaceFolder | {languageId: string, uri: Uri}

I thought that the WorkspaceFolder would get the settings actually listed in that WorksapceFolder's .vscode/settings.json but then why would there be a TextDocument or Uri option (where there wouldn't necessarily be any settings. But you are limiting the scope to those settings that apply to that document or uri - and that is the result of local settings overriding global settings, for example.

const codeWorkspaceConfigs = vscode.workspace.getConfiguration('launch'); // no scope argument

for me with this non-scoped version I get the .code-workspace settings only. While ConfigurationScope is an optional parameter to the getConfiguration() command I don't see any place that tells you what will happen (what the scope might be) if it is omitted. Maybe that is obvious to others, but it isn't to me.

To get a specific setting from .code-workspace this works for me:

let settings = vscode.workspace.getConfiguration().get('commandAlias.category');

and that setting is in both .code-workspace and in user settings.json. And it doesn't seem to matter what file is active at the time the configuration is retrieved.

getting code-workspace settings

like image 24
Mark Avatar answered Oct 18 '25 12:10

Mark