Skip to main content
← Back to list
01Issue
BugShippedSwamp CLIPublic
Assigneesskunk-ape

Relationships

#3569 Extension lockfile stores machine-local paths (OS separators, gitignored .swamp/ files, pulledAt), so a repo shared by Windows and Linux never stays clean

Opened by kagarmoe · 10/16/2026· Shipped 10/19/2026

What happened

A repo shared between Windows and Linux (the same git repo, checked out on both) never stays clean.

extensions/models/upstream_extensions.json records each extension's files with the pulling OS's path separator:

"@swamp/ssh": {
  "version": "2026.10.13.1",
  "pulledAt": "2026-10-16T01:34:34.943Z",
  "files": [".swamp\\bundles\\2f6574ec\\ssh.js", ".swamp\\pulled-extensions\\@swamp\\ssh\\files\\LICENSE.txt", "…"],
  "filesChecksum": "e0461e3a…",
  "serverUrl": "https://swamp-club.com",
  "publishedChannel": "stable"
}

On Linux, after a git pull of a lockfile written on Windows, every command warns:

[WRN] 14 pulled extension(s) have missing source files: @swamp/ssh, @swamp/stagecraft, … (e.g. .swamp\\bundles\\2f6574ec\\ssh.js, …). Run 'swamp extension install' to restore them.

swamp extension install then rewrites all 464 lines with /. The next commit from Windows flips them back, so the Linux checkout always shows the file as modified and blocks git pull --ff-only.

The underlying problem

The committed lockfile holds machine-local state:

  • Every path in files is under .swamp/, which swamp's own managed .gitignore excludes. The lockfile lists files that are never committed. Each machine rebuilds them, and the bundle hash directories may differ.
  • The paths are derivable. version and filesChecksum pin the content, and the extension's manifest lists its files.
  • pulledAt changes the file on every pull, even when nothing pinned changed.

Proposed

  • Better: pin only what makes an install reproducible: name, version, checksum, serverUrl and publishedChannel, as deno.lock and package-lock.json do. Derive local paths at runtime, and keep pulledAt and the file list under .swamp/.
  • Smaller fallback: write POSIX / separators always, and accept either separator on read. Accepting both matters too: without it, lockfiles already committed from Windows keep warning on Linux.

Environment

  • Windows 11 Pro: swamp 20261015.233727.0-sha.a39bdd69
  • WSL2 Ubuntu 26.04 on the same machine: swamp 20261016.021405.0-sha.b46b8895
  • The WSL clone's git origin is the Windows checkout. swamp serve runs in WSL.
02Bog Flow
✓OPEN✓TRIAGED✓IN PROGRESS✓SHIPPED+ 1 MOREASSIGNED+ 5 MOREREVIEW+ 8 MOREPR_MERGED+ 2 MORESESSION_SUMMARIZED

Shipped

10/19/2026, 9:46:01 PM

Click a lifecycle step above to view its details.

03Sludge Pulse
skunk-ape assigned skunk-ape10/19/2026, 7:19:36 PM
Editable. Press Enter to edit.

skunk-ape commented 10/19/2026, 9:46:07 PM

Thanks @kagarmoe for reporting this! We shipped: Make the extension lockfile portable across OSes. files and include are written with forward slashes, and files no longer lists bundle-cache paths, whose namespace hash is per-OS. One canonical form, applied when the lockfile is read, makes every reader accept legacy backslash and bundle entries without warning, and extension install rewrites a legacy non-managed lockfile once. Read-only commands never write. pulledAt stays (already kept across same-version reinstalls); filesChecksum is already independent of the OS.. The fix has been merged and a release is on its way. We appreciate your contribution to swamp.

skunk-ape commented 10/19/2026, 9:46:30 PM

Thanks for the detailed report: the Windows lockfile example pointed straight at both causes.

This is fixed in swamp release 20261019.214045.0-sha.6dbc53eb (https://github.com/swamp-club/swamp/pull/3212). Run swamp update on both machines to get it.

What changed

  • Lockfile paths in extensions/models/upstream_extensions.json are now always written with /, on every OS.
  • files lists only an extension's source files under .swamp/pulled-extensions/. It no longer lists bundle-cache paths (.swamp/bundles/<hash>/...), whose hash directory differs between Windows and Linux. Each machine rebuilds its bundles.
  • A lockfile an older swamp wrote on Windows still reads correctly on Linux: no "missing source files" warning, and commands like extension list don't rewrite it.
  • pulledAt was already kept when an extension is reinstalled at the same version, so it only changes when the version changes. filesChecksum was already the same on every OS.

To clean up an existing lockfile: once both machines run the new release, run swamp extension install once on either one and commit the result. It rewrites the lockfile with / paths and no bundle entries, without reinstalling anything. From then on, Windows and Linux write the same lockfile, so the shared checkout stays clean.

Sign in to post a ripple.