SpotX + Spicetify Customization
Installs, configures, and maintains Spotify with themes, extensions, custom apps, and the LibreSpot Store inside the client. No command-line knowledge required. v4 ships a Windows desktop app and a fleet CLI alongside the original single-file PowerShell script, so you can run whichever suits the machine in front of you.
The two badges say different things on purpose. Version is what this source tree builds, 4.6.0, which is prepared and has not been published. Stable is 4.5.1, the newest release on GitHub and what every download link below gives you.
These are failures reported on the upstream trackers by people running SpotX and Spicetify by hand. Each row quotes a real thread and names the part of LibreSpot that handles it. Where a thread was opened to document a mechanism rather than to report a fresh problem, the row says so.
| What people report | LibreSpot's answer |
|---|---|
| "SpotX-patched client drops xpui-snapshot.js, silently breaking Spicetify custom apps" (SpotX #892, open) and "Custom app patches silently applied to a bundle the client never loads when xpui-snapshot.js is absent" (spicetify/cli #3922, closed as not planned). Both were opened on 2026-09-07 by one reporter to document the mechanism. A Spicetify member answered "This is SpotX's fault, not ours. SpotX is aware of this, but as far as I know, no fix is planned." and, on the SpotX thread, "We always tell people not to use SpotX & spicetify at the same time because we both modify stuff." SpotX has not replied. | LibreSpot re-wires the custom-app route onto the bundle the patched client actually loads, after Spicetify applies. See Spotify Compatibility. |
| "Market place is not showing up (read it)" (spicetify/cli #3816, 33 comments, closed as not planned) | Maintenance repairs Marketplace and can reset its storage from a copy it takes first. See Three Modes. |
| "Extensions are deleted every twice Spotify startup." (spicetify/cli #3861, closed as not planned) | Auto-reapply watches for the Spotify update that removes your setup and puts it back. See Auto-Reapply (new in v3.6.0). |
| "Spotify version mismatch with Spicetify." (spicetify/cli #3606, locked and closed as not planned) | The pinned tuple is one LibreSpot has verified end to end, and the compatibility matrix reports supported, degraded, or unsupported with a next step for each. See Spotify Compatibility. |
| "Windows Defender detects malware (false positive) when running a bat file" (SpotX #741, 44 comments, closed as not planned) | Every download is pinned by SHA256 and verified before use, and LibreSpot holds a SpotX commit that adds no Defender exclusions. See Trust & risk disclosure. |
| A snippet or theme leaves Spotify unusable, and there is nothing to roll back to (r/spicetify) | Safe mode starts Spotify once without extensions or custom apps and restores the verified snapshot afterwards, and Full Reset returns the client to stock. See Three Modes. |
None of this makes Spotify Premium appear, and LibreSpot does not claim it does. Read the capability boundary for what stays on Spotify's side.
1. Download the desktop app. Get LibreSpot-Desktop.exe and checksums.txt from the latest stable release. Both files come from the same release page, and the official repository is the only place to get them.
2. Check the file. Every release asset has a SHA256 line in checksums.txt from that same release, and the hash of the file you downloaded has to match its line. GitHub also records a signed attestation for each published release, which gh release verify-asset can confirm. How to verify a LibreSpot download shows both checks. A mismatch means delete the file and don't run it.
3. Run it. Double-click LibreSpot-Desktop.exe. No install, no admin prompt. Home tells you what it found and offers one action, so a new machine starts with Recommended Setup and a healthy one opens Spotify.
Windows SmartScreen may warn because the file is unsigned by design. A hash that matches checksums.txt is what proves the file is the release artifact. See Signing & verification.
Advanced: the PowerShell script
LibreSpot.ps1 is the single-file script the v4 apps grew out of, and LibreSpot.exe is that script compiled with PS2EXE. Both ship in every release. This block downloads LibreSpot.ps1 and checksums.txt from the latest release, validates SHA256 before anything runs, and keeps the script at a reusable local path:
$d = "$env:LOCALAPPDATA\LibreSpot\bootstrap"; New-Item -ItemType Directory -Path $d -Force | Out-Null
$base = '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/SysAdminDoc/LibreSpot/releases/latest/download'
Invoke-WebRequest "$base/LibreSpot.ps1" -OutFile "$d\LibreSpot.ps1" -UseBasicParsing
Invoke-WebRequest "$base/checksums.txt" -OutFile "$d\checksums.txt" -UseBasicParsing
function Get-LibreSpotBootstrapSha256 {
param([string]$Path)
$cmd = Get-Command Get-FileHash -ErrorAction SilentlyContinue
if ($cmd) { return (Get-FileHash -LiteralPath $Path -Algorithm SHA256).Hash.ToUpperInvariant() }
$stream = [System.IO.File]::OpenRead($Path); $sha = [System.Security.Cryptography.SHA256]::Create()
try { return (($sha.ComputeHash($stream) | ForEach-Object { $_.ToString('x2') }) -join '').ToUpperInvariant() }
finally { $stream.Dispose(); $sha.Dispose() }
}
$expected = (((Get-Content "$d\checksums.txt" | Where-Object { $_ -match 'LibreSpot\.ps1$' }) -split '\s+')[0]).ToUpperInvariant()
$actual = Get-LibreSpotBootstrapSha256 "$d\LibreSpot.ps1"
if ($actual -ne $expected) { Remove-Item "$d\LibreSpot.ps1" -Force; throw "SHA256 mismatch, expected $expected, got $actual. The download may be corrupted or tampered with." }
Write-Host "SHA256 verified: $actual" -ForegroundColor Green
& "$d\LibreSpot.ps1"Or download LibreSpot.ps1 and right-click Run with PowerShell. Either way the script asks for admin only when a step needs it.
Managed: the fleet CLI
LibreSpot.Cli.exe is the unattended artifact for Intune, PDQ, SCCM, WinRM, and PSRemoting. The fleet section further down lists the implemented verbs and answer-file examples.
Requirements: Windows 10/11 (64-bit) and an internet connection. The PowerShell script path also needs Windows PowerShell 5.1 or PowerShell 7.6 LTS, both of which it's tested on.
Fake “free Spotify Premium” installers often begin with a video or message that tells you to paste PowerShell. Use the official LibreSpot repository and its linked release page instead. Installing the desktop app never involves pasting a command.
LibreSpot is published in exactly one place: https://github.com/SysAdminDoc/LibreSpot/releases. Anything offering it from another host is not LibreSpot, whatever the repository is called and however many stars it has. Star counts are cheap to buy and several lookalike projects sitting in the same search results have more of them than this one does. The tells are consistent. The README is padded or barely says what the tool does, the download is a link to a file host rather than a GitHub release asset, and somewhere you are asked to fetch a separate "template", "config" or "activation" file to make it work. LibreSpot has no such file and never asks for one.
A release asset can prove where it came from, which no amount of presentation can fake:
gh release verify-asset v4.5.1 .\LibreSpot-Desktop.exeThat checks GitHub's signed attestation for the asset against this repository. If it fails, or if the asset did not come from a release page here, delete the download.
For a release asset, download checksums.txt from that same release page and compare the asset with its SHA256 line. In PowerShell, from the folder that holds the download:
(Get-FileHash .\LibreSpot-Desktop.exe -Algorithm SHA256).Hash
Get-Content .\checksums.txtIf the GitHub CLI is installed, the release attestation check confirms the asset was uploaded to that published release:
gh release verify-asset -R SysAdminDoc/LibreSpot v4.5.1 .\LibreSpot-Desktop.exeDo not use Telegram links, rehosted files, or builds copied to another site. Never paste commands from videos, social posts, or chat messages. If a command asks you to disable Defender or add an exclusion, close it. A hash mismatch means the file must be deleted and not run.
This is what the next release will contain. It is built from this tree and has not been published yet, so the download links above still give you v4.5.1.
- Context menus are readable on Prism's light schemes. Spotify's own stylesheet hard-codes white with alpha for menu text, which no colour replacement can reach, so Prism maps those to the scheme's own text colour.
- The Store and Custom Install say when a custom app has open upstream defects, starting with the bundled Stats app.
Build-Scripts.ps1 -ProposeCatalogRefreshreports what advancing every community pin would mean, and applies none of it.- The downloader's patch-level check tracks all three Windows PowerShell advisories that reach it, not just the December 2025 one.
- The README opens with the failures people hit running SpotX and Spicetify by hand, each next to the feature that handles it.
This release is built from this tree and is available from the download links above.
Prism's settings entry survives a slow client start. The retry waits for Spicetify's menu and modal surfaces, then registers Spicetify.Menu.Item and opens Spicetify.PopupModal.display. That logic had been written months earlier and announced as shipped, but it only ever reached a copy of the theme that nothing installs, so the theme people actually had still registered the menu once and gave up. There is one copy of the theme in the tree now, and a test that fails if a second one appears.
Safe mode now gives Spotify one clean diagnostic launch without sacrificing the current setup. LibreSpot authenticates the private recovery marker with the current Windows account, verifies the complete snapshot before changing anything, and keeps one Restore my setup action ready until the original files and Spicetify apply both succeed.
Fleet admins can move a verified asset cache to an offline endpoint. Import rejects undeclared files and damaged content before it swaps the cache into place, with rollback if the commit is interrupted. Cache writes stage and flush each object before replacement, and Core and PowerShell serialize index changes through the same lease. Every existing cache or configuration parent is checked for reparse points before a lock or staging directory is created. A bounded transaction marker records each directory move, so a process that dies during publication is recovered on the next cache operation without losing unindexed files. Core's recovery fixture kills a disposable helper at every publication boundary and verifies the result in a fresh process. A malformed index stays in place and is reported, while concurrent saves retain both entries. Exit code 13 now matches the actual run behavior too: selected assets missing is success with a warning, including the Intune mapping.
Local crash dumps are opt-in and limited to the next LibreSpot process. Support export accepts only a structurally valid Windows minidump whose header flags and stream kinds match the .NET Triage policy, keeps the two newest files locally, and adds just the newest accepted dump when the setting is enabled. Self-contained single-file builds need the adjacent .NET createdump.exe helper, which the local release publisher carries beside the desktop and CLI executables and includes in checksums.txt. The binary is diagnostic memory that may contain sensitive process state. Nothing is uploaded automatically.
The Home update notice can show GitHub's SHA256 for LibreSpot-Desktop.exe and copy the exact verification command. Default-install and release-response tests now exercise the real behavior, while the catalog generator is checked across both supported PowerShell editions. The live engine also starts after a Spotify reload when Spicetify omits its optional ReactDOM global. Startup waits until the React hooks, history navigation, local storage, and player event methods used by the engine are callable, so staged companion publication cannot start a partial runtime. Route probing finishes before listeners are attached, and a failed setup removes the claimed runtime and all registered cleanup hooks before retrying. If Spotify's companion APIs never arrive, the in-client surface reports the startup failure with a retry action instead of waiting forever. A panel that throws stays inside its own error view, with Retry panel and Open Health actions that leave saved settings intact.
Desktop setup, the standalone script, and the auto-reapply watcher now coordinate changes to one Spotify and Spicetify installation through a shared per-user lease. A second operation reports that the installation is busy before it takes a snapshot or stops Spotify, while separate installations can run at the same time. External PowerShell runs also own their complete process trees with a Windows Job Object, so timeout, cancellation, watchdog shutdown, and launcher exit terminate descendants before cleanup. Containment failures are reported explicitly and unrelated processes remain untouched.
CLI, theme, and custom app installers now unpack pinned archives into a verified staging folder on the target volume. A single recoverable transaction swaps the package, companion extension, and Spicetify configuration together. Failed requested apps retain their existing config entries, required theme files are checked after staging, and a changed configuration target is left alone when recovery cannot prove that the transaction owns it.
Auto-reapply watcher failures keep the originating download, parameter, patch, or Spicetify application stage in the saved diagnostics. The marker is cleared after the result is recorded, and the existing retry and hold behavior remains in place.
Marketplace reset now follows the IndexedDB request to its real terminal result. Health keeps the action visibly pending when another Spotify window blocks deletion or the local watchdog expires, reuses an in-flight request instead of starting a duplicate, and closes a database connection that arrives after an open attempt timed out.
Marketplace backup and reset recovery now include its legacy localStorage fallback as well as IndexedDB. The pinned migration rule gives database values precedence and uses legacy values only when migration is incomplete or IndexedDB is unavailable. Reset clears only marketplace: keys and restores the captured backend state without changing unrelated Spotify or LibreSpot storage.
The settings workspace inside Spotify has been rebuilt around six focused pages. A compact LibreSpot rail keeps Store, Look, Tweaks, Features, Presets, and Health easy to reach without competing with Spotify's own navigation. The settings cog in Spotify's top bar opens Look directly.
Store now feels like a first-party catalog. All 24 supported themes have working preview images and scheme details, while extensions and apps have searchable cards that explain what each item does, whether it is installed, where it comes from, and how LibreSpot handles setup. Prism, Compact, and Accessibility still support a live preview that restores the saved profile when it ends.
Look has a full appearance workbench. Tweaks pairs each reviewed rule with a before-and-after preview. Features keeps 379 live and desktop-applied controls in a filterable group view, Presets shows the result before applying a profile, and Health groups every check by engine, route wiring, or compatibility.
The layouts respond to the space Spotify leaves between its library and Now Playing panels, including wrapped Tweaks categories when the content column gets narrow. The release was installed into Spotify 1.2.93.667 with Spicetify 2.44.0 and checked at 1280 and 1590 pixels. The Store tabs, search, theme previews, live appearance controls, tweak switches, feature overrides, presets, diagnostics, and the replacement settings icon were exercised in the running client.
LibreSpot is now the store inside Spotify. The old Extensions inventory and the separate Marketplace entry have been replaced by one Store at the top of LibreSpot's rail. The profile menu keeps a Store entry, while the compact settings button in Spotify's top bar opens LibreSpot's Look panel directly.
The Store presents 24 supported themes with screenshots, plain descriptions, source details, compatibility notes, and every available color scheme. Prism, Compact, and Accessibility can be previewed live before they are applied. Community themes open the exact matching setup control in LibreSpot Desktop. Extensions and apps have their own searchable tabs with installed state and trust details.
New installs use Prism with its Dark scheme and install LibreSpot by default. The separate Spicetify Marketplace is off by default, while existing setups that chose it remain supported. The old LibreSpot Extensions and Marketplace routes redirect into the Store instead of leaving stale pages behind.
The release was exercised inside the pinned Spotify 1.2.93.667 client with Spicetify 2.44.0. Theme selection, live preview and restore, search, category tabs, advanced settings, legacy route redirects, and the desktop setup handoff were checked without taking over the active desktop.
v4.2.0 makes the desktop app the front door and tidies what sits behind it. Quick Start now points straight at LibreSpot-Desktop.exe and checksums.txt, explains the same-release hash and release attestation checks in plain words, and keeps the PowerShell script and the fleet CLI behind labeled Advanced and Managed sections. The unverified one-line install command is gone.
Settings opens with the four choices most people change: the Spotify build, the theme, the Marketplace, and whether Spotify opens when the run finishes. Everything else is one click away in labeled groups, and the apply button lives in a footer that never scrolls out of reach. The page scrolls as one. Two things keep their own scrollbar because they have to: the 348-flag feature list, which is virtualized so that opening Settings does not build every row, and the custom-patches JSON editor. Searching for a hidden option opens its group and scrolls it into view. Clearing the search puts the groups back the way you left them.
Home shows a quiet Update LibreSpot link when a newer stable release exists. The check runs in the background once a day, never downloads anything, and never interrupts you. When GitHub publishes a digest for the desktop asset, a Verify the download disclosure shows that SHA256 value and the exact gh release verify-asset command with a copy button. Releases without a digest keep the original link-only notice.
Closing Spotify is polite now. Both the desktop restart and the script ask each Spotify window to close, wait up to five seconds, and only then force whatever is still running. The run log names each process, its PID, the wait, and the reason.
The security policy names v4.0.x and later as the supported stable line and marks the old standalone v3.7.x script releases as superseded. The blocked plan no longer describes signing as pending, and the signing decision record ships with the repository.
v4.1.2 completes an installed-client audit of the LibreSpot workspace in Spotify 1.2.93.667 with Spicetify 2.44.0. Text fields, selects, sliders, time inputs, disclosures, saved presets, profile copying, diagnostics, snippets, and live flags now use Spotify's real event shapes and APIs. Removing a custom flag restores Spotify's remote value instead of leaving the override behind.
Tweaks reads the Home and Your Library items that Spotify is actually showing, stores their stable identities, and reapplies the chosen order after navigation or a redraw. Snippet selectors were checked against the pinned client. Cover shapes are mutually exclusive, progress and compact-row rules work on current classes, and the optional Now Playing cards can be hidden without disturbing the rest of the sidebar.
The extension now uses Spotify artwork and Spotify's icon library for previews and status marks. Light, OLED, dark, and high-contrast palettes keep entity headers, action controls, the playbar, and notifications readable. The fixed-accent mode has a native color picker, all form controls have names, and sliders expose a 32-pixel target.
The Spotify surface suite has its own test project; run pnpm test in src/LibreSpot.App for the current result rather than trusting a number printed here. Hidden live-client verification covered all six panels, Marketplace coexistence, settings, a playlist, persistence across a full reload, failure feedback, and 36 scheme, effects, and viewport combinations. The matrix found no clipped controls or horizontal overflow.
v4.1.0 adds a LibreSpot workspace inside Spotify and a companion engine that stays active on every route. Palette, layout, effects, client feature flags, snippets, and presets update in place. The desktop app installs the hash-pinned bundle, keeps its profile in sync, repairs both LibreSpot and Marketplace routes after each apply, and reports engine health in Maintenance.
The shared catalog is tied to the pinned Spotify 1.2.93 bundle. It contains all 348 declared flags, 31 SpotX controls, 12 reviewed snippets, 22 installable themes, three built-in layer themes, and four presets. Source hashes make a stale catalog fail the build.
The live proof used Spotify 1.2.93.667 with Spicetify 2.44.0. Hidden browser control exercised the common live changes and the Marketplace route without restarting Spotify. A 36-case visual matrix covered four schemes, three effects tiers, and three viewport sizes with no horizontal overflow or clipped LibreSpot controls.
v4.0.0 is the first stable release of the v4 line. The desktop app and the fleet CLI leave preview, and the single-file PowerShell script ships in the same release for anyone who wants it. Everything below landed across the v4 previews and is now the released behavior.
One screen that tells you what to do. The everyday view has three choices: Home, Maintenance, and Settings. Home gives you one readiness result, four checks, and one action chosen from the latest system check. A new setup starts the recommended path, a healthy managed stack opens Spotify, and a known problem offers its first safe repair. Recovery that could remove data opens Maintenance for review instead of running from Home. First-run guidance and technical environment details stay behind the Details row until you ask for them.
Maintenance puts recovery first. It shows the most important issue and one safe repair before any technical detail. Start Spotify in safe mode saves an exact copy of your Spicetify config and custom apps, then binds the private snapshot path and manifest SHA256 to your Windows account. Recovery authenticates that protected marker and checks every saved file before it opens Spotify without extensions or apps. One Restore my setup action stays ready. Diagnostics remain under one labeled section, while reset actions are separate and collapsed until you choose to review them.
Recovery actions describe the change they make. The action formerly called Restore vanilla Spotify removes active Spicetify customizations and says plainly that SpotX stays in place. Home says eligible changes have backups rather than promising that every change can be reversed.
The app tells you which version it is. The version sits under the LibreSpot name in the navigation rail, and crash reports record the full product version instead of a shorter numeric one.
Home recovers from a failed check. If LibreSpot cannot verify your PC, the screen offers a Retry button instead of naming a control that does not exist. Maintenance behaves the same way rather than looking like Spotify is simply missing.
Crash reports still appear when the usual folder cannot be created. LibreSpot writes them under the temp directory in that case, and Open folder goes to wherever the report actually landed.
Home fits the smallest window. At the minimum window size the readiness checks used to be cut off at both edges with no way to scroll to them.
Search boxes tell you what they do. Settings search and the theme gallery show placeholder text inside the empty field, and the theme box is no longer labeled as if it were the pack picker. The taskbar Jump List says Home and Settings, matching the rail.
Every language is reachable. The picker sits at the bottom of the navigation rail, next to the reversible-changes note, and all five interfaces are complete and translation-reviewed. That covers the desktop shell. The panel LibreSpot adds inside Spotify and the standalone LibreSpot.ps1 window are English only, so on a non-English system the shell follows your language and the in-client panel does not.
One answer about your Spotify build. Version strings are read through a single parser, so a build carrying a git hash, a trailing note, or a fourth component gets the same verdict on every screen.
Readable in high contrast, and while you switch. Disabled controls mute their label instead of fading the whole control below the contrast floor, and turning Windows high contrast on while the app is running recolors the shell immediately rather than waiting for a restart.
LibreSpot refuses to install or reapply over Spicetify v3 artifacts. If the health report shows a Spicetify v3 conflict, run spicetify restore first, then reinstall the pinned Spicetify 2.x integration.
The v3 compatibility contract is fixture-backed. When a v3 CLI is detected, LibreSpot can read the upstream supported-versions.json schema-v2 allowlist. Allowlisted versions proceed, versions with a same-minor lower modular map are marked degraded, and versions without a usable fallback are refused. A missing or malformed document now fails closed and points to spicetify restore before the pinned 2.x CLI is reinstalled. The pinned Spicetify v2.44.0 path does not activate this contract.
A smaller shipping shell. The three workspaces live in dedicated UserControls while preserving localized text, focus behavior, and automation names. Per-user registry, configuration, profile, backup, log, crash, and executable-path isolation is covered by multi-user regression tests.
Pinned compatibility is executable. The supported SpotX/Spotify, Spicetify CLI, Marketplace, and theme tuple now has one fixture-backed release contract checked by Windows PowerShell preflight and Core tests.
The shared core is fully extracted. All non-UI logic shared by the desktop shell and the fleet CLI, environment snapshotting, upstream/community drift comparison, undo-policy evaluation, backend orchestration, support bundles, the app catalog, and the localized Strings resources with their language satellites, now lives once in the WPF-free LibreSpot.Core library instead of being compiled into both apps. Behavior is unchanged, but the code is smaller, de-duplicated, and, unlike the WPF shell, able to be mutation-tested. Verified with the full test suite plus an offscreen render of the real shell resolving localized text across languages.
Provenance-checked Spicetify downloads. On top of the mandatory SHA256 hash, the pinned Spicetify CLI download now optionally verifies GitHub build-provenance attestations: when the GitHub CLI is present, LibreSpot confirms the artifact was built by Spicetify's own release pipeline against a cached signer identity. A genuine provenance failure raises a trust warning; if the tooling, network, or sign-in is unavailable it quietly falls back to SHA256-only and never blocks the install.
Sharper upstream guardrails and honest trust docs. The SpotX pin-advance guardrail now accounts for Spicetify's hard-fail-on-unsupported-version gate (merged upstream after 2.44.0): advancing the pin must confirm the newer Spicetify still applies rather than hard-refusing, not just re-check CSS maps. The signing docs now say LibreSpot ships unsigned by design and SHA256 checksums.txt is the permanent verification path. The antivirus FAQ steers users to the compiled desktop executable over the raw script and shows VirusTotal-by-hash verification. The .NET 10.0.11 CVE-floor rationale records the 2026-08-11 servicing batch it clears.
Quieter, safer internals. The Microsoft Store Spotify and Windows Defender exclusion probes no longer risk an unbounded wait when a child process leaves an output pipe open. The accessibility palette gained a regression gate that verifies the primary, destructive, and caution buttons keep their WCAG AA text contrast on every future theme change, not only the body-text tiers that were already covered.
The store page actually opens now. SpotX serves Spotify's combined xpui.js bundle, but the Spicetify CLI wires the Marketplace route into sibling files that layout never loads. The store opened to a permanently blank page with no errors anywhere. LibreSpot now re-wires the store route into the bundle Spotify actually runs after every apply, verified end to end on a live install. Stack health gains a "Store page not wired" state (all six languages) that detects the broken layout and points straight at Repair Marketplace. The end-of-install launch also warms up the first patched session hidden and restarts Spotify automatically, so the window you sign in to is responsive instead of frozen for its first ten seconds.
Marketplace that actually works. The default Marketplace-only setup now follows the official Spicetify Marketplace install contract: LibreSpot creates and activates the placeholder theme and keeps CSS injection on, so store themes and snippets render instead of silently doing nothing, and a managed fallback restores a visible Marketplace button in Spotify's top bar when a Spotify redesign breaks Spicetify's own nav link. Marketplace health now warns when the theme contract is inactive and points you to Repair Marketplace, and the post-install launch guarantees a fresh, patched Spotify session.
Truthful, resilient UX. Readiness starts in a checking state, reports system, Spotify, permission, and dependency results independently, and replaces success artwork with loading or failure guidance when needed. Maintenance holds the recovery tools. When a newer stable LibreSpot release exists, Home adds one quiet Update LibreSpot link under the main action. It checks once a day in the background, never downloads anything, and never interrupts you. Activity updates announce changing content, translated prompts wrap and scroll safely, and high-contrast and reduced-motion variants share the same interaction contract.
The v4 desktop opens Settings with the four choices most people change, keeps every other option one click away in labeled groups, and keeps readable cards, a searchable theme gallery, safe .librespot profile import and export, local profile sharing cards, dark native window chrome, completion notifications, issue-level repair buttons, a reversible-changes pane, and assistive-technology feedback. Common users no longer need to see those tools before starting the recommended setup.
It also registers Windows shell affordances from the running desktop executable: per-user librespot:// profile links, .librespot file imports, jump-list shortcuts, taskbar thumbnail actions, tray minimize/restore, and tray completion notifications that reopen LibreSpot when clicked. Registration is per-user and points at the current executable path, so portable and installed builds both repair stale associations on launch.
The desktop rail uses Home, Maintenance, and Settings. Windows protocol and profile-association descriptions follow the saved interface language.
LibreSpot wraps two open-source projects into one interface:
- SpotX, patches Spotify to remove ads, block telemetry, and enable experimental UI features
- Spicetify, injects custom themes, extensions, custom apps, and the in-app Marketplace into Spotify
The root project, desktop shell, fleet CLI, and PowerShell hosts are MIT-licensed. The in-Spotify live customization engine is an AGPL-3.0-only component and ships with LibreSpot's own Prism theme and engine archive. SpotX, Spicetify CLI, Marketplace, and the official theme archive are fetched from pinned upstream sources during installation. Their licenses and retrieval posture are recorded in the third-party notices and the notices manifest.
Instead of running multiple scripts, editing config files, and hoping the versions are compatible, LibreSpot handles the entire workflow: clean uninstall, fresh Spotify install, SpotX patching, Spicetify CLI setup, theme installation, extension configuration, verified custom-app installation, and Marketplace deployment, all in the correct order, with full error handling.
The desktop shell keeps each workspace in a named UserControl. The Custom workspace is further divided into install, appearance, behavior, advanced, patch, extension, app, and profile sections, so the UI and its code-behind stay easy to trace without changing the user-facing workflow.
Choose LibreSpot in Spotify's navigation after installing the LibreSpot custom app from the desktop app. Store is the first page. The companion extension keeps the selected state active while you move through Home, Search, Library, playlists, and Spotify settings.
Every live control exposes its explanation to assistive technology. Store searches announce the result count or an empty state once as the list changes.
The Store's extension tab counts everything the engine knows about, including the LibreSpot companion that installs with the engine itself. That is why it reads one higher than the 15 you can pick in Custom Install. The counting rule is recorded in schemas/librespot-customization.json.
| Look | Tweaks |
|---|---|
| Live theme, scheme, layer, accent, type, scale, corner, schedule, and effects controls. | Twelve reviewed CSS snippets with source and Spotify-version evidence. |
![]() |
![]() |
| Features | Store extensions |
|---|---|
| All 348 client flags and all 31 SpotX controls, grouped and searchable. | Searchable cards explain each extension, its source, installed state, and setup path. |
![]() |
![]() |
| Presets | Health |
|---|---|
| OLED, Accessibility, Compact, Performance, and user-saved profiles. | Named checks for layout anchors, both custom-app routes, Spotify version, and the live engine. |
![]() |
![]() |
Three layer themes ship with the engine:
| Theme | Purpose | Schemes |
|---|---|---|
| Prism | Scheduled color changes, artwork accents, Material palette generation, and adaptive effects. | Dark, Light, OLED, HighContrast |
| Compact | Denser track rows, a thinner navigation rail, and a lower playbar. | Dark, Light, OLED, HighContrast |
| Accessibility | Larger controls, thicker focus, a readable font option, flat surfaces, and stronger contrast. | Light, HighContrast, Dark, OLED |
Scheme previews, layers, effects tiers, client-side flags, snippets, and presets change immediately. Artwork accents update in request order, and a derived Material palette stays in place while you navigate or the companion reapplies the current scheme. Installing a new custom app or extension still needs the desktop app. SpotX controls and cosmetic bundle patches also need a desktop reapply because they change files before Spotify starts. LibreSpot marks those controls clearly and copies a .librespot profile for the existing desktop import path.
Built-in preset cards compare the controls they own. Editing an applied profile changes its action back to Apply even when its display name stays the same.
Note: Spotify frequently updates its client, which can break SpotX and Spicetify patches. LibreSpot blocks Spotify auto-updates by default (via SpotX) to keep your installation stable.
If you manually update Spotify and patches stop working, use Maintenance > Reapply After Update to re-patch. The WPF Maintenance dashboard also flags After Spotify update drift and recommends targeted recovery steps before a full reset.
Current source script version: v3.12.0. This tree builds desktop and CLI v4.6.0, which is prepared and not yet published. Public latest stable release: v4.5.1.
Pinned dependency versions in the current source script:
| Component | Pinned Version |
|---|---|
| SpotX | 550bc72c, 2026-07-06 (Spotify 1.2.93) |
| Spicetify CLI | v2.44.0 |
| Marketplace | v1.0.11 |
| Themes | Commit df033493 |
Compatibility matrix: Maintenance > Check matrix reports SpotX, Spicetify CLI, Marketplace, and theme archive status separately. The Maintenance workspace also shows detected Spotify, SpotX, Spicetify CLI, and Marketplace values beside the pinned tuple, with a supported, degraded, unsupported, or unknown verdict and a next step for each state. The current SpotX target is Spotify 1.2.93. Spicetify CLI v2.44.0 declares Windows/Microsoft Store compatibility through Spotify 1.2.96, and 1.2.93 is the newest build LibreSpot has verified end to end with the rest of the tuple. Those are two different limits and LibreSpot reports them separately. A client above 1.2.93 but at or below 1.2.96 reads as degraded, with a next step, because Spicetify claims to handle it and LibreSpot has not checked it. Only a client past 1.2.96 reads as unsupported, and no message calls LibreSpot's ceiling a Spicetify one. The supported tuple is recorded in schemas/compatibility-baseline.json; Build-Scripts.ps1 -Validate and the Core contract tests fail if the PowerShell pins, WPF/CLI constants, or documented range drift apart.
SpotX has no release tag for the pinned commit; upstream's newest tag is 1.9 (2025-01-03). The 2.0 value LibreSpot records for SpotX is its own adapter version for commit 550bc72c, which is why the table above identifies the pin by commit and date.
Why the SpotX pin holds (verified 2026-09-03): SpotX main now recommends Spotify 1.2.99 and, since commit afb4c3f (2026-07-11), adds Microsoft Defender exclusions by default (opt-out -defender_exclusions_off). Spicetify CLI 2.44.0 declares Windows support through Spotify 1.2.96, while the newest Spotify build LibreSpot has verified with this tuple is 1.2.93. LibreSpot deliberately holds the pre-Defender SpotX commit 550bc72c at Spotify 1.2.93 so it ships a pairing it has actually tested and does not weaken Defender. The policy boundary is recorded as afb4c3fc in the pinned metadata. A changed SpotX commit must declare the post-boundary policy, declare the exact -defender_exclusions_off adapter argument, and prove that argument is passed before any exclusion command can run. The SpotX pin and Spotify target advance together only once a newer pairing is verified here, since Spicetify already declares support well past the pinned target. The advance must also confirm the newer Spicetify build still applies rather than hard-refusing: spicetify/cli main merged a hard-fail-on-unsupported-version gate after 2.44.0, so a future build can refuse backup apply on Spotify versions above its declared ceiling instead of best-effort patching. The pinned 2.44.0 predates that gate, which is why LibreSpot can re-wire the custom-app route after apply at all. That post-apply route re-wiring is verified against Spotify 1.2.93.667, and against no other build. Each verified build is recorded under routeWiring in schemas/compatibility-baseline.json with the SHA256 of the bundle before and after the repair, and Build-Scripts.ps1 -Validate fails when this sentence names a build that has not been proven against a real extracted bundle.
Recommended setup, one click, sensible defaults. Removes any existing installation, applies SpotX ad-blocking, installs Spicetify CLI with LibreSpot Store and Prism, then enables Full App Display, True Shuffle, and Trash Bin.
Custom Install, full control over every option. Configure SpotX patching flags (ad-blocking, podcasts, lyrics, UI experiments, update blocking, cache limits), author reviewed SpotX patches.json custom patches with JSON formatting, regex safety checks, dry-run feedback, and HTTPS import, browse 24 supported themes through a searchable gallery with per-theme color schemes, select from 15 extensions, ten built in and five community, plus the verified Stats custom app, save and preview named local profiles, and choose between clean or overlay install.
Maintenance, manage an existing installation without reinstalling. Backup and restore Spicetify configs, reapply patches after Spotify updates, inspect and clear verified download-cache health, preview and explicitly undo eligible low-risk PATH changes from the latest operation receipt, export a validated Marketplace state archive for missing-file recovery, export a redacted local support bundle, or arm the next LibreSpot launch for an optional .NET Triage crash dump. You can also remove active Spicetify customizations while keeping SpotX in place, uninstall Spicetify, check for dependency updates, or perform a full system reset. Marketplace 1.0.11 stores saved state in the embedded browser's IndexedDB database. LibreSpot's in-Spotify backup includes the keys it can read, and a failed cross-store restore compensates the exact prior engine bytes and Marketplace keys before reporting the failure. Marketplace reset saves a bounded copy in LibreSpot storage before it touches the database, so Health can restore or export it after the clipboard changes or Spotify starts again, recreating the known settings store when needed. Marketplace's own export/import controls remain useful for state LibreSpot cannot read.
LibreSpot changes the local desktop client. It does not grant Spotify Premium or change account entitlements.
| Capability | LibreSpot's boundary |
|---|---|
| Desktop ad patching | Supported as documented, with the account risk described below. |
| Spotify Premium access | Not granted. LibreSpot cannot turn a free account into Premium. |
| Offline downloads, lossless audio, and Very High quality | Not unlocked. These remain Spotify account or service capabilities. |
| Mobile on-demand playback and Jams | Not unlocked. LibreSpot is a Windows desktop tool. |
| Lyrics availability | Not unlocked. Availability remains controlled by Spotify, your account, and your region. |
| Existing Premium account | Use Custom Install's Premium account (skip ad-blocking) option to leave ad-related patches off. |
Maintenance > Full Reset can return the local Spotify installation to its stock state. It does not change your Spotify subscription or account entitlements.
LibreSpot.Cli.exe is the console-capable fleet artifact for endpoint tools. It ships stable as of v4.0.0. The implemented verbs are --version, --version --json, version --json, status --json, detect --json, detect --intune, validate --answer-file <path> --json, install --answer-file <path> --profile <name> --ndjson, reapply --answer-file <path> --profile <name> --ndjson, repair --repair-id <id> --silent --yes --ndjson, repair --safe-mode --dry-run --ndjson, uninstall --silent --yes --keep-spotify --ndjson, install|reapply --dry-run --answer-file <path> --ndjson, repair|uninstall --dry-run --ndjson, plan --answer-file <path> --json, undo --operation-id <id> --token-kind <kind> --dry-run --json, undo --operation-id <id> --token-kind <kind> --yes --json, cache export --output <zip>, cache import <zip>, export-support --output <path>, watcher install --silent, and watcher remove --silent. repair --safe-mode records a verified recovery snapshot before it disables extensions and custom apps, then opens Spotify unless --no-restart was supplied. Recovery accepts only the current Windows-protected marker schema, verifies the manifest hash, and checks every listed file before touching the live setup. repair --repair-id ExportMarketplaceState writes a timestamped archive under %USERPROFILE%\LibreSpot_Backups\MarketplaceState; RestoreMarketplaceState restores only missing files from the newest validated archive and then reapplies when Spicetify is available. Neither operation exports or claims to restore the embedded Marketplace IndexedDB database. Use Marketplace's own export/import controls for that state. status --json schema v4 reports compatibilityWarnings, which names the installed Spotify build when it is newer than the one LibreSpot verified or than the range Spicetify declares, and is an empty array otherwise. The schema also includes structured patcher ownership plus asset-cache inventory counts, byte totals, stale/corrupt state, and per-entry labels when available, and each pinned upstream/community asset's source URL, version or commit, last-verification timestamp, changelog/release link, and freshness state. detect --intune exits 0 only when the existing health report maps to a compliant state; clean slate, drift, blocked, and repair states return documented nonzero fleet exit codes without mutating the machine. Mutating backend verbs stream stable LS NDJSON events from the fleet schema contract, write rotating .ndjson logs to %ProgramData%\LibreSpot\logs by default, and install/reapply write validated answer-file settings or named answer-file profiles to config.json before invoking the shared backend. One operation GUID now follows the command into the PowerShell journal and appears in CLI JSON/plain output, desktop activity, rolling logs, crash reports, and support-bundle manifests. Local EventPipe/ETW collectors can also subscribe to the LibreSpot-Operations EventSource; LibreSpot does not upload this telemetry.
The current --help output lists every flag declared by schemas/fleet-cli-contract.json for each verb, including the destructive uninstall requirements.
Seed one trusted machine online, export its complete cache, copy the ZIP through your normal software-distribution channel, then import it before the answer-file install:
LibreSpot.Cli.exe cache export --output .\librespot-asset-cache.zip --json
LibreSpot.Cli.exe cache import .\librespot-asset-cache.zip --json
LibreSpot.Cli.exe install --answer-file .\librespot-answer.json --profile standard --silent --yes --no-restart --ndjsonExport refuses a cache if any indexed file is missing, stale, corrupt, oversized, duplicated, or a reparse point. Import accepts only entries that were marked present with a valid verification timestamp. It checks the manifest, exact ZIP layout, declared sizes, and every SHA256 in a private staging folder. LibreSpot then prepares the complete merged cache beside the live directory and swaps it into place, restoring the old directory if that commit fails. The import makes no network request. Object and index writes publish from flushed temporary files under a shared lease, so an interrupted write leaves the prior file intact and concurrent saves retain both entries. An index with a missing, null, or non-array entries field is refused before mutation. Cache-root and destination-parent reparse points are refused, and files copied into a replacement are flushed before publication. Regression coverage exercises SpotX, Spicetify, an official theme, a community theme, a community extension, Marketplace, and a custom app from the bundle. The format is documented in schemas/asset-cache-bundle.json. The manifest and command output both call out Spotify itself because SpotX still obtains the Spotify installer through Spotify's vendor download chain.
Answer-file spotx.customPatchesEnabled and spotx.customPatchesJson mirror the WPF custom patch editor for reviewed custom SpotX patch sets.
Undo is deliberately narrower than general rollback: select the source operation and token exactly as reported by the latest receipt, review --dry-run, then pass --yes. The current allowlist restores only captured user-PATH additions when the registry value, type, and fingerprint still match; stale, unknown, elevated, destructive, and non-low-risk tokens are refused without mutation.
Executable samples live under samples/deployment/. The examples below are
covered by the local parser smoke tests so README commands, sample scripts, and
the CLI grammar stay aligned.
Intune Win32 detection command:
LibreSpot.Cli.exe detect --intuneIntune Win32 install command, PDQ Deploy install step, or SCCM application program command:
LibreSpot.Cli.exe install --answer-file .\librespot-answer.json --profile standard --silent --yes --no-restart --ndjsonPDQ or SCCM repair command using a health-report repair ID:
LibreSpot.Cli.exe repair --repair-id RepairMarketplace --silent --yes --ndjsonUninstall LibreSpot customizations while keeping Spotify installed:
LibreSpot.Cli.exe uninstall --silent --yes --keep-spotify --ndjsonWinRM or PSRemoting over SSH:
Invoke-Command -ComputerName PC-42 -ScriptBlock { C:\ProgramData\LibreSpot\LibreSpot.Cli.exe reapply --answer-file C:\ProgramData\LibreSpot\librespot-answer.json --profile standard --silent --yes --no-restart --ndjson }
ssh admin@PC-42 "C:\ProgramData\LibreSpot\LibreSpot.Cli.exe detect --json"Endpoint return-code handling:
| Code | Meaning | Intune behaviour | Endpoint handling |
|---|---|---|---|
0 |
Success or compliant | success |
Treat as success. |
1 |
Unexpected backend failure | failure |
Collect the NDJSON log and support bundle. |
2 |
Validation or configuration error | failure |
Fail the deployment and review stderr/JSON. |
10 |
LibreSpot target state not installed | failure |
Intune detection should mark app absent. |
11 |
Drift detected | failure |
Run the documented repair or reapply command. |
12 |
Repair needed | failure |
Run a health-report repair ID such as RepairMarketplace. |
13 |
Completed with selected assets missing | success |
Configure exit 13 as success in Intune, then review stderr or NDJSON for each missing asset. |
20 |
Blocked by local state, such as Spotify running | retry |
Retry after closing Spotify or during a maintenance window. |
30 |
Network or rate-limit failure | retry |
Retry later. A download, API call, or connectivity check failed transiently. |
40 |
Hash or signature trust failure | failure |
Stop and investigate. A download did not match its pinned SHA256 or signature. |
50 |
Insufficient permissions | failure |
Check that the run context owns the per-user Spotify and LibreSpot folders. |
60 |
Canceled | failure |
The caller or user stopped the run. Nothing partial is left behind. |
1618 |
Another install is in progress | retry |
Retry after the other installer or LibreSpot run finishes. |
3010 |
Success, reboot recommended | softReboot |
Treat as success and let the endpoint tool schedule a restart. |
1641 |
Reboot initiated | hardReboot |
LibreSpot started the restart. Expect the session to end. |
Every code above is defined in schemas/fleet-exit-codes.json, which is the
contract endpoint tooling should read. The Intune column repeats that file's
intuneBehavior value verbatim, and a test fails when the two disagree.
Mutating examples above write rotating NDJSON logs under
%ProgramData%\LibreSpot\logs; add --log-dir <path> to redirect logs into an
endpoint-tool collection folder. Use samples/deployment/librespot-answer.json
as a starting answer file and keep riskAcknowledged explicit in any production
copy.
Package-manager distribution remains disabled. The local release manifest is the source of truth for the eight published assets, and there are no checked-in package templates or install-level package checks.
The script and the compiled LibreSpot.exe log full removal as seven numbered phases:
- Process termination (with retry logic)
- Microsoft Store / AppX removal
- File system cleanup (Roaming, Local, Temp, cache, shortcuts, glob patterns)
- Registry cleanup (uninstall keys, protocol handlers, app paths, startup entries)
- Scheduled task removal
- Firewall rule removal
- Verification sweep with retry
The desktop app and the fleet CLI run their own cleanup and report it as progress rather than numbered phases. It covers processes, the Microsoft Store package, files and shortcuts, the registry, scheduled tasks, and a final verification sweep. It does not remove firewall rules or sweep the temporary-folder patterns, so use the script for those.
Custom Install exposes all 27 SpotX static lyrics color options: spotify, blueberry, blue, discord, forest, fresh, github, lavender, orange, pumpkin, purple, red, strawberry, turquoise, yellow, oceano, royal, krux, pinkle, zing, radium, sandbar, postlight, relish, drot, default, and spotify#2.
Prism, the bundled theme. LibreSpot's own Spicetify theme. It travels inside the package, so it installs from disk with nothing to download and no pinned release asset that can go stale. Four schemes: Dark, Light, OLED, and HighContrast.
Prism does three things the wider theme ecosystem has not shipped. It switches between light and dark on a clock you set, which matters because Spotify launches its browser with dark mode forced and prefers-color-scheme reports the wrong answer to every theme that asks. It repaints the play button, progress bar, and highlights from the current album art through Spotify's own colour extractor, falling back to the scheme's fixed accent when that service is unavailable. It runs a one-second frame-rate probe after the engine starts, dropping from full glass to a cheaper tier on its own when the machine cannot keep up. The probe has a deadline and defers when Spotify is in the background, so it cannot hold normal controls or lower effects from a throttled sample. Reduced-motion users get the flat, fast version with no probe at all. Appearance, effects, dynamic accent, and the auto-reduce switch live in one dialog reached from the profile menu.
Every file is pinned by SHA256 in all three hosts, so a truncated or edited copy is refused instead of half-installed. The theme is UI customization only: nothing in it touches ads, Premium state, telemetry, or any Spotify binary, and removing the theme reverses all of it. When a theme is replaced, LibreSpot walks only the installed tree and unlinks nested junctions before copying the new files. An old or malformed theme tree cannot redirect that cleanup into another folder.
Compact and Accessibility, also bundled. Compact is a dense layout for large libraries and small Spotify windows. Accessibility gives large targets, a readable font option, strong focus rings, and no transparency. Both carry the same four schemes as Prism, and both preview live in Custom Install.
16 official themes: Sleek, Dribbblish, Ziro, text, StarryNight, Turntable, Blackout, Blossom, BurntSienna, Default, Dreary, Flow, Matte, Nightlight, Onepunch, and SharkBlue.
Blackout is retained deliberately. Upstream removed it from spicetify-themes on 2026-07-14, after the df033493 commit LibreSpot pins, so LibreSpot still ships the last published version rather than dropping a theme people have applied. Advancing the theme pin would remove it, which is why that advance is a recorded decision rather than a routine bump.
5 community themes: Catppuccin (4 flavors), Comfy, Bloom (Fluent Design), Lucid (dynamic album-art backgrounds), and Hazy (glassmorphism). Downloaded directly from their GitHub repos.
Each theme ships with its full set of color schemes. Live theme previews load inline when selecting a theme in Custom Install. Or skip the theme and use the Marketplace to browse and install themes from within Spotify.
samples/spotx-custom-patches-prism.json is a small companion to Prism: two cosmetic tweaks written in SpotX's own patches.json format, ready to paste into Custom Install > Custom Patches. Because they land at the SpotX layer they survive without Spicetify. They are cosmetic only.
Built-in (ship with Spicetify CLI):
| Extension | Description |
|---|---|
| Full App Display | Full-screen album art with blur and playback controls |
| True Shuffle | Fisher-Yates shuffle instead of Spotify's weighted algorithm |
| Trash Bin | Auto-skip songs and artists you've marked as unwanted |
| Keyboard Shortcuts | Vim-style navigation bindings |
| Bookmark | Save and recall pages, tracks, albums, and timestamps |
| Loopy Loop | Set A-B loop points on any track |
| Pop-up Lyrics | Synchronized lyrics in a separate resizable window |
| Auto Skip Video | Skip canvas videos and region-locked content |
| Auto Skip Explicit | Skip tracks marked as explicit |
| Web Now Playing | Expose now-playing data for Rainmeter widgets |
Community (downloaded from GitHub during install):
Every community extension is opt-in. Recommended Setup installs only Full App Display, True Shuffle, and Trash Bin from Spicetify's built-in set.
| Extension | Description |
|---|---|
| Hide Podcasts | Remove podcast, episode, and audiobook UI elements |
| Beautiful Lyrics | Immersive synced lyrics with dynamic backgrounds and blur |
| Playlist Icons | Custom icons and folder images for playlists |
| Volume Percentage | Exact volume percentage next to the slider |
| Ad-block (Spicetify fallback) | Spicetify-layer ad blocking for when SpotX patching fails on a newer Spotify build, a fallback, not a SpotX replacement |
Custom Install also exposes Stats from harbassan/spicetify-apps. LibreSpot downloads the pinned stats-v1.1.3 release ZIP, verifies SHA256, installs it to Spicetify's CustomApps\stats directory, and registers custom_apps = stats. Stats is off by default. Some Stats views can contact Last.fm when opened inside Spotify.
Spotify auto-updates roughly every 1-2 weeks and overwrites the SpotX patches every time. Manually reapplying after every update gets old fast.
Maintenance > Protect and repair > "Auto-reapply when Spotify updates itself" registers a per-user scheduled task that fires at logon and repeats every 30 minutes. Between those repeats it watches Spotify's own folders, so an update that lands a minute after a check is picked up in about a minute rather than waiting out the half hour; the repeat stays as the backstop if watching is not possible. It silently does nothing unless Spotify's version actually changed; when it changes, it hash-verifies the pinned SpotX script and reruns your saved config, but only when Spotify is closed, so it never interrupts playback. Every action gets logged to %APPDATA%\LibreSpot\watcher.log for audit.
You can also manage the task from the command line if you prefer:
LibreSpot.ps1 -InstallWatcher # register the scheduled task
LibreSpot.ps1 -UninstallWatcher # remove it
LibreSpot.ps1 -Watch # run one tick manually (what the task invokes)
LibreSpot.ps1 -Clean # pre-tick Recommended setup + Clean Install for a one-shot rebuild
LibreSpot.ps1 -RemoveSelfData # unregister the watcher and delete all LibreSpot-owned data, then exit- Responsive UI, the script runs an install in background runspaces, and the desktop app runs it in a separate PowerShell process. Either way the window stays responsive with a live log, elapsed timer, and progress bar
- Windows shell integration, WPF builds register
librespot://sharing and.librespotExplorer handlers, route double-clicked profile files through the validated preview/confirm flow, expose jump-list/taskbar actions, and minimize to a tray icon with clickable completion notices - Least-privilege desktop workflow, WPF setup and maintenance run in the current standard-user session without relaunching the whole app through UAC; the legacy PowerShell and PS2EXE entry points retain their existing self-elevation behavior
- Profile sharing cards, WPF Custom mode renders an inert local share URI, QR card, selected-profile comparison, embedded changelog preview, and community links without requiring a hosted sharing service
- Runtime localization, WPF builds include a persisted language selector with reviewed EN, RU, ZH-Hans, PT-BR, and ES resources; validation rejects missing/raw UI strings, broken placeholders, translated product/file tokens, and unreviewed English carry-over
- Window management, Spotify and installer windows are hidden while an install runs, in both the script and the desktop app. Only the script keeps its own window on top until the run finishes
- Settings persistence, your Custom Install configuration is saved to
%APPDATA%\LibreSpot\config.jsonand restored next launch - Community asset verification, opt-in community extensions, themes, and custom apps are pinned in
schemas/community-assets.jsonwith provenance, SHA256, license, branch, support, fallback, network-behavior, and catalog-review metadata; the review gate rejects archived, stale, undocumented, or unknown-network entries from easy-mode defaults while retaining deferred entries as opt-in, and Maintenance health,status --json, and redacted support bundles report the decision and reason without failing offline - Community catalog: browse the reviewed asset list and its trust evidence on the LibreSpot community catalog, generated from the same schemas used by the local review gate. Each card records what the asset does over the network and whether it touches the Spotify Web API, because since February 2026 an extension calling that API with its own client ID works for five people and then stops. None of the reviewed assets does; every one either stays inside the Spotify client's own APIs or makes no Spotify call at all
- Marketplace visibility evidence, Reapply and Repair Marketplace record the installed files, manifest version,
custom_appsregistration, Spicetify apply stage, directspotify:app:marketplaceopen attempt, and last observed Spotify process so Maintenance andstatus --jsoncan distinguish files installed from likely visible - Repair preservation, before Reapply or Repair Marketplace replaces managed Spicetify files, LibreSpot snapshots
config-xpui.iniandCustomAppsunder%USERPROFILE%\LibreSpot_Backups, restores only missing files, and retains support-bundle evidence. Health backups include Marketplace's ownedmarketplace:keys from IndexedDB and its localStorage fallback, but arbitrary Marketplace-installed files and unrelated browser state still require Marketplace's own export/import controls - In-Spotify backup recovery, a raw
.librespotprofile is an engine-only recovery input. Health's complete backup envelope snapshots the engine bytes and Marketplace's owned settings before restore. If either write fails, it puts back the exact prior bytes and keys, removes keys introduced by the failed merge, and keeps a bounded recovery copy when compensation cannot finish. Marketplace reset keeps its own copy outside the database until you restore or dismiss it, and can recreate its known settings store after deletion - Asset-cache inventory, verified download-cache entries keep source labels, source URLs, byte size, first-seen, last-used, and last-verified metadata; corrupt files are quarantined with journal receipts, and Maintenance,
status --json, and support bundles show cache count, size, stale, corrupt, and clear-cache state. Fleet admins can export a complete cache and import it offline with full manifest, ZIP-layout, size, and SHA256 verification - Config backup, up to 5 rotating Spicetify config backups stored in
%USERPROFILE%\LibreSpot_Backups - Architecture support, the Spicetify CLI download is pinned with a separate SHA256 for x64 and ARM64. LibreSpot's own desktop and CLI executables are built for x64 only and run under emulation on ARM devices
- Dual download methods, every lane falls back to a BITS transfer when
Invoke-WebRequestfails - Self-elevating script,
LibreSpot.ps1and the compiledLibreSpot.exerequest administrator rights when a step needs them. The desktop app and the fleet CLI stay in the current user's session instead
Will this break if Spotify updates? SpotX blocks Spotify auto-updates by default. If you manually update Spotify, use Maintenance > Reapply After Update to re-patch.
What should I do after Spotify updates? Open Maintenance and check the After Spotify update note. LibreSpot compares the current Spotify version with the last patched version, watcher status, Spicetify apply result, and Marketplace state, then points to the safest next action: close Spotify, reapply the saved profile, repair Marketplace, remove Spicetify customizations, or open logs.
Can I use this with a Premium account? Yes. Enable "Premium account (skip ad-blocking)" in Custom Install to skip ad-related patches while keeping all other modifications.
How do I change my theme later? Re-run LibreSpot in Custom mode to pick a different theme, or use the optional Spicetify Marketplace to browse and apply themes from within Spotify. LibreSpot installs your selected themes, extensions, and custom apps directly, Marketplace is an add-on for discovering more, not required.
Marketplace is installed but I do not see it.
Use Maintenance > Repair and open Marketplace. LibreSpot reinstalls the custom app, re-enables custom_apps, reapplies Spicetify, and opens spotify:app:marketplace directly.
Marketplace-installed themes or extensions reset when Spotify closes. This is a known upstream issue (spicetify/cli#3837). Themes and extensions installed through LibreSpot's Custom Install are not affected because they are applied directly. If you rely on Marketplace-only additions, uncheck "Install the Spicetify Marketplace" in Custom mode and choose bundled themes/extensions instead.
What is included in a profile or backup?
A raw .librespot profile contains LibreSpot-managed engine settings only. Health's complete backup envelope also includes the owned marketplace: keys it can read from Marketplace's IndexedDB and localStorage fallback. It does not copy arbitrary Marketplace theme or extension files, unrelated browser state, credentials, or cloud data.
How do I collect diagnostics without leaking local paths or secrets? Use Maintenance > Support bundle. LibreSpot previews the selected health report, operation journal, log, and crash-report windows, redacts local user/machine paths, GitHub headers, proxy credentials, tokens, passwords, and command-line secret arguments, then writes a local zip. The manifest includes the latest stable operation GUID so support evidence can be matched to the activity dialog and logs. If file logging fails, the activity view reports it once and the bundle lists unreadable files instead of treating missing logs as complete. Native process output and redirected worker logs use bounded capture with an explicit truncation marker, so a noisy or hung tool cannot grow diagnostic memory without limit. Malformed output bytes are consumed with replacement decoding so later diagnostics still get classified. It does not upload the bundle.
For a crash that the text report cannot explain, turn on Local crash dump under Maintenance diagnostics before the next launch. The switch arms only LibreSpot, requests the .NET Triage format, and keeps two dumps under %LOCALAPPDATA%\LibreSpot\crashes. Self-contained single-file builds need .NET's adjacent createdump.exe helper, so the local release publisher carries that support file beside the desktop and CLI executables and includes it in checksums.txt. The runtime filters personal paths and passwords before writing the binary. LibreSpot never uploads it. While the switch is on, a support bundle includes only the newest dump that passes the Windows Triage header and stream policy and calls out that binary in its privacy report. Those flags and stream checks are policy gates, not proof that every byte is anonymous, so treat the dump as diagnostic memory that may contain sensitive data. LibreSpot checks the format version, header flags, allowed stream kinds, stream directory, and every referenced payload range. A damaged, full-memory, private-memory, or unrelated .dmp file is skipped.
What does Remove LibreSpot Data erase?
Maintenance > Remove LibreSpot data (in the v4 desktop app) deletes LibreSpot-owned config, local profiles, operation journals, logs, crashes, verified cache, backups, and watcher state while leaving Spotify and Spicetify files untouched. It writes a path-free irreversible receipt to %TEMP%\LibreSpot\remove-self-data-receipt.latest.json. In the stable script, run LibreSpot.ps1 -RemoveSelfData for the same cleanup.
How do I go back to stock Spotify? Use Maintenance > Full Reset. This removes all modifications, uninstalls Spotify, and cleans up every trace.
Can I migrate from BlockTheSpot? BlockTheSpot archived its repository in February 2026. LibreSpot's environment health report distinguishes likely BlockTheSpot-family DLL/config artifacts, raw SpotX backups, standalone Spicetify, and LibreSpot-owned state before setup. Review the migration recommendation first: standalone Spicetify config and CustomApps are preserved before setup, while Full Reset removes foreign Spotify state only after its destructive confirmation. The same ownership result is available through CLI status JSON and local support bundles.
Is this safe? Every download is verified against pinned SHA256 hashes. LibreSpot ships its own MIT-licensed hosts and its AGPL-3.0-only in-Spotify app, including Prism and the live engine. SpotX, Spicetify CLI, Marketplace, and the theme archive are fetched from their official GitHub repositories at install time. See Trust & risk disclosure below for enforcement context and account risk details.
My antivirus flagged LibreSpot / SpotX, is it a virus?
A detection alone cannot answer that. Security products can flag scripts and patched application files for several reasons, and LibreSpot will not label a detection harmless on your behalf. Stop before allowing or restoring the file. Confirm that it came from the official LibreSpot release or the pinned upstream source, then compare its SHA256 with the matching entry in that same release's checksums.txt or LibreSpot's logged pin. A matching hash establishes file identity, not safety. If the source or hash does not match, or cannot be confirmed, leave the file blocked and delete the download. If both match, review the detection in Windows Security Protection History and submit the exact file to Microsoft Security Intelligence or your security vendor for analysis. Do not add an antivirus exclusion or turn off protection for LibreSpot.
Windows SmartScreen says "Unknown publisher", what do I do?
LibreSpot ships unsigned by design and is not code-signed. SignPath Foundation OSS signing was evaluated and set aside, so there is no pending certificate to wait for. Do not bypass the warning merely because this README says the project is legitimate. First confirm that the file came from the official Releases page and that its SHA256 matches checksums.txt from the same release. A match proves identity only. Continue only when your Windows policy permits unsigned software and you have independently accepted that risk. Leave the file blocked if you are unsure.
Expect the warning again on the next release. SmartScreen builds reputation per file, and an unsigned artifact starts from nothing every time, so a version you have run happily for months earns no credit for the one that replaces it. That is not a sign something changed for the worse.
Smart App Control blocks LibreSpot from running.
This applies to everything LibreSpot ships, not just the script: LibreSpot-Desktop.exe, LibreSpot.Cli.exe, LibreSpot.exe and LibreSpot.ps1 are all blocked while Smart App Control is on, because it refuses unsigned code and none of them is signed. There is no per-app allowance, no "run anyway", and no exclusion list: the feature is on, in evaluation, or off for the whole device. Turning it off used to mean reinstalling Windows. The preview update that changed this, KB5079391, was withdrawn after it failed to install with error 0x80073712. The update that actually shipped is out-of-band KB5086672 (2026-03-31), builds 26200.8117 and 26100.8117. On it, Windows 11 24H2 and 25H2 can switch Smart App Control off from Settings > Privacy & security > Windows Security > App & browser control, and switch it back on later. No clean install is needed.
Leave Smart App Control enabled. LibreSpot does not provide or recommend a bypass, and turning a security feature off to run one unsigned program is a decision only you can make. The supported answer is to run LibreSpot on a device where Smart App Control is off or still in evaluation mode. If you do decide to turn it off on a recent Windows 11 build, confirm the file's SHA256 against checksums.txt from the same release first, because that check is the only identity evidence left once the platform stops doing it for you. On a managed device, ask the administrator whether an approved LibreSpot artifact is allowed.
What LibreSpot does:
- Downloads SpotX and Spicetify CLI directly from their official GitHub repositories using commit-pinned URLs with SHA256 verification
- Patches the local Spotify installation to remove ads and apply themes/extensions
- Optionally registers a scheduled task for automatic reapplication after Spotify updates
Downloader hardening (CVE-2025-54100, CVE-2026-26170, CVE-2026-40400): LibreSpot fetches with PowerShell's Invoke-WebRequest. Three Windows PowerShell 5.1 advisories reach that primitive: CVE-2025-54100, a web-content RCE fixed in December 2025, CVE-2026-26170, a local elevation fixed in April 2026, and CVE-2026-40400, a relative path traversal that executes code over a network, fixed on 2026-07-14. The two mitigations are SHA256 pinning (guarantees payload integrity) and patch level (keeping Windows updated closes the interpreter-side vectors). SHA256 alone does not remove them on an unpatched host. LibreSpot adds a non-blocking preflight that warns when the host predates 2026-07-14 and names which of the three are still unfixed there. See SECURITY.md for details.
PowerShell 7.6.0 through 7.6.4 also receive a non-blocking security-floor warning for CVE-2026-50523 and related August 2026 fixes. Update to PowerShell 7.6.5 or later before continuing. See SECURITY.md for details.
What LibreSpot does NOT do:
- Collect, transmit, or store any credentials, tokens, or account data
- Bundle or redistribute Spotify binaries. LibreSpot's own hosts and in-Spotify app are part of the release, while SpotX, Spicetify CLI, Marketplace, and theme archives are retrieved from their upstream sources at install time
- Communicate, as LibreSpot itself, with any server other than GitHub (for downloads) and Spotify (normal app traffic)
- Modify Spotify's authentication, payment, or account systems
Note on community extensions and custom apps: the bullet above covers LibreSpot itself. Some opt-in community entries you can enable in Custom Install do contact their own services, for example, Beautiful Lyrics fetches lyrics from a third-party backend and uses an external API for optional Discord features, while Stats can contact Last.fm-backed views. Entries that talk to a third-party service are flagged in the Custom Install catalog and recorded in
schemas/community-assets.jsonundernetworkBehavior. They are off by default.
Browser engine age: Spotify's desktop client is a Chromium app, so pinning Spotify pins the browser engine inside it. The reviewed 1.2.93 build ships Chromium 146 (read from libcef.dll on 2026-09-04, recorded in schemas/compatibility-baseline.json). Chromium releases security fixes on its own schedule and CEF does not backport them, so that engine will fall behind current Chrome until the reviewed tuple moves to a newer Spotify. Maintenance shows the engine version beside the detected Spotify build. This is the trade the pin makes: a client the whole stack is verified against, running a browser engine that is older than the one in your browser.
Account risk: Spotify's Terms of Service and User Guidelines prohibit circumventing ads and modifying the client. While enforcement against individual users of tools like SpotX has not been publicly documented, using LibreSpot is at your own risk. LibreSpot provides a "Full Reset" option in Maintenance mode to return Spotify to its unmodified state at any time.
Enforcement landscape: Spotify has increased enforcement against client modification tools. In September 2025, Spotify DMCA'd ReVanced (which redistributed patched Spotify APKs). In January 2026, Spotify added server-side dual-sync verification that terminated modified mobile app sessions (causing xManager and ReVancedXposed to archive). In February 2026, Spotify tightened Developer Platform access (Premium required for Dev Mode, 1 Client ID per developer, 5 authorized users). BlockTheSpot, which injected DLLs into the Spotify process, archived its repository in February 2026. Desktop patching (SpotX's approach, which LibreSpot wraps) operates at the network/rendering layer and has not been affected by the mobile enforcement wave. LibreSpot does not redistribute patched binaries, does not inject DLLs, does not use Spotify API Client IDs, and downloads only from official upstream GitHub repositories with hash verification. LibreSpot monitors Spotify's first launch after patching for session stability, if Spotify exits unexpectedly within 20 seconds, LibreSpot warns in the install log so you can investigate before assuming the setup is complete. Users should review Spotify's User Guidelines and make their own informed decisions.
Returning to stock Spotify:
Use Maintenance > Full Reset. This removes all modifications, uninstalls Spotify, and cleans up every trace. You can also manually run spicetify restore followed by a clean Spotify reinstall. See SECURITY.md for what happens if SpotX or Spicetify are taken down, and how to restore stock Spotify without LibreSpot.
Releases ship unsigned by design. LibreSpot is not code-signed and is not waiting on a certificate: SignPath Foundation OSS signing was evaluated and set aside, so there is no "once the cert arrives" milestone. The three user-facing executable artifacts are LibreSpot.exe, LibreSpot-Desktop.exe, and LibreSpot.Cli.exe. They are published as unsigned artifacts, and Windows SmartScreen may warn about them. The adjacent createdump.exe file is a .NET runtime crash-dump helper, not a fourth entry point. Verify identity with the SHA256 checksums.txt published alongside each release. A matching hash proves that the file is the release artifact, but it does not prove that the file is safe.
The public latest stable release, v4.5.1, ships nine assets: LibreSpot.ps1, LibreSpot.exe, the .NET 10 LibreSpot-Desktop.exe and LibreSpot.Cli.exe, the adjacent createdump.exe helper, librespot-engine.zip, the CycloneDX SBOM, checksums.txt, and librespot-release-manifest.json. The engine archive is the same live customization app the desktop executable carries inside itself, so the script lane can install it from a file next to LibreSpot.ps1 instead of downloading it. The repository itself does not track build artifacts. LibreSpot.exe and checksums.txt are generated fresh for each local release build, so always verify against the copies you downloaded from the latest stable release, not against anything in a source checkout. v4.5.1 ships source script v3.12.0.
The .NET 10 desktop and CLI artifacts publish self-contained and compressed, which embeds the runtime, so they only receive .NET servicing security fixes when rebuilt against a patched runtime. Compression takes the desktop download from about 176 MB to about 76 MB and, measured on 2026-09-03, makes the first launch faster rather than slower because the file the host reads is less than half the size; later launches cost roughly a quarter of a second more. The numbers and the method are recorded in schemas/publish-footprint-budget.json. Both projects set TargetLatestRuntimePatch, and Build-Scripts.ps1 -DependencyHealth records the resolved Microsoft.NETCore.App / Microsoft.WindowsDesktop.App patch level and fails the release preflight when the build host is below the documented 10.0.11 floor (schemas/dependency-health-allowlist.json → dotnetRuntimeFloor). The release publisher pins RuntimeFrameworkVersion to the selected .NET 10 runtime directory and copies createdump.exe from that same directory, so the crash helper matches the runtime embedded in both single-file apps. Build release artifacts on an up-to-date .NET 10 SDK.
The advanced PowerShell path in Quick Start verifies LibreSpot.ps1 automatically. For manual verification of any downloaded release asset:
# Compare the hash of each downloaded asset to its line in checksums.txt
function Get-Sha256 {
param([string]$Path)
$cmd = Get-Command Get-FileHash -ErrorAction SilentlyContinue
if ($cmd) { return (Get-FileHash -LiteralPath $Path -Algorithm SHA256).Hash.ToUpperInvariant() }
$stream = [System.IO.File]::OpenRead($Path); $sha = [System.Security.Cryptography.SHA256]::Create()
try { return (($sha.ComputeHash($stream) | ForEach-Object { $_.ToString('x2') }) -join '').ToUpperInvariant() }
finally { $stream.Dispose(); $sha.Dispose() }
}
Get-Sha256 .\LibreSpot-Desktop.exe
Get-Sha256 .\LibreSpot.exe
Get-Sha256 .\LibreSpot.ps1
Get-Content .\checksums.txtGitHub Actions build-provenance attestations are not produced by the local release process because this repository intentionally does not track build workflows. Immutable GitHub releases do generate a Sigstore-verifiable release attestation when they are published. Run gh release verify v4.5.1 to verify the release tag and commit, then run gh release verify-asset v4.5.1 .\LibreSpot-Desktop.exe for a downloaded asset. Source archives are not covered by gh release verify-asset. Use checksums.txt, the release manifest, and the SBOM as the local build evidence, then match the SHA256 in checksums.txt to confirm a download is authentic.
Releases are built and uploaded from the maintainer machine. GitHub Actions do not build, test, or publish release assets. Run the local gates first.
The xUnit 4 projects are Microsoft Testing Platform applications. Build them, then invoke their generated executables directly so the MTP filters and reporting options are passed to the test runner itself:
.\Build-Scripts.ps1 -Validate
.\Build-Scripts.ps1 -Lint
.\Build-Scripts.ps1 -DependencyHealth
dotnet build .\tests\LibreSpot.Desktop.Tests\LibreSpot.Desktop.Tests.csproj --no-restore
.\tests\LibreSpot.Desktop.Tests\bin\Debug\net10.0-windows\LibreSpot.Desktop.Tests.exe --filter-not-class "*Wpf*" --minimum-expected-tests 1 --progress off
dotnet build .\tests\LibreSpot.Core.Tests\LibreSpot.Core.Tests.csproj --no-restore
.\tests\LibreSpot.Core.Tests\bin\Debug\net10.0-windows\LibreSpot.Core.Tests.exe --minimum-expected-tests 1 --progress off
powershell -NoProfile -ExecutionPolicy Bypass -Command "Import-Module Pester -RequiredVersion 5.9.1; Invoke-Pester -Configuration (New-PesterConfiguration -Hashtable (& .\tests\powershell\pester.config.ps1))"Build the release root, compile LibreSpot.ps1 with PS2EXE, generate the
CycloneDX SBOM, write SHA256 checksums.txt, then create the release manifest:
.\Build-Scripts.ps1 -PublishRelease
.\Build-Scripts.ps1 -CompileStableExe
.\Build-Scripts.ps1 -GenerateSbom
.\Build-Scripts.ps1 -GenerateChecksums
.\Build-Scripts.ps1 -GenerateReleaseManifest -ReleaseRoot .\publish -ReleaseVersion 4.5.1 -ReleaseChannel stable-PublishRelease empties publish, publishes the desktop and CLI projects as
self-contained single-file win-x64 executables, copies the matching .NET
createdump.exe helper beside them, and copies in LibreSpot.ps1 and
resources\custom-apps\librespot-engine.zip. It pins the build properties
that make the output reproducible (Deterministic,
ContinuousIntegrationBuild, EmbedUntrackedSources, PublishRepositoryUrl)
and prints the size and SHA256 of each asset. The release manifest records the
SDK version, the commit, and that property set under buildInputs, so anyone
can rebuild the same commit and compare.
Publishing the same commit twice produces byte-identical
LibreSpot-Desktop.exe and LibreSpot.Cli.exe. LibreSpot.exe is the
exception: ps2exe does not build reproducibly, so verify that one against the
checksums.txt published with it rather than by rebuilding.
-CompileStableExe writes publish\LibreSpot.exe with the pinned PS2EXE flags
(icon, admin manifest, no console, and the file version taken from
LibreSpot.ps1) and needs the ps2exe module available to pwsh. Its child
PowerShell process permits that reviewed local module to load even when the
current user's execution policy blocks unsigned module scripts.
-GenerateSbom restores the pinned CycloneDX 6.2.0 local tool and writes
publish\LibreSpot.sbom.cdx.json for the desktop project. It reads the assets
already restored by -PublishRelease without changing the locked dependency
graph. Manifest generation then re-checks that file version against the script, checks the
SBOM is CycloneDX 1.7 from that tool with per-component hashes and licenses,
and measures the desktop executable against the publish footprint budget, so a
mismatched or oversized artifact fails before the release is uploaded.
-GenerateChecksums hashes the seven artifacts the release contract covers,
which is every published asset except the SBOM and the release manifest, and
writes the checksums.txt file consumed by manifest generation. Nine files are
uploaded; seven of them carry a checksum line.
Create and push the version tag, create a draft GitHub release, upload every
file in publish, and publish the draft only after the asset list is complete.
Immutable release protection applies when the draft is published. Finish with
the release truth check and the GitHub attestation checks:
.\Build-Scripts.ps1 -ReleaseTruth
gh release verify vX.Y.Z
gh release verify-asset vX.Y.Z .\publish\LibreSpot-Desktop.exeCompare every downloaded file with checksums.txt. gh release verify-asset
does not cover GitHub source archives.
gh-pages serves the public catalog page. It is generated output, so it has to
be regenerated and pushed whenever schemas/community-assets.json or
schemas/theme-preview-manifest.json changes. Otherwise the page keeps
advertising trust evidence, review decisions, and pins that the repository no
longer stands behind.
.\Build-Scripts.ps1 -CatalogTruthThat fetches gh-pages into a ref it owns, regenerates the catalog into a
temporary directory, and compares it with the published catalog.json. A
mismatch fails and names the regenerate step. catalog.json carries a SHA256
of each source schema, so a change to a manifest field the page does not render
(an assetPath, an easyModeDefault) is caught too, not just the fields that
show on a card.
When the remote cannot be reached the check warns and passes, so an offline
machine is not blocked. It only warns for an unreachable remote: if
the fetch succeeds and the catalog still cannot be read, that is a failure.
-Validate runs the same comparison against whatever origin/gh-pages the
clone already has, without fetching.
When it reports drift, regenerate and push:
$staging = Join-Path $env:TEMP 'librespot-catalog'
.\tools\Build-CommunityCatalog.ps1 -OutputDirectory $staging
git worktree add ..\LibreSpot-ghpages gh-pages
Copy-Item "$staging\*" ..\LibreSpot-ghpages -Recurse -Force
git -C ..\LibreSpot-ghpages add -A
git -C ..\LibreSpot-ghpages commit -m "Publish the reviewed community catalog"
git -C ..\LibreSpot-ghpages push origin gh-pages
git worktree remove ..\LibreSpot-ghpages
.\Build-Scripts.ps1 -CatalogTruthThe generator decodes both schemas as UTF-8 and writes JSON through one canonical formatter. The documented command therefore produces byte-identical output in Windows PowerShell 5.1 and PowerShell 7. Its cross-edition Pester contract also pins a fixed-date catalog digest. An intentional schema or format change needs a reviewed digest update.
Run dependency-health checks before release packaging:
.\Build-Scripts.ps1 -DependencyHealthThis writes publish\dependency-health.json, fails on outdated direct NuGet
packages, records vulnerable package metadata, and allows only documented
test-only transitive lag from schemas\dependency-health-allowlist.json. It also
audits the live customization engine's JavaScript dependencies with pnpm audit,
both the shipped tree and the build tooling, and fails on any advisory that is
not accepted in the same allowlist with an owner, a reason and a recheck date.
The UI automation suite runs an Axe.Windows rule scan, the same engine behind
Accessibility Insights, against the Home, Settings and Maintenance states. The
shell is launched hidden, so the scan never takes over the screen. The
--uia-capture=<path> option writes the requested PNG at the path supplied by
the caller; the other UI-automation state stays under its isolated root:
.\tests\LibreSpot.Desktop.Tests\bin\Debug\net10.0-windows\LibreSpot.Desktop.Tests.exe --filter-method "*AxeWindowsScan*" --minimum-expected-tests 1Known violations live in schemas\axe-windows-baseline.json with a count and a
reason for each. A new violation, or one more of an existing kind, fails the
scan. A fourth test plants a button with no accessible name and fails if the
scan does not report it, so a scan that has quietly stopped working cannot pass
as a clean result.
The repository also carries a bounded Core mutation pilot. Restore the local
tool and run it from src\LibreSpot.Core when changing Core logic:
dotnet tool restore
Push-Location .\src\LibreSpot.Core
dotnet stryker --test-runner mtp --concurrency 1
Pop-LocationThe MTP runner is still preview software. The baseline is 24.51% over
1,477 tested mutants, measured 2026-09-05, with a 24% break threshold in
src\LibreSpot.Core\stryker-config.json. Treat the report as a regression
ratchet, not as a release gate for the WPF shell.
Exercise the auto-reapply watcher through a uniquely named, standard-user, disposable Task Scheduler task:
.\Build-Scripts.ps1 -WatcherIntegrationThe test runner isolates all watcher files under %TEMP%, covers success and
failure/cancellation state transitions, emits Scheduler evidence on failure,
and removes its task and temp data in a finally block.
Run the rendered WPF state matrix without activating foreground windows:
.\tools\Invoke-WpfQaMatrix.ps1The command captures and verifies Home setup, healthy, safe-repair, and recovery-review states, plus Settings, Maintenance, navigation, readiness, Details, undo, support-bundle, profile, prompt, loading, error, success, and nested crash-dialog surfaces across the supported dark/high-contrast palettes
and English/Spanish locales, plus a long-text prompt in every advertised
non-English locale. It rejects unnamed actions, clipped primary text, missing
focus rings, incomplete renders, and mismatched capture metadata. Captures use
a temporary directory and are removed after a passing run; pass -OutputPath <directory> to retain them for review or -Quick for the English dark-state
sweep, one Spanish high-contrast proof, and the four long-text locale proofs.
Development planning is maintained in local working-tree docs. ROADMAP.md is the only active queue for incomplete work; completed work is represented by Git history and release notes.
If you want to understand what the upstream tools actually change inside Spotify (the binary patches, the bundle rewrites, how themes and feature flags work, and why the two tools sometimes fight), read docs/how-spotx-and-spicetify-alter-spotify.md.
LibreSpot is a wrapper and installer, the real work is done by these projects:
- SpotX, Spotify ad-blocking and patching
- Spicetify CLI, Spotify theming and extension framework
- Spicetify Marketplace, In-app store for themes and extensions
- Spicetify Themes, Official community theme collection
The in-Spotify live customization engine under src/LibreSpot.App is an AGPL-3.0 component because it incorporates compatible upstream work. Its license and third-party notices apply to that component.










