Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

XDG support on windows #6747

Open
dsisnero opened this issue Apr 13, 2023 · 28 comments
Open

XDG support on windows #6747

dsisnero opened this issue Apr 13, 2023 · 28 comments
Labels
A-core Area: Helix core improvements C-enhancement Category: Improvements S-needs-discussion Status: Needs discussion or design.

Comments

@dsisnero
Copy link

I am a windows user and I set the XDG environment variables. On windows, helix doesn't honor these environment variables so it always goes to %APPDATA%, My %APPDATA% drive, is full so I changed XDG directories to a different drive. I think that if the variables are set, even on windows, should allow to follow XDG directories and if not should revert back to %APPDATA%

@kirawi
Copy link
Member

kirawi commented Apr 28, 2023

I'd suggest opening an issue to the upstream library: https://github.com/lunacookies/etcetera

@utkarshgupta137
Copy link

The etcetera library is working as intended. The problem is that helix uses choose_base_strategy function from etcetera which uses Windows' Known Folder API on Windows and XDG on Unix. If you want to instead use XDG variables on Windows too, you can call base_strategy::Xdg::new() instead of choose_base_strategy() here: https://github.com/helix-editor/helix/blob/23.03/helix-loader/src/lib.rs#L110

@henriqpsantos
Copy link

Hi. Any updates on this? IMO, the config locations should be consistent across OS, when the XDG_ environment variables are set.

@kirawi kirawi added C-enhancement Category: Improvements A-core Area: Helix core improvements S-needs-discussion Status: Needs discussion or design. and removed upstream labels Jun 2, 2023
@kirawi
Copy link
Member

kirawi commented Jun 2, 2023

The XDG and Windows strategies can't co-exist using the types in the crate. XDG would probably have to be implemented manually for Windows so it can fall back to the Windows strategy when the environment variables aren't set.

@utkarshgupta137
Copy link

The existence of the XDG variables isn't supposed to determine whether or not the XDG spec is followed i.e. ~/.config should be checked if $XDG_CONFIG_HOME isn't defined. You need to decide if the XDG or the Windows spec will be the primary location for Helix.

So the flow can be like this:

  • Check Xdg::config_dir() & use it if it exists
  • Check Windows::config_dir() & use it if it exists
  • If you want Xdg spec to be the primary location, then Helix should create Xdg::config_dir(), otherwise Windows::config_dir()

@kirawi
Copy link
Member

kirawi commented Jun 3, 2023

The Windows spec should be the default since it's what most users will expect (i.e #7084). According to the spec, I don't think I'm wrong either. It says that if the environment variables aren't defined, it should fall back to the system default, which would be defined by the Windows spec.

i.e.

If $XDG_CONFIG_HOME is either not set or empty, a default equal to $HOME/.config should be used.

@dsisnero
Copy link
Author

dsisnero commented Jun 3, 2023 via email

@kirawi
Copy link
Member

kirawi commented Jun 3, 2023

Yes, that is what I mean.

@utkarshgupta137
Copy link

The Windows spec should be the default since it's what most users will expect (i.e #7084).

If you want Windows to be the primary/recommended location, then flow should be:

  • Check Windows::config_dir() & use it if it exists
  • Check Xdg::config_dir() & use it if it exists
  • Use Windows::config_dir()

It shouldn't just be use the location provided by $XDG_CONFIG_HOME if it is defined. You should also check ~/.config if $XDG_CONFIG_HOME isn't defined. Otherwise, if a user who isn't aware of XDG variables (which is likely the vast majority of Windows users), suddenly defines or stops defining $XDG_CONFIG_HOME, their configs would stop working.

According to the spec, I don't think I'm wrong either. It says that if the environment variables aren't defined, it should fall back to the system default, which would be defined by the Windows spec.

The defaults are defined by the XDG spec itself, as you quoted yourself:

If $XDG_CONFIG_HOME is either not set or empty, a default equal to $HOME/.config should be used.

It doesn't say that the OS should specify the default.

@kirawi
Copy link
Member

kirawi commented Jun 4, 2023

It is a little ambiguous as it could also mean "equivalent," and most implementations interpret it as such (i.e. Racket or GTK glib). A hard-coded default would be pretty useless and not user-friendly (what benefit is there to forcing users to use these unix paths instead of the Windows paths that they already know?). The flow should be this:

  • If there is a set non-empty XDG environment variable and it points to a valid absolute path, it should be used.
  • Otherwise, use the Windows known files specification to find the OS-defined folder.

@utkarshgupta137
Copy link

It is a little ambiguous as it could also mean "equivalent," and most implementations interpret it as such (i.e. Racket or GTK glib). A hard-coded default would be pretty useless and not user-friendly (what benefit is there to forcing users to use these unix paths instead of the Windows paths that they already know?). The flow should be this:

* If there is a set non-empty XDG environment variable and it points to a valid absolute path, it should be used.

* Otherwise, use the Windows known files specification to find the OS-defined folder.

Hmmm. I don't use CLI on Windows, so I don't have strong opinions. I assumed it worked similarly to macOS because CLIs/TUIs on macOS follow "proper" XDG spec i.e. they default to ~/.config & such and fallback to ~/Library/Application Support only if they supported that location in the past.

@henriqpsantos
Copy link

henriqpsantos commented Jun 5, 2023

I like how WezTerm handles this problem, and it also sounds more intuitive to me -- working from more specific to more general in terms of priority:
1- CLI argument
2- Program-specific environment variable (i.e. $HELIX_CONFIG_DIR)
3- File on the same directory as executable
4- XDG_ environment variables
5- $HOME\.config\helix.toml
6- $HOME\.helix.toml
Add a step 4.5 or replace 5/6 for windows, using %APPDATA% folders instead of $HOME. The way that I find more logical is to merge the first existing (valid path) file with the global config.

It is a little ambiguous as it could also mean "equivalent," and most implementations interpret it as such (i.e. Racket or GTK glib). A hard-coded default would be pretty useless and not user-friendly (what benefit is there to forcing users to use these unix paths instead of the Windows paths that they already know?). The flow should be this:

* If there is a set non-empty XDG environment variable and it points to a valid absolute path, it should be used.

* Otherwise, use the Windows known files specification to find the OS-defined folder.

IMO hard-coded paths such as $HOME or %APPDATA% should only be used as a last priority.

@kirawi
Copy link
Member

kirawi commented Jun 5, 2023

#2135 for that. This issue is specifically about supporting XDG on Windows.

@henriqpsantos
Copy link

I'm on windows. The standard, in my opinion, should be to support them for consistency across platforms. The issue for me is that the config directory on windows is hard-coded or must be specified by way of a CLI argument (or a symlink, but that is supported anyway).

@kirawi
Copy link
Member

kirawi commented Jun 6, 2023

Yes, the linked PR covers that. Even so, that PR does not support XDG on Windows. So this issue can be seen as an extension of that. To rephrase, this issue is specifically about using the XDG environment variables to find the config folders within the scope of the current system. What you're talking about falls outside of this.

@go2null
Copy link

go2null commented Dec 19, 2023

#6747 (comment)

Hmmm. I don't use CLI on Windows, so I don't have strong opinions. I assumed it worked similarly to macOS because CLIs/TUIs on macOS follow "proper" XDG spec i.e. they default to ~/.config & such and fallback to ~/Library/Application Support only if they supported that location in the past.

#6747 (comment)

So the flow can be like this:
* Check Xdg::config_dir() & use it if it exists
* Check Windows::config_dir() & use it if it exists
* If you want Xdg spec to be the primary location, then Helix should create Xdg::config_dir(), otherwise Windows::config_dir()

This seems to most obvious solution.

It's what I expect. I pull my dotfiles into my MSYS2 environment and everything should work.
(Even vim can follow XDG 😄 )

@dsisnero
Copy link
Author

What is the status on this? How can I change my config in runtime directories on windows without using a command line switch?

@tgross35
Copy link
Contributor

The behavior for Mac is also a bit weird. Usually if configuration uses system-native config paths then it is ~/Library/Application Support/myapp on Mac, %APPDATA%/myapp on Windows, and ~/.config/myapp on Linux (this is what the dirs crate does). Or, ~/.config/myapp is used on all three platforms, which isn't uncommon for CLI apps.

It is kind of unusual that Helix uses AppData on WIndows but ~/.config on Mac. IMO either the system native path should be used on all platforms (i.e., change the Mac default location to ~/Library/Application Support), or use ~/.config on all platforms (i.e., change Windows to accept this).

Or, since deprecating config locations is unlikely, allow either native locations or ~/.config and error (or at least warn) if config exists in both.

@kirawi
Copy link
Member

kirawi commented Jan 19, 2024

According to the upstream library etcetera, the convention is to use XDG for cli apps on all non-Windows platforms: https://docs.rs/etcetera/latest/etcetera/base_strategy/fn.choose_base_strategy.html

We could probably check if other editors like Vim/Kakoune do the same.

@tgross35
Copy link
Contributor

I think the current config is consistent with neovim (On Mac it uses ~/.config, and it looks like WIndows is AppData https://jdhao.github.io/2018/11/15/neovim_configuration_windows/). Vim is stubborn and always ~/.vimrc (list of XDG support https://wiki.archlinux.org/title/XDG_Base_Directory).

I think many CLI apps that predate Rust usually use ~/.config or ~/.appname on all platforms, such as git. A lot of Rust apps seem to punt to dirs, which does AppData on Windows and ~/Libraries/Application Support on Mac, such as evcxr and zoxide. Alacritty and fd do the same as Helix link1 link2, but Wezterm is always ~/.config link.

What a mess... In any case, I feel that it isn't a bad idea to check ~/.config on Windows too and at least warn the user that config isn't read from that location.

@utkarshgupta137
Copy link

According to the upstream library etcetera, the convention is to use XDG for cli apps on all non-Windows platforms: https://docs.rs/etcetera/latest/etcetera/base_strategy/fn.choose_base_strategy.html

We could probably check if other editors like Vim/Kakoune do the same.

Again, etcetera only contains a helper function for this pattern, since it seems to be a common pattern. If you want, you can use Xdg directly.

@dsisnero
Copy link
Author

As long as the option is there to change it without a command line switch and so it is not hardcoded. Just pick APPDATA or HOME/.config as fallback but give the ability to use XDG if that is set. I think it should fall back to os convention but not as long a we can change it with ENV variable it doesn't matter too much

@dsisnero
Copy link
Author

Any update on this?

@mr-valente
Copy link

mr-valente commented Sep 25, 2024

Would love this as I also have XDG environment variables set on Windows. For now I'm just aliasing hx -c $env:XDG_CONFIG_HOME/helix/config.toml as hlx in my powershell profile, but obviously would prefer native XDG support.

@henry-js
Copy link

henry-js commented Dec 6, 2024

Function Start-Helix ([string[]]$arguments) { hx -c "$env:XDG_CONFIG_HOME\helix\config.toml" (-join $arguments) }
Set-Alias -Name hlx -Value Start-Helix

@dsisnero
Copy link
Author

dsisnero commented Dec 6, 2024 via email

@henry-js
Copy link

henry-js commented Dec 7, 2024

To clarify, will the proposed change allow all configuration files including languages & themes to use XDG? or just the config.toml file solely?

@mr-valente
Copy link

mr-valente commented Dec 7, 2024

It would make sense, and indeed be very nice to allow all configuration files (including languages and themes) to use XDG as @henry-js suggested. Indeed, with themes, even if you run hx -c "$env:XDG_CONFIG_HOME\helix\config.toml" Helix will still only look in %AppData%\helix\themes for themes on Windows, which is quite inconvenient if you have custom themes. The documentation says it looks in ~/.config/helix/themes on Linux, but our workaround of aliasing with -c doesn't actually set the Helix home directory it just specifically picks the config.toml file from the location specified and continues to use %AppData%\helix as the Helix home directory.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-core Area: Helix core improvements C-enhancement Category: Improvements S-needs-discussion Status: Needs discussion or design.
Projects
None yet
Development

No branches or pull requests

8 participants