**Related issue:** N/A — part of the Windows Fleet-maintained apps catalog expansion (letter D batch; follows #48872, #48881, #48950, #48969). Adds twelve new Windows Fleet-maintained apps: | App | winget package | Installer | Notes | |-----|----------------|-----------|-------| | DataSpell | `JetBrains.DataSpell` | NSIS (install4j), machine, x64 | Mirrors the DataGrip FMA pattern: `fuzzy_match_name` + `use_display_version_for_patch` (registry version is a JetBrains build number; marketing version parsed from the name). | | dnGrep | `dnGrep.dnGrep` | MSI, machine, x64 | Versioned+arch ARP name ("dnGrep 5.0.9 (x64)") → fuzzy match. | | Draftable Desktop | `Draftable.Draftable` | MSI, machine, x64 | Uses the machine-scope `DraftableDesktopSystem` MSI. **Caveat:** hard winget dependency on .NET 10 Desktop Runtime — installs fine but won't launch without it (same class as the BleachBit VCRedist dependency). | | dRofus | `dRofus.dRofus` | MSI, machine, x64 | Versioned ARP name ("dRofus 2.18") → fuzzy match. | | Devolutions Launcher | `Devolutions.Launcher` | MSI, machine, x64 | Distinct ARP identity from the existing Remote Desktop Manager FMA. | | Devolutions Workspace | `Devolutions.Workspace` | MSI, machine, x64 | Product renamed: ARP DisplayName is **"Devolutions Password Manager"** (set as `unique_identifier`). `program_publisher` overridden to "Devolutions Inc." (capital I) — verified via msiinfo; the locale-derived lowercase would not match. | | Delinea Connection Manager | `Delinea.DelineaConnectionManager` | MSI, machine, x64 | Dual-purpose MSI defaults to **per-user** (ALLUSERS=2 + MSIINSTALLPERUSER=1); custom install script forces `ALLUSERS=1 MSIINSTALLPERUSER=""`. `program_publisher` = "Delinea Inc.." (double period, as stored in the MSI). Unversioned URL → `ignore_hash`. | | DAX Studio | `DaxStudio.DaxStudio` | Inno, machine, x64 | `/ALLUSERS` for machine scope; versioned ARP name → fuzzy. | | DevPod | `LoftLabs.DevPod` | MSI, machine, x64 | Uses the WiX MSI variant (the manifest also has an NSIS per-user one). | | Directory Opus | `GPSoftware.DirectoryOpus` | Inno, machine, x64 | Standard Inno silent install/uninstall. | | DYMO ID | `DYMO.DYMOID` | InstallShield→MSI, machine, x86 | `/S /V"/qn /norestart"`; uninstall via msiexec by ProductCode. | | digiSeal Reader | `secrypt.digiSealreader` | EXE (self-extracting), machine, x86 | `installer_scope: ""` (manifest declares no scope); `-silent` install, shipped uninstaller with `-silent`. Unversioned URL → `ignore_hash`. | Considered but **not** added (recorded in the workstream tracker): - **Datadog Agent** (`Datadog.Agent`): winget PackageVersion is `7.81.0.1` but the MSI and registry report `7.81.0.0`, so the patch policy would flag every install as perpetually outdated. `use_display_version_for_patch` can't fix it (the manifest has no `AppsAndFeaturesEntries`); it needs a version-normalizing ingester ref (like `onepassword_version_shortener`). Deferred pending that helper (task spawned). - **Dell Display and Peripheral Manager** (`Dell.DisplayAndPeripheralManager`, covers both "Dell Display Manager" and "Dell Peripheral Manager"): the winget-pinned host `dl.dell.com` returns **403** to non-browser User-Agents, and Fleet's downloader sends `Go-http-client` (same failure that dropped Crestron AirMedia in letter C). The `downloads.dell.com` mirror serves the identical path to any UA, but there's no input field to override the manifest URL. Deferred pending a downloader User-Agent fix (task spawned — would also unblock Crestron). - **Dell EMC System Update** (`Dell.SystemUpdate`): registers its ARP entry under **HKCU** (per-user) under a SYSTEM install; legacy product Dell steers users away from (toward Dell Command Update, already an FMA); firmware/driver DUP bootstrapper. - **Devolutions Remote Desktop Manager Agent** (`Devolutions.RemoteDesktopManagerAgent`): legacy/superseded by "Devolutions Agent" (2026.1); winget manifest frozen at 2025.2.28.0 since Sept 2025; vendor docs page 404s. - **Dedoose** (`Dedoose.Dedoose`): per-user-only scope, x86, latest-pointer URL (CloudShow class). - **Defraggler** (`Piriform.Defraggler`): abandoned (final release 2020, no winget commits since 2023); legacy defrag tool with an unverified ARP publisher string. - **DiRoots ProSheets** (`DiRoots.ProSheets`): validated install but its Advanced Installer bootstrapper uninstall hung to the timeout and it drags bundled PDF24 Creator entries into inventory (dropped at validation). - **DroidCam Client** (`dev47apps.DroidCam`): NSIS `/S` install hung headless to the timeout (inline vc_redist); 3DxWare/Citrix headless-hang class (dropped at validation). Identities verified per app (msiinfo Property tables; installer PE/version resources; winget AppsAndFeaturesEntries; uninstall-database corroboration). Two publisher-casing mismatches (Devolutions Workspace, Delinea) were caught by direct MSI inspection and fixed with `program_publisher` before they could silently break the exists queries. SHAs verified against manifests for pinned URLs; `ignore_hash` used only where the manifest is demonstrably actively maintained. Icons via `tools/software/icons/generate-icons.sh` (the pre-existing DataSpell icon component is reused untouched). # Checklist for submitter - [x] Input data is properly validated, `SELECT *` is avoided, SQL injection is prevented (using placeholders for values in statements), JS inline code is prevented especially for url redirects, and untrusted data interpolated into shell scripts/commands is validated against shell metacharacters. - [x] Timeouts are implemented and retries are limited to avoid infinite loops ## Testing - [ ] QA'd all new/changed functionality manually (relying on the FMA CI validator for Windows install/uninstall validation)
59 lines
1.8 KiB
PowerShell
59 lines
1.8 KiB
PowerShell
# Uninstalls digiSeal reader.
|
|
#
|
|
# The setup registers an HKLM ARP entry (DisplayName "digiSeal reader") whose
|
|
# UninstallString points at the shipped "uninstall digiSeal reader.exe". That
|
|
# uninstaller supports a -silent switch for unattended removal.
|
|
|
|
$softwareName = "digiSeal reader"
|
|
|
|
$machineKey = 'HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\*'
|
|
$machineKey32on64 = 'HKLM:\SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall\*'
|
|
|
|
$exitCode = $null
|
|
|
|
try {
|
|
|
|
[array]$uninstallKeys = Get-ChildItem `
|
|
-Path @($machineKey, $machineKey32on64) `
|
|
-ErrorAction SilentlyContinue |
|
|
ForEach-Object { Get-ItemProperty $_.PSPath }
|
|
|
|
foreach ($key in $uninstallKeys) {
|
|
if ($key.DisplayName -eq $softwareName) {
|
|
$raw = $key.QuietUninstallString
|
|
if (-not $raw) { $raw = $key.UninstallString }
|
|
if (-not $raw) { continue }
|
|
|
|
# Parse into executable + args, handling quoted/unquoted/bare shapes.
|
|
if ($raw -match '^\s*"([^"]+)"\s*(.*)$') {
|
|
$exe = $matches[1]; $exeArgs = $matches[2].Trim()
|
|
} elseif ($raw -match '(?i)^\s*(.+?\.exe)\s*(.*)$') {
|
|
$exe = $matches[1]; $exeArgs = $matches[2].Trim()
|
|
} else {
|
|
$exe = $raw; $exeArgs = ""
|
|
}
|
|
|
|
if ($exeArgs -notmatch '(?i)-silent') { $exeArgs = "$exeArgs -silent".Trim() }
|
|
|
|
Write-Host "Uninstall command: $exe"
|
|
Write-Host "Uninstall args: $exeArgs"
|
|
$process = Start-Process -FilePath $exe -ArgumentList $exeArgs -NoNewWindow -PassThru -Wait
|
|
$exitCode = $process.ExitCode
|
|
break
|
|
}
|
|
}
|
|
|
|
} catch {
|
|
Write-Host "Error: $_"
|
|
Exit 1
|
|
}
|
|
|
|
if ($null -eq $exitCode) {
|
|
Write-Host "Uninstall entry not found for '$softwareName'."
|
|
Exit 1
|
|
}
|
|
|
|
Write-Host "Uninstall exit code: $exitCode"
|
|
if ($exitCode -eq 3010 -or $exitCode -eq 1641) { Exit 0 }
|
|
Exit $exitCode
|