feat: Enhance update manager to handle UTF-8 BOM and improve asset resolution logic

This commit is contained in:
claudi 2026-03-12 11:00:43 +01:00
parent 44124595d8
commit 093b196d0d
4 changed files with 46 additions and 2 deletions

View file

@ -0,0 +1 @@
{"timestamp": "2026-03-12T10:57:42.150570", "release": {"tag_name": "v0.8.4", "name": "WebDropBridge v0.8.4", "version": "0.8.4", "body": "Shared branded release for WebDrop Bridge v0.8.4", "assets": [{"id": 49, "name": "AgravityBridge-0.8.4-win-x64.msi", "size": 214445231, "download_count": 2, "created_at": "2026-03-12T08:25:03Z", "uuid": "7ffcd98a-99a9-4100-8e71-3ebe63534b8f", "browser_download_url": "https://git.him-tools.de/HIM-public/webdrop-bridge/releases/download/v0.8.4/AgravityBridge-0.8.4-win-x64.msi", "type": "attachment"}, {"id": 50, "name": "AgravityBridge-0.8.4-win-x64.msi.sha256", "size": 64, "download_count": 2, "created_at": "2026-03-12T08:25:03Z", "uuid": "ddd00072-a5bc-422f-93c0-7cc3bc3408d3", "browser_download_url": "https://git.him-tools.de/HIM-public/webdrop-bridge/releases/download/v0.8.4/AgravityBridge-0.8.4-win-x64.msi.sha256", "type": "attachment"}, {"id": 47, "name": "WebDropBridge-0.8.4-win-x64.msi", "size": 214445229, "download_count": 0, "created_at": "2026-03-12T08:24:20Z", "uuid": "5a20eef9-b77d-4e04-be06-d85c3ebd3f6e", "browser_download_url": "https://git.him-tools.de/HIM-public/webdrop-bridge/releases/download/v0.8.4/WebDropBridge-0.8.4-win-x64.msi", "type": "attachment"}, {"id": 48, "name": "WebDropBridge-0.8.4-win-x64.msi.sha256", "size": 64, "download_count": 0, "created_at": "2026-03-12T08:24:21Z", "uuid": "9972b3bb-7c4b-4b26-951a-5a8dfc1a1f27", "browser_download_url": "https://git.him-tools.de/HIM-public/webdrop-bridge/releases/download/v0.8.4/WebDropBridge-0.8.4-win-x64.msi.sha256", "type": "attachment"}, {"id": 51, "name": "release-manifest.json", "size": 931, "download_count": 0, "created_at": "2026-03-12T08:25:03Z", "uuid": "e3c13ccd-cbc6-4eb1-988e-7f465a75eca6", "browser_download_url": "https://git.him-tools.de/HIM-public/webdrop-bridge/releases/download/v0.8.4/release-manifest.json", "type": "attachment"}], "published_at": "2026-03-12T08:23:40Z"}}

14
.tmp_check_update.py Normal file
View file

@ -0,0 +1,14 @@
import asyncio
from pathlib import Path
from webdrop_bridge.core.updater import UpdateManager
async def main():
manager = UpdateManager(current_version='0.8.3', config_dir=Path('.tmp-update-check'))
release = await manager.check_for_updates()
print('release:', None if not release else (release.tag_name, release.version, len(release.assets)))
if release:
installer, checksum = await manager._resolve_release_assets(release)
print('installer:', None if not installer else installer.get('name'))
print('checksum:', None if not checksum else checksum.get('name'))
asyncio.run(main())

View file

@ -80,7 +80,8 @@ if ($artifactPaths.Count -eq 0) {
exit 1
}
$localData.manifest | ConvertTo-Json -Depth 10 | Set-Content -Path $localManifestPath -Encoding utf8
$localManifestJson = $localData.manifest | ConvertTo-Json -Depth 10
[System.IO.File]::WriteAllText($localManifestPath, $localManifestJson, (New-Object System.Text.UTF8Encoding($false)))
if ($DryRun) {
Copy-Item $localManifestPath $manifestOutput -Force
@ -155,6 +156,12 @@ else {
Copy-Item $localManifestPath $manifestOutput -Force
}
# Ensure uploaded manifest is UTF-8 without BOM (for strict JSON parsers)
if (Test-Path $manifestOutput) {
$manifestText = Get-Content -Raw -Path $manifestOutput
[System.IO.File]::WriteAllText($manifestOutput, $manifestText, (New-Object System.Text.UTF8Encoding($false)))
}
$artifactPaths.Add($manifestOutput)
$assetMap = Get-AssetMap -Assets $releaseInfo.assets

View file

@ -93,7 +93,9 @@ class UpdateManager:
"""Download and parse a JSON asset from a release."""
try:
with urlopen(url, timeout=10) as response:
return json.loads(response.read().decode("utf-8"))
# Some release pipelines may upload JSON files with UTF-8 BOM.
# Use utf-8-sig to transparently handle both BOM and non-BOM files.
return json.loads(response.read().decode("utf-8-sig"))
except (URLError, json.JSONDecodeError) as e:
logger.error(f"Failed to download JSON asset: {e}")
return None
@ -148,8 +150,28 @@ class UpdateManager:
brand_prefix = f"{self.brand_id}-*"
installer_asset = None
# Prefer brand-specific naming when possible.
if self.brand_id == "webdrop_bridge":
preferred_patterns = ["webdropbridge-*.msi", "webdropbridge*.msi"]
else:
preferred_patterns = [f"{self.brand_id.lower()}-*.msi", f"{self.brand_id.lower()}*.msi"]
# 1) Try strict brand-pattern match first
for asset in release.assets:
asset_name = asset.get("name", "")
asset_name_lower = asset_name.lower()
if not asset_name_lower.endswith(extension):
continue
if any(fnmatch.fnmatch(asset_name_lower, pattern) for pattern in preferred_patterns):
installer_asset = asset
break
# 2) Fallback: preserve previous behavior (first installer for platform)
for asset in release.assets:
if installer_asset:
break
asset_name = asset.get("name", "")
if not asset_name.endswith(extension):
continue