C# code formatting settings in VS Code and OmniSharp

I quite often get or see questions about configuring C# code formatting settings for Visual Studio Code.

OmniSharp (the open source Roslyn-based technology that powers C# language services) in VS Code exposes a rich set of code formatting settings which you can use to tailor and customize your C# experience.

Let’s have a look at how you can use them.

Tabs/spaces

First let’s tackle tabs vs spaces, because that’s probably the most important thing. A cool new feature in Visual Studio Code C# extension 1.6 (released just before Christmas) is that it can now automatically infer your “tabs vs spaces” and “tab size” settings from Visual Studio Code into OmniSharp.

This means, that configuring the following general editor settings under Preferences > UserSettings, i.e.:

will be enough for VS Code C# extension to apply these settings to format C# code. You can also switch off this new OmniSharp behavior by setting omnisharp.useEditorFormattingSettings: false.

So this is great, very convenient, but what if you are interested in more advanced control over C# formatting?

Customizing OmniSharp configuration

Well, aside from this new feature, OmniSharp allows you to modify C# formatting options in a couple of ways.

First and foremost, it’s important to mention that OmniSharp exposes a JSON configuration file which surfaces all of the code formatting capabilities of Roslyn. The file schema is stored at JSON Schema Store here, and the default settings are shown below.

All the properties should be rather self descriptive and they give you a very deep and granular control over the appearance of your C# code.

At startup, OmniSharp obtains the configuration options using the following order of precedence (each of the subsequent configuration sources, can overwrite any of the settings set by the previous source):

1) The built-in config.json – which is located in the OmniSharp folder inside the C# extension folder itself (for example, on a Mac that’s ~/.vscode/extensions/ms-vscode.csharp-1.6.0/bin/omnisharp.).
If the file doesn’t exist, you can simply create it.

You could use the schema I just posted above and the config.json file to provide global C# formatting settings, however bear in mind that it will be overwritten on next extension update.

2) Environment variables – you could pass environment variables into the OmniSharp process to control the formatting settings. However, because it’s the C# extension that starts the process on your behalf in VS Code, then this option is not really applicable for custom use at the moment.

3) Command line arguments – formatting settings can be passed as arguments when starting OmniSharp. Similarly as in the previous point – this means you can’t really leverage this feature as a user, as it’s C# extension that controls it.

Interstingly, this is the technique used by VS Code C# extension to share VS Code editor settings with OmniSharp (as described earlier).

4) An omnisharp.json file located in the working directory which OmniSharp has been pointed at

The highest order of precedence is given to omnisharp.json located in the folder which OmniSharp server is looking at (so project folder specific).

This doesn’t need to be a full copy of config.json – it can contain only individual settings, and they will be merged into the settings provided by config.json, environment variables and command line args, and simply overwrite the matching ones.

For example, to override the default formattingOptions > SpaceAfterCast setting of (false), you should create the following omnisharp.json file in the folder of your project:

Limitations & Future

At the moment any change in formatting settings is only picked up by OmniSharp at startup of the OmniSharp process.

This means any change in the editor settings, in config.json or omnisharp.json requires an OmniSharp restart. You can trigger that by pressing ctrl+shift+p (cmd+shift+p on Mac) and choosing “Restart Omnisharp” option.

This will change in the future and is already tracked in the OmniSharp repo.

Additionally, the plan is to provide persistent global omnisharp.json file – at the moment the only “global” option is to use config.json, which is not ideal as that file gets overwritten on extension updates.

If you have any further feedback, please log an issue in the OmniSharp repo.

Be Sociable, Share!

  • http://www.gameosaur.com/ neoKushan

    This was a good read, but it was a bit painful due to the size of the StrathWeb banner when I attempt to zoom the page in. It takes up over 1/3 of the page and I’m only at 150% zoom.

    See: https://i.imgur.com/jWTXN2y.png