Skip to content

fix(deployment): link to the staged file without a doubled separator - #24477

Open
Ramnath0521 wants to merge 1 commit into
Nexus-Mods:masterfrom
Ramnath0521:fix/issue-24408
Open

Ramnath0521 wants to merge 1 commit into
Nexus-Mods:masterfrom
Ramnath0521:fix/issue-24408

Conversation

@Ramnath0521

Copy link
Copy Markdown

Fixes #24408

Cause

LinkingActivator builds the source path of every deployed file by joining strings with path.sep:

[installPathStr, source, relPath].join(path.sep)

When the staging path is configured with a trailing separator (for example E:/Modding/Vortex-Data/Staging/witcher3/), that produces a doubled separator before the mod folder: .../Staging/witcher3//<mod>/..., which is what the log in the issue shows.

The operating system normalizes the link target when the symlink is created, so readlink later returns the path with a single separator. isLink() in the symlink activators compares that against the un-normalized sourcePath as plain strings (symlinkPath === sourcePath), so they never match and externalChanges() reports every file of the previous mod as changed outside of Vortex.

Change

Build the two source paths with path.join instead of [...].join(path.sep), in deployFile() (the path the link is created with) and in externalChanges() (the path it is checked against). path.join collapses the doubled separator, so both sides agree whatever the configured staging path looks like. No other behaviour changes.

I left the data (game) path joins alone: they are only used as the location of the link, not compared against a readlink result.

Test

LinkingDeployment.test.ts gets one test that runs the real symlink deployment method through the existing makeDeployment harness with a staging path that ends in a separator, and asserts the target passed to symlinkAsync is path.join(stagingDir, modName, "mod.ini"). symlinkAsync is stubbed so the test does not need symlink privileges (creating symlinks needs Developer Mode or admin on Windows).

  • Without the fix, on Windows 11:
    • Expected: ...\staging\SomeMod\mod.ini
    • Received: ...\staging\\SomeMod\mod.ini
  • With the fix the test passes.

What I ran, and what I did not

On Windows 11 / Node 24, from src/renderer:

  • pnpm exec vitest run src/extensions/mod_management src/extensions/hardlink_activator src/extensions/move_activator: 45 files, 488 tests pass.
  • oxfmt --check and eslint --quiet clean on the two changed files.
  • tsc reports nothing in the changed lines; its only error in these files is Cannot find module '@vortex/shared', because I did not build that package locally.

I did not run pnpm run verify, the full build, or an end-to-end run with a real symlink deployment of a game: this machine cannot create symlinks without elevation. To get the renderer tests to load I installed with lifecycle scripts disabled, so winapi-bindings was not built and I used a throwaway local stand-in for it (not part of this change).


Written with AI assistance (Claude Code). I reproduced the failure on my own Windows machine, read the diff, and verified the added test fails before the fix and passes after. Errors are mine.

🤖 Generated with Claude Code

@github-actions

Copy link
Copy Markdown

This PR has conflicts. You need to rebase the PR before it can be merged.

LinkingActivator built the source path of each deployed file by joining
strings with path.sep. A staging path configured with a trailing
separator gave a doubled one, but the OS normalizes the symlink target,
so isLink() compared a single-separator readlink result against the
doubled path and reported every deployed file as changed outside of
Vortex.

Build both source paths with path.join so they always agree.

Fixes Nexus-Mods#24408

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
@github-actions

Copy link
Copy Markdown

This PR doesn't have conflicts anymore. It can be merged after all status checks have passed and it has been reviewed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

When you set a staging path ending in a \ Vortex starts throwing errors about changes outside of the app

2 participants