Run Winget via an Offer in Self-Service

Good Afternoon,

Our servicedesk uses Winget to quickly update applications on end-user systems to resolve vulnerability tickets. We would like to make this a one-step process by deploying it as an Offer in Self-Service. Unfortunately, it doesn’t look like this works and I’m not sure why. I want to blame Winget, but figured I would post here just to be sure.

I have tried a couple different iterations of the “script” once with Action Script and again with straight PowerShell. Neither of them run the command or create the log file. I tested the PowerShell command locally and it worked fine.

// Action Script to run the winget command on a remote system
parameter "powerShellExe" = "{pathname of file ((it as string) of value "Path" of key "HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\PowerShell\1\ShellIds\Microsoft.PowerShell" of native registry)}"


waithidden "{parameter "powerShellExe"}" -Command "winget upgrade --all --accept-package-agreements --accept-source-agreements --disable-interactivity --silent | Out-File 'C:\Temp\winget.log' -encoding ascii"
# PowerShell script to run Winget on a remote system
Start-Process -FilePath "powershell.exe" -ArgumentList "-Command ""winget upgrade --all --accept-package-agreements --accept-source-agreements --disable-interactivity --silent | Out-File 'C:\Temp\winget.log' -encoding ascii""" -WindowStyle Hidden

I also thought about combining the two, but the punctuation/syntax for that is a nightmare.

Let me know if you have any suggestions.

Many thanks,
_MattG

Does this post help - Why does the powershell script "winget" doesn't work with BigFix? ?

I found a lot of partial solutions for this but hardly anyone has compiled all the steps needed to run winget from BigFix.

First, BigFix runs actions as the SYSTEM user which has quirks with winget. Essentially, winget is an exe file that is can be invoked from command line via “App Paths”. App Paths are here in the registry:

HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\App Paths

HKEY_LOCAL_MACHINE\Software\Microsoft\Windows\CurrentVersion\App Paths

The HKEY_CURRENT_USER registry key is typically where the winget exe path is located and is why the SYSTEM user cannot typically invoke winget.

To get winget working with BigFix, you need to do the following:

  1. Install Microsoft Visual C++ Redistributable 2015-2022 x64.
    • You can get it from here. I think you only need the x64 version for winget to work but there’s no harm in getting both the x86 and x64 versions.
    • Relevance might look something like this:

      not exists key whose (value “DisplayName” of it as string starts with “Microsoft Visual C++ 2015-2022 Redistributable (x64)” and value “DisplayVersion” of it as string as version >= “14.44.35208.0” as version) of key “HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall” of native registry

    • The action script would need this to install silently:

      wait __Download\VC_redist.x64.exe /quiet /norestart

  2. Install winget.
    • There are TONS of ways to install winget. There is a way to deploy it as a package (link) but for the sake of sharing here I’ll share the programmatic way of downloading the latest version of winget via PowerShell.
    • If you just want to download the fixlet, here is the bigfix.me link.
    • Relevance 1

      (name of it starts with “Win” and version of it >= “10.0.16299.0”) of operating system and true

    • Relevance 2

      exists key whose (value “DisplayName” of it as string starts with “Microsoft Visual C++ 2015-2022 Redistributable (x64)”) of key “HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall” of native registry and true

    • Relevance 3

      exists files “winget.exe” of folders whose (name of it starts with “Microsoft.DesktopAppInstaller” and name of it ends with “x64__8wekyb3d8bbwe”) of folder “C:\Program Files\WindowsApps” and true

    • Relevance 4

      not exists files “winget.exe” whose (version of it >= “1.24.25180.0”) of folders whose (name of it starts with “Microsoft.DesktopAppInstaller” and name of it ends with “x64__8wekyb3d8bbwe”) of folder “C:\Program Files\WindowsApps”
      ndowsApps" and true

    • PowerShell (use instead of Action Script)
      # Get winget location that SYSTEM user can access
      $wingetPath = (Resolve-Path 'C:\Program Files\WindowsApps\Microsoft.DesktopAppInstaller_*_x64__8wekyb3d8bbwe\winget.exe')[-1].Path
      
      # Attempt to install winget using winget
      $process = Start-Process $wingetPath -ArgumentList 'install --id Microsoft.AppInstaller --accept-source-agreements --accept-package-agreements' -Wait -PassThru
      
      # If install failed, attempt install with Repair-WinGetPackageManager
      if ($process.ExitCode -ne 0) {
      	$progressPreference = 'SilentlyContinue'
      	Install-PackageProvider -Name NuGet -Force
      	Install-Module -Name Microsoft.WinGet.Client -Force -Repository PSGallery
      	Repair-WinGetPackageManager
      }
      
  3. Install program with winget using BigFix.
    • Here is an example using 7-Zip.
    • Relevance 1

      (name of it starts with “Win” and version of it >= “10.0.16299.0”) of operating system and true

    • Relevance 2

      exists key whose (value “DisplayName” of it as string starts with “Microsoft Visual C++ 2015-2022 Redistributable (x64)”) of key “HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall” of native registry and true

    • Relevance 3

      exists files “winget.exe” whose (version of it >= “1.24.25180.0”) of folders whose (name of it starts with “Microsoft.DesktopAppInstaller” and name of it ends with “x64__8wekyb3d8bbwe”) of folder “C:\Program Files\WindowsApps” and true

    • Relevance 4 (you can remove this one if you want to install 7-Zip instead of upgrading)

      exists keys whose (value “DisplayName” of it as string starts with “7-Zip”) of keys “HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall” of (x32 registries; x64 registries) and true

    • PowerShell (if installing instead of upgrading, replace upgrade with install in the Start-Process argument list)
      # Get winget location that SYSTEM user can access
      $wingetPath = (Resolve-Path 'C:\Program Files\WindowsApps\Microsoft.DesktopAppInstaller_*_x64__8wekyb3d8bbwe\winget.exe')[-1].Path
      
      # Upgrade app with winget
      $process = Start-Process $wingetPath -ArgumentList 'upgrade --id 7zip.7zip --silent --force --accept-source-agreements --accept-package-agreements --source winget --scope machine' -Wait -PassThru
      
      # If upgrade failed, throw error
      if ($process.ExitCode -notin 0, -1978335189) {
      	throw $process.ExitCode
      }
      

Hope this helps!

4 Likes

@skyler

Many thanks for the insight and detailed post. I turly appreciate the help here. The real savior here for me is that last powershell script. I am in the process of confirming that this will work with SSA, but my manual testing seems promising. I will update here once we have confirmation.

Regards,
_MattG

1 Like

Confirmed working in BigFix Self-Service (SSA). Thanks again @skyler for the solution!

2 Likes