Skip to content

Add XDG_DATA_HOME as default storage location#353

Open
rankynbass wants to merge 11 commits into
goatcorp:mainfrom
rankynbass:add-xdg-spec
Open

Add XDG_DATA_HOME as default storage location#353
rankynbass wants to merge 11 commits into
goatcorp:mainfrom
rankynbass:add-xdg-spec

Conversation

@rankynbass

@rankynbass rankynbass commented May 5, 2026

Copy link
Copy Markdown
Contributor

This patch adds $XDG_DATA_HOME (default: ~/.local/share) as the default location for the xlcore folder. This (better) obeys the XDG desktop specification. Ideally, the ini files would go in $XDG_CONFIG_HOME/xlcore (default: ~/.config), but that would require extensive reworking of the storage system, and isn't really worth it. I'm using $XDG_DATA_HOME because $XDG_CONFIG_HOME really shouldn't be used to store large amounts of data. It's not uncommon for people to back up ~/.config to a git repo, for example.

  • $XDG_DATA_HOME/xlcore will be used if it exists
  • ~/.xlcore will be the fallback if the above is not found and ~/.xlcore is found
  • $XDG_DATA_HOME/xlcore will be created and used if neither of the above are true
  • $XL_USER_DIR / $XL_USERDIR / $XL_PATH can be used to override the default storage location. Necessary for dual-boxing.

Edit to add:
In the interest of full disclosure, I think VSCode has enabled AI generation by default, because it kept finishing my code blocks and comments for me. I did not ask it to do anything, or prompt it, it just kept completing my code blocks, and occasionally adding extra parenthesis and semicolons in the wrong spot. I tried turning it off, but it kept "fixing" my code. So a bit of this is technically AI generated, though it is what I intended to do.

It is very annoying, and I think I'm going to ditch VSCode now, because sometimes I hit tab to indent, and it decides to generate a new function that doesn't work or even do anything useful.

* XDG_DATA_HOME/xlcore will be used if it exists
* ~/.xlcore will be the fallback if the above is not found and ~/.xlcore is found
* XDG_DATA_HOME/xlcore will be created and used if neither of the above are true
@rnaissance

Copy link
Copy Markdown
Contributor

i dont know if there was already an issue associated with this, but linking related issue which this appears to address: #177


really glad to see someone updating this project to use the xdg basedir spec!

a few thoughts on the current implementation follow. i am not a reviewer/codeowner for this project, so be advised my thoughts here are not review blockers in any way. with that in mind:

  • $XL_USER_DIR / $XL_USERDIR / $XL_PATH can be used to override the default storage location. Necessary for dual-boxing.

a purpose of the xdg basedir specification is to enable relocating these by providing $XDG_CONFIG_HOME, $XDG_DATA_HOME, etc. in the environment, so this would effectively providing an extra nonstandard way to accomplish the same thing. is there a reason to provide these extra vars, instead of directing people to use the xdg basedir specified env vars?

  • $XDG_DATA_HOME/xlcore will be used if it exists
    [...]
  • $XDG_DATA_HOME/xlcore will be created and used if neither of the above are true

a suggestion to consider for the subdirectory name: instead of using the appname, xlcore, use the application ID, dev.goats.xivlauncher. while this is not something required by the xdg basedir specification, there are reasons to consider this:

  • dev.goats.xivlauncher is already a unique identifier used by the project (e.g., the flatpak https://flathub.org/en/apps/dev.goats.xivlauncher )
  • this is becoming an increasingly common convention that helps avoid the risk of name collisions. to name a couple of projects that i'm aware of off the top of my head that have adopted it, gnome and flutter have been adopting it
  • the likely reason that many existing applications don't do this yet because they were created before that convention was established and migrating later is a pain, so right now is an opportunity to get it done before a new location becomes established. plus then it'll be consistent if at some point in the future the desktop file is updated to use application ID (see desktop entry specification section 2 "File Naming" and/or this project starts using xdg desktop portal

@rankynbass

Copy link
Copy Markdown
Contributor Author

I have no great opinion one way or the other about using dev.goats.xivlauncher as the folder name; I was simply following the naming scheme currently in use. However, I do see a potential benefit to using dev.goats.xivlauncher: nobody is likely to have created this folder before.

I have added this patch to my xivlauncher-rb fork, and for several people, the launcher has ended up using XDG_DATA_HOME/xlcore when they already had a ~/.xlcore and (supposedly) did not have XDG_DATA_HOME/xlcore. I suspect that these users had at one point created the XDG_DATA_HOME/xlcore folder with XL_PATH/XL_USERDIR and forgot about it.

As for the use of XL_USERDIR, its purpose is both for backwards compatibility for people currently using it, and also for dual-boxing. You need separate prefixes and ffxivConfig folders to launch two copies of the game with xivlauncher. So you could have your main config at XDG_DATA_HOME/dev.goats.xivlauncher, and your second config in the XDG_DATA_HOME/dev.goats.xivlauncher.2 folder, for example.

storage = new Storage(APP_NAME);
// XDG will handle the storage path for Linux and Mac. It will fall back to the old ~/.xlcore path on Linux and Mac if it exists and the XDG path does not.
var userDir = XDG.GetStoragePath(APP_NAME, CoreEnvironmentSettings.UserDir);
storage = new Storage(APP_NAME, userDir);

@marzent marzent May 20, 2026

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are we not packing all that logic into the Storage class, where it makes sense to be?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here's a PR for that: goatcorp/FFXIVQuickLauncher#1867

In the mean time, I'd still like to get this added, since it can take a very long time to get anything linux-related merged into XL.

Comment thread src/XIVLauncher.Core/XDG.cs Outdated

static XDG()
{
if (Environment.OSVersion.Platform == PlatformID.Win32NT)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

XDG as a concept mostly makes sense on Linux...

Comment thread src/XIVLauncher.Core/XDG.cs Outdated
}
else if (platform == Platform.Linux || platform == Platform.Mac)
{
if (Directory.Exists(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), appName)))

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

On macOS Environment.SpecialFolder doesn't give you XDG paths, but rather system native locations, such as $HOME/Library/Application Support etc.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

According to the documentation I was reading, $HOME/Library/Application Support/{appName} (or just $HOME/Library/{appname})is the closest there is to XDG_DATA_HOME, and this at least doesn't pollute the ~/Library folder directly. I could switch to using environment variables directly, and that would create ~/.local/share/dev.goats.xlcore for Mac users. Not sure if xlcore even compiles for macos, though.

Also move ~/.xlcore to XDG_DATA_HOME/dev.goats.xlcore if possible
If not, fall back to using ~/.xlcore
Comment thread src/XIVLauncher.Core/XDG.cs Outdated
}
else if (platform == Platform.Linux || platform == Platform.Mac)
{
var xdgStoragePath = new DirectoryInfo(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), $"dev.goats.{appName}"));

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the application id used for the flatpak is dev.goats.xivlauncher, not dev.goats.xlcore

* Rename XDG to StorageHelper
* Set appname to dev.goats.xivlauncher instead of xlcore
@rankynbass

Copy link
Copy Markdown
Contributor Author

Switched to using goatcorp/FFXIVQuickLauncher#1867 for the submodule, and renamed a few things. If ~/.xlcore is found and is on the same volume, it will be moved to ~/.local/share/dev.goats.xivlauncher. If it is on a different volume, the move is considered to be too slow, and it will be used in place.

Because DirectoryInfo.MoveTo() throws an error if the locations are
not on the same volume. No need to check drives and paths and all that
@rankynbass

Copy link
Copy Markdown
Contributor Author

I think this is ready to go, as soon as PR 1867 is merged into XL.Common. However, the flatpak release will need --filesystem=xdg-data/dev.goats.xivlauncher added to the finish-args in the flatpak yml file. Otherwise XDG_DATA_HOME will point to ~/.var/app/dev.goats.xivlauncher/data/, which is inconvenient if the user wants to switch to a native install or the AppImage.

@rankynbass

Copy link
Copy Markdown
Contributor Author

After a bit more poking around and testing, flatpak just seems to be a problem in general. The --filesystem=xdg-data/dev.goats.xivlauncherdoesn't really work as expected, since it doesn't allow xlcore to *create* or move ~/.xlcore to the ~/.local/share/dev.goats.xivlauncher folder, just creates a bind mount to it if it *does* exist. And if the:create` option is added, then the folder will be created empty, and used instead of an existing ~/.xlcore.

It's probably better to not use the filesystem option.

After moving ~/.xlcore to XDG_DATA_HOME/d.g.x, make a symlink
back at ~/.xlcore pointing to the new location.
Disable with XL_MAKE_SYMLINK=0. In the future, we can change
this to off by default, so symlinks will only be created on
demand. For now, having ~/.xlcore is probably best for steamdeck
users.
@rankynbass

Copy link
Copy Markdown
Contributor Author

This patch now does the following:

  • XDG_DATA_HOME/dev.goats.xivlauncher is now the default storage directory. It is used on new installs, and an attempt is made to move ~/.xlcore to this location. If it fails, we'll try to make a symlink at the new path pointing at ~/.xlcore. If it succeeds, we'll make a symlink at ~/.xlcore pointing to the new location. This can be controlled with the XL_MAKE_SYMLINK environment variable. Default is on.
  • The laucher.ini config will be loaded in, and then a helper function will check all the path-related entries. If the entry starts with ~/.xlcore, it'll be replaced with XDG_DATA_HOME/dev.goats.xivlauncher
  • If a flatpak user switches to a native install (or the reverse), the symlink at ~/.xlcore will be used to create a new symlink for the second type of launcher. This is because flatpaks override the XDG_DATA_HOME variable to point to their sandboxed location, usually ~/.var/app/dev.goats.xivlauncher/data
  • Flatseal should not be used to add an override for the xdg-data-home/dev.goats.xivlauncher folder. This creates more problems than it fixes.

it was accidentally re-using GamePath
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants