release: publish 1.0.7 Windows shell fixes
Windows CI / verify (push) Failing after 8s

Stabilize Start menu and desktop shortcut migration with persistent versioned icon resources, stale-registration recovery, and explicit Windows shell notifications. Keep development, packaged, and shortcut identities aligned, and add regression coverage for orphaned per-user installs, reduced-motion changelog transitions, and update-popover pointer transit.
This commit is contained in:
Sucukdeluxe
2026-08-12 12:55:46 +02:00
parent 5bc58a0d85
commit 49033f9ff2
13 changed files with 195 additions and 22 deletions
+16 -4
View File
@@ -7,6 +7,7 @@ const packageLock = JSON.parse(fs.readFileSync(path.join(root, 'package-lock.jso
const mainSource = fs.readFileSync(path.join(root, 'src', 'main.ts'), 'utf8');
const indexSource = fs.readFileSync(path.join(root, 'src', 'index.html'), 'utf8');
const installerSource = fs.readFileSync(path.join(root, 'build', 'installer.nsh'), 'utf8');
const installerSmokeSource = fs.readFileSync(path.join(root, 'scripts', 'smoke-test-installer.js'), 'utf8');
const manifestPath = path.join(root, 'scripts', 'public-release-files.json');
const failures = [];
@@ -14,9 +15,9 @@ function check(condition, message) {
if (!condition) failures.push(message);
}
check(packageJson.version === '1.0.6', `package version is ${packageJson.version}`);
check(packageLock.version === '1.0.6', `lockfile version is ${packageLock.version}`);
check(packageLock.packages?.['']?.version === '1.0.6', `lockfile root package version is ${packageLock.packages?.['']?.version}`);
check(packageJson.version === '1.0.7', `package version is ${packageJson.version}`);
check(packageLock.version === '1.0.7', `lockfile version is ${packageLock.version}`);
check(packageLock.packages?.['']?.version === '1.0.7', `lockfile root package version is ${packageLock.packages?.['']?.version}`);
check(packageJson.build?.appId === 'io.github.sucukdeluxe.twitch-vod-manager', `appId is ${packageJson.build?.appId}`);
check(packageJson.build?.publish?.provider === 'generic', `publish provider is ${packageJson.build?.publish?.provider}`);
check(packageJson.build?.publish?.url === 'https://github.com/Sucukdeluxe/Twitch-VOD-Manager/releases/latest/download/', `publish URL is ${packageJson.build?.publish?.url}`);
@@ -24,12 +25,23 @@ check(JSON.stringify(packageJson.build?.files) === JSON.stringify(['dist/**/*',
check(packageJson.build?.win?.icon === 'build/icon.ico', `Windows icon is ${packageJson.build?.win?.icon}`);
check(packageJson.build?.nsis?.installerIcon === 'build/icon.ico', `installer icon is ${packageJson.build?.nsis?.installerIcon}`);
check(packageJson.build?.nsis?.uninstallerIcon === 'build/icon.ico', `uninstaller icon is ${packageJson.build?.nsis?.uninstallerIcon}`);
check(packageJson.build?.nsis?.shortcutName === 'Twitch VOD Manager', `Windows Start Menu shortcut is not stable: ${packageJson.build?.nsis?.shortcutName}`);
check(installerSource.includes('!macro preInit'), 'installer does not recover from orphaned Windows registration before upgrade detection');
check(installerSource.includes('ReadRegStr $0 HKCU "${INSTALL_REGISTRY_KEY}" InstallLocation'), 'installer does not read the existing per-user install location before upgrade detection');
check(installerSource.includes('${ifNot} ${FileExists} "$0\\${APP_EXECUTABLE_FILENAME}"'), 'installer does not detect a missing executable in an existing per-user registration');
check(installerSource.includes('DeleteRegKey HKCU "${INSTALL_REGISTRY_KEY}"') && installerSource.includes('DeleteRegKey HKCU "${UNINSTALL_REGISTRY_KEY}"'), 'installer does not clear orphaned per-user registration before upgrade detection');
const shortcutIconResource = packageJson.build?.extraResources?.find((entry) => entry?.from === 'build/icon.ico');
check(shortcutIconResource?.to === 'app-icons/icon-${version}.ico', `versioned shortcut icon resource is ${shortcutIconResource?.to}`);
check(installerSource.includes('"$LOCALAPPDATA\\Twitch VOD Manager\\Shortcut Icons\\icon-${VERSION}.ico"'), 'installed shortcuts do not use the persistent versioned icon resource');
check(installerSource.includes('CopyFiles /SILENT "$INSTDIR\\resources\\app-icons\\icon-${VERSION}.ico"'), 'versioned shortcut icon is not copied to persistent storage');
check(installerSource.includes('CreateShortCut "$newDesktopLink"'), 'desktop shortcut is not refreshed with the versioned icon resource');
check(installerSource.includes('CreateShortCut "$newStartMenuLink"'), 'start menu shortcut is not refreshed with the versioned icon resource');
check(installerSource.includes('Delete "$SMPROGRAMS\\Twitch VOD Manager v*.lnk"'), 'legacy versioned Start Menu shortcuts are not removed during upgrade');
const stableStartShortcutBlock = installerSource.match(/Delete "\$SMPROGRAMS\\Twitch VOD Manager v\*\.lnk"([\s\S]*?)System::Call 'shell32::SHChangeNotify\(i 0x00001000/);
check(Boolean(stableStartShortcutBlock) && !stableStartShortcutBlock[1].includes('${if} ${FileExists} "$newStartMenuLink"'), 'stable Start Menu shortcut is not recreated when an older installer did not register it');
check(installerSource.includes('SHChangeNotify(i 0x00001000, i 0x0005, w "$SMPROGRAMS"'), 'Windows Start Menu is not notified after shortcut refresh');
check(installerSmokeSource.includes("'/currentuser'"), 'installer smoke does not force a per-user test installation');
check(installerSmokeSource.includes('assertCleanInstallerSmokeSurface'), 'installer smoke can run against an existing workstation installation');
check(installerSource.includes('SHChangeNotify(i 0x08000000, i 0x1000'), 'Windows shell icon cache is not flushed after shortcut refresh');
check(installerSource.includes('${ifNot} ${isUpdated}') && installerSource.includes('RMDir /r "$LOCALAPPDATA\\Twitch VOD Manager\\Shortcut Icons"'), 'persistent shortcut icons are not cleaned up on a real uninstall');
check(packageJson.build?.win?.signAndEditExecutable !== false, 'Windows executable resource editing is enabled');
@@ -50,7 +62,7 @@ check(mainSource.includes('GITHUB_RELEASES_DOWNLOAD_BASE_URL'), 'GitHub releases
check(mainSource.includes('https://api.github.com/repos/Sucukdeluxe/Twitch-VOD-Manager/releases/latest'), 'GitHub latest release API URL is missing');
check(mainSource.includes('https://github.com/Sucukdeluxe/Twitch-VOD-Manager/releases/download'), 'GitHub release download URL is missing');
check(!/storyboards\/\d{8,12}(?:-|\/)/.test(mainSource), 'numeric Twitch VOD example remains in the public source');
check(indexSource.includes('Version: v1.0.6'), 'initial version label is not 1.0.6');
check(indexSource.includes('Version: v1.0.7'), 'initial version label is not 1.0.7');
check(!indexSource.includes('Version: v4.1.13'), 'legacy version label is still present');
check(fs.existsSync(manifestPath), 'public release manifest is missing');