Zum Inhalt
Home » How to: winget & Intune

How to: winget & Intune

Mit dem Windows Package Manager (winget) lassen sich sehr einfach Applikationen auf einem Windows Gerät Installieren. Winget bietet ein grosses Repository an, von welchem man sich wie beispielsweise auch bei Chocolatey bedienen kann. Der grosse Vorteil an winget ist, dass dieser Client in den neuen Windows Versionen bereits im System integriert ist und zukünftig mehr in den Endpoint Manager (Intune) integriert wird.
Wie du winget Applikationen als win32 App (als System) mit Intune verteilen kannst, zeige ich dir in diesem Beitrag auf.

Falls du die Apps komplett automatisiert erstellen und in deine Umgebung hochladen möchtest, kannst du das mit meinem Tool dem "Intune Win32 Deployer".

Table of Contents

Was ist winget beziehungsweise der Windows Package Manager?

Der Windows Package Manager ist wie Chocolatey ein Package-Repository beziehungsweise Manager, der frei genutzt werden kann. Mit diesem kannst du sehr einfach via Command-Line Programme installieren und Updaten.

Bisher habe ich dazu immer Chocolatey verwendet, dies vor allem, weil winget nur im Userkontext genutzt werden konnte. Dies hat aber geändert und mich veranlasst, meine Installationen nach und nach anzupassen.

Der Windows Package Manager wird auch in Zukunft eine immer wichtigere Rolle spielen, so soll er den heutigen Windows Store for Business anfangs 2023 ablösen.
Einen super Beitrag zur Ablösung des Windows Store for Business findest du auf der Seite von Rudy Ooms: Microsoft Store for Business Deprecated! What to do now? (call4cloud.nl)

Windows Package Manager (App Installer) mit Intune verteilen

Der App Installer ist eigentlich in den aktuellen Versionen von Windows enthalten, jedoch ist das Kommando winget beziehungsweise die winget.exe noch nicht verfügbar. Das kann gerade bei Rollouts mit Autopilot zu Problemen führen.
Darum verteile ich jeweils den App Installer als separates Win32-Paket, welches ich dann auch als Abhängigkeit bei den einzelnen Applikationen hinterlegen kann.

Zur Installation lade ich die aktuelle Version des App Installers von "https://aka.ms/getwinget" herunter, lege diese in einem temporären Verzeichnis ab und installiere ihn aus diesem. Zum Schluss lösche ich das Verzeichnis wieder.

Das Ganze verpacke ich zusammen mit einer Deinstallationsroutine und einem Validationfile (check.ps1) in ein intunewin / win32 App und lade es zu Intune hoch.

Zum Hochladen navigierst du im Endpoint Manager zu "Apps > Windows" +Add (Windows App (win32)).
Hier lädst du die Datei "install.intunewin" aus meiner Vorlage hoch.

win32 app erstellen

Zudem vergibst du der App einen Namen, eine Beschreibung und füllst den Herausgeber ab:

Auf der nächsten Seite fügst du folgende zwei Befehle ein:

install command%SystemRoot%\sysnative\WindowsPowerShell\v1.0\powershell.exe -windowstyle hidden -executionpolicy bypass -command .\install.ps1
uninstall command%SystemRoot%\sysnative\WindowsPowerShell\v1.0\powershell.exe -windowstyle hidden -executionpolicy bypass -command .\uninstall.ps1
install command, win32 app, Intune

In der Erkennungsregel lädst du das Script "check.ps1" hoch.

detection rule, script, Intune

Abhängigkeiten und eine Supersedence Regel musst du nicht definieren.
Zum Schluss muss die App nur noch zuweisen werden.

winget Pakete mit Intune verteilen (win32)

Zum Verteilen einer Applikation aus dem winget Repository habe ich eine Vorlage zusammengestellt, welche du verwenden kannst. In dieser Vorlage muss vor der Paketierung und dem Hochladen lediglich die korrekte ID eingetragen werden.

winget ID finden

Die ID findest du entweder via CMD oder PowerShell und dem Kommando "winget search" oder noch einfacher Online unter winget.run.

winget search

Den Docs Artikel mit weiteren Details zur Suche via "command line" findest du hier: search Command | Microsoft Docs

winget Vorlage anpassen und intunewin erstellen

Hast du die ID gefunden, musst du diesen nur noch in meiner Vorlage einfügen.
Dies musst du in allen drei Dateien machen:

  • install.ps1
  • uninstall.ps1
  • check.ps1

In allen Dateien findest du oben einmal den Vermerk "WINGETPROGRAMID", den du durch die gewünschte ID ersetzt.

Hast du die drei Dateien angepasst, verwandelst du sie in ein intunewin.
Wie das geht, habe ich dir hier beschrieben: Win32 App / .intunewin erstellen

Erkennungsregel

Bei der Erkennungsregel hast du zwei Möglichkeiten, entweder du verwendest ein Script (flexibler) oder eine statische Erkennungsregel aufgrund eines Ordners.

Entschiedest du dich für den Weg via Script, bis du hier bereits fertig. Denn diese hast du im Punkt oberhalb mit der Anpassung der Datei "check.ps1" bereits vorbereitet.

Möchtest du lieber eine Regel via Ordner-Erkennung (Manually configured detection rule) verwenden, musst du pro Paket den entsprechenden Ordner mit der korrekten Version heraussuchen. Dies geht am einfachsten, wenn du das Programm bei dir oder einem Testgerät installiertest und den Ordner unter folgendem Pfad suchst:

C:\Program Files\WindowsApps

Falls du keinen Zugriff auf den Ordner findest du hier eine Anleitung, wie du dir diesen als Admin erteilen kannst: How to Access WindowsApps folder in Windows 10/8 - wintips.org - Windows Tips & How-tos

Hast du den entsprechenden Ordner gefunden, kopiere dir den Pfad heraus. Diesen benötigst du erst im nächsten Schritt wieder.

Path of winget app

Win32 App in Intune erstellen

Wenn du die Vorlage angepasst, das intunewin erstellt und dich für eine Erkennungsregel entschieden hast, kannst du das App im Endpoint Manager unter "Apps > Windows apps" erstellen.

win32 app erstellen

Auf der ersten Seite hinterlegst du den App-Namen, die Beschreibung sowie einen Herausgeber.
Auf der zweiten Seite fügst du folgende zwei Befehle ein:

install command%SystemRoot%\sysnative\WindowsPowerShell\v1.0\powershell.exe -windowstyle hidden -executionpolicy bypass -command .\install.ps1
uninstall command%SystemRoot%\sysnative\WindowsPowerShell\v1.0\powershell.exe -windowstyle hidden -executionpolicy bypass -command .\uninstall.ps1

Zudem stelle ich das "Device restart behavior" auf "No specific action", dass mir die Installation möglichst keinen Neustart erzwingt.

Intune, App information
win32 app, install command

In den Requirements musst du nichts Spezielles definieren. (z.B. x64 und 2004)

In der Erkennungsregel lädst du jetzt entweder das Script hoch oder hinterlegst den kopierten Pfad.

script detection
Erkennungsregel mit Script
File Detection
Erkennungsregel mit Pfad

In den Abhängigkeiten wählst du den "Windows Package Manager" aus:

Abhängigkeit, Windows Package Manager

Supersedence Regel musst du keine definieren und zum Schluss die App nur noch zuweisen.
FERTIG!

Erklärung der Vorlage (install.ps1)

In den ersten 6 Zeilen wird der optionale Parameter "$param" deklariert. Dieser wird nur benötigt, falls du der Installation etwas zusätzlich mitgeben muss (z.B. ein Lizenzkey).
Diese Parameter kannst du dann einfach hinten an den Installationsbefehl im Win32 App in Intune anhängen.

In der Zeile 8 wird die winget ID deklariert, das ist die ID gemäss Repository.

$ProgramName = "WINGETPROGRAMID"
Codesprache: Power Shell (powershell)

Anschliessend wird in der Zeile 9 und 10 der Pfad für ein lokales Log angegeben und das Transkript / Log gestartet:

$Path_local = "$Env:Programfiles\_MEM" Start-Transcript -Path "$Path_local\Log\$ProgramName-install.log" -Force
Codesprache: Power Shell (powershell)

Da der Befehl winget im Systemkontext nicht direkt bekannt ist, müssen wir zunächst in das richtige Verzeichnis navigieren und den vollständigen Pfad zur "winget.exe" auflösen.
Das mache ich in der Zeile 13 bis 16.
Die EXE wird anschliessend über die Variabel $wingetexe aufgerufen.

$winget_exe = Resolve-Path "C:\Program Files\WindowsApps\Microsoft.DesktopAppInstaller_*_x64__8wekyb3d8bbwe\winget.exe" if ($winget_exe.count -gt 1){ $winget_exe = $winget_exe[-1].Path }
Codesprache: Power Shell (powershell)

Anschliessend (Zeile 19) kommt der Hauptprozess, in dem das Programm via winget mit dem normalen Installationsbefehl und den Parametern für die "silent" Installation installiert wird.

& $winget_exe install --exact --id $ProgramName --silent --accept-package-agreements --accept-source-agreements --scope=machine $param
Codesprache: Power Shell (powershell)

Zum Schluss wird das Transkript wieder beendet und der Prozess abgeschlossen.

Stop-Transcript
Codesprache: Power Shell (powershell)

Update von winget Apps

Der schnellste Weg winget Applikationen zu updaten ist mit folgenden zwei Befehlen:
(Der erste für eine spezifische Applikation, der zweite für alle.)

# Upgrade specific app (change Logitech.Options with the desired winget id) winget upgrade Logitech.Options # Upgrade all apps winget upgrade --query --silent --force --accept-package-agreements --accept-source-agreements --all
Codesprache: Power Shell (powershell)

Den "Upgrade all" Befehl kannst du auch an deine Geräte als Scheduled Task verteilen, um immer alle Apps up-to-date zu halten. Dazu habe ich dir hier eine Vorlage (intunewin) vorbereitet:

Um dieses Paket zu verteilen, kannst du die gleichen Parameter verwenden, wie oben beschrieben für den "Windows Package Manager".

Ein Nachteil dieser Variante kann sein, dass sämtliche Apps, die auf winget publiziert sind, in den Updater Prozess miteinbezogen werden. Das ist nicht immer gewünscht.
Eine Lösung dafür bietet das Tool: Winget-AutoUpdate: WAU daily updates apps as system and notify connected users. (Allowlist and Blocklist support) (github.com)

34 Gedanken zu „How to: winget & Intune“

  1. Hallo Florian - toll, deine winget-Lektüre !! Wie immer eine Inspiration !!
    Ich würde gerne vor der Installation durch den winget-Befehl eine Überprüfung machen (mit dem Parameter 'upgrade'), ob eine Version des zu installierenden Pakets eventuell schon vorhanden ist (winget.exe upgrade -like "*$ProgramName*"). Wenn ja, dann soll winget nicht mit dem 'install' Parameter, sondern mit dem 'upgrade' Parameter weitermachen.
    Aber ich vertue mich mit meiner weiteren "if-then" Anweisung anstelle deines ".\winget.exe ..." Befehls. Kann ich denn den Aufruf von winget auch als Variable definieren ??

    Vielen Dank für deine Beiträge und vorab für deine Hilfe
    Frank

    1. Hallo Frank, vielen Dank für dein super Feedback!

      Die Idee mit dem Upgrade ist super, das hatte ich mit den Chocolatey Paketen auch so gemacht.
      Weil winget aber sämtliche auf dem Gerät installierte Programme mit dem öffentlichen Repository abgleicht, werden Apps automatisch "eingebunden". Das führt dazu, dass bei Installationen die Erkennungsregel bereits auf "installiert" switcht und das "install.ps1" nicht ausgeführt wird.

      Ich löse diese in kleinen Umgebungen mit dem Scheduled Task, der alle winget apps updatet und in komplexeren mit dem Tool "Winget-autoupdate".
      Beide Optionen habe ich im Beitrag ergänzt.

      1. Wow - was für eine schnelle Reaktion. Danke !!
        Nachdem ich bislang immer "große" intunewin-Pakete für die Softwareverteilung gebaut habe, möchte ich peu à peu auf eine Vorgehensweise mit winget umsteigen. Allerdings darf nicht generell jedes Programm upgedatet werden, sondern nur gezielte. Der Task über die Aufgabenplanung kann ja dann in den Parametern mit den gewünschten Programmen dediziert angepasst werden.
        Aber bei der Installation würde ich gerne prüfen, ob schon eine "upgradebare" Version installiert ist und wenn ja, dann upgraden und wenn nicht, dann eine "normale" Installation. So kann ich verhindern, dass eine veraltete Version installiert bleibt und durch die Erkennungsregel rutscht.
        Die Idee dabei ist folgende: Über den Parameter "upgrade" erstmal herausfinden, welche durch winget upgradbaren Installationen vorhanden sind:

        $ProgramName = "WINGETPROGRAMID"
        if ('winget.exe upgrade' -like "*$ProgramName*"){
        winget.exe upgrade $ProgramName --silent --accept-package-agreements --accept-source-agreements $param
        }
        else{
        winget.exe install --exact --id $ProgramName --silent --accept-package-agreements --accept-source-agreements $param
        }

        Aber der Aufruf einfach nur von "winget.exe" funktioniert ja nicht im System-Kontext. Oder könnte ich das in einer Variablen platzieren ??

        1. Ah, jetzt vershee ich.
          Ja, das könntest du so machen:

          $Path_WingetAll = Resolve-Path "C:\Program Files\WindowsApps\Microsoft.DesktopAppInstaller_*_x64__8wekyb3d8bbwe"
          if($Path_WingetAll){$Path_Winget = $Path_WingetAll[-1].Path}
          cd $Path_Winget

          if($(.\winget upgrade) -like "*$ProgramName*"){...}

  2. Hi,

    Ich hätte eine kurze Frage zu deinem Script.
    Ich habe dieses angewendet und auch die Überprüfung ist erfolgreich, der App Installer ist auch unter den Programme zu finden.

    Problem was ich habe ist das "Winget" nicht per CMD zur Verfügung steht.
    Wenn der Client dann eine Zeitlang läuft scheint er sich die benötigten Daten per aus dem MS Store zu "ziehen"

    Problem dabei ist das die Software die in der OOB / ESP bzw. direkt nach der User Anmeldung installiert werden soll natürlich nicht installiert werden kann da Winget nicht zur Verfügung steht.

    Wie hast du dieses Problem gelöst oder mache ich etwas falsch?

    Gruß
    Flo 🙂

      1. Hi Flo,

        vielen Dank für deine schnelle Rückmeldung.

        Ich denke ich habe den Fehler gefunden, es werden scheinbar noch Daten aus dem Microsoft Store heruntergeladen, es gibt aber scheinbar derzeit einen Bug / Problem mit dem MS Store (0x80131500)

        Nachdem ich einen Client eingerichtet und Windows Updates gemacht habe funktionierte der MS Store wieder und dann auch Winget.
        Anschließend habe ich einen AutoPiot Reset vom Gerät gemacht, in der OOBE hatte das Gerät dann kein Winget, nach der ESP hatte es dann dank deinem Script umgehend Winget.

        Es besteht also scheinbar eine Abhängigkeit zu irgendwelchen Daten aus dem Store die Nachgeladen werden.

            1. Hi Angelo
              Wenn du Apps erst nach der ESP-Phase installieren möchtest, wähle in den ESP-Einstellungen nur die Apps an, die Initial installier werden sollen. Alle anderen werden dann erst nach dem ersten Login angestossen.

    1. Hi there. Thanks for the efforts here - really appreciate the springboard it has given me to start using winget for package installation. However, I seem to have hit a snag - can it be used to install Microsoft Store applications in the device/system context? I want to be able to deploy Power Apps to a device that will be used with a kiosk profile

    2. Thanks for this awesome how to about Winget. Im stubling on a problem right now, on 2 devices i can install perfectly apps through Intune and on another device nothing is happening and I don't have any clue where to start looking. In CMD or powershell i can use the command Winget put no installs are happening through the company portal.

      I hope you are able to guide me in the right direction.

      1. Are the apps in a "waiting for download" loop?
        Then maybe the device is missing the Intune Agent for MSI installations. This is the case if they are only registered/joined, but not Intune managed.

    3. Hello,

      First of all thank you for the amazing tutorial, unfortunatelly the uninstall, upgrade and check are not working for nonlocal admin users.

      If anyone has a solution for this, I am all ears!

      Kr,
      Gustavo

      1. Hi Gustavo,
        That's correct. The way shown in this tutorial works only for deployments in the system context.
        If you want to install apps in the user context (non admin) you don't habe to resolve the path to the exe, you can use just the term "winget" in your script.

        1. Florian,

          I want to deploy in the system context, but the update, check and uninstall are not working for users that are not local admin of their machines.

    4. Hallo Florian,

      vielleicht hast du noch einen Tipp für mich.

      Ich wende dein Script zur Installation von Winget und auch das von "call4cloud.nl" an.
      Egal welches der Scripte ich nutze, Winget / Winget.exe steht nach der Ausführung des Scriptes nicht unmittelbar bereit, erst wenn der Client in der Lage gewesen ist eine Verbindung zum MS Store aufzubauen und "die aktuellste" Version herunterzuladen stehen die Befehle zur Verfügung.

      Bin ich der einzige mit diesem Problem?
      Durch den oben beschriebenen Umstand ist es nicht möglich in der OOBE / ESP erfolgreich Programme mit Winget zu installieren was leider mehr als schade ist 🙂

      Gruß
      Florian

      1. Hi Florian, ja leider leider ist es so, dass es winget noch/wieder etwas zu lange braucht, bis es bereit ist.
        Ich bin dabei einige tests zu machen und hoffe eine Lösung zu finden. In der Zwischenzeit habe ich es auch so gehandhabt, dass die winget Apps nicht während der ESP-Phase installiert werden.
        Gruss Florian 😉

      1. For me, the main advantage is that it is and will be more integrated in Windows, so you didn't have another third-party involved.
        For now, not alle features are as evolved as in chocolatey, but I'm sure that therere soon on a similar level.

        1. Thank you, I agree with that, for now I will keep deploying with Chocolatey, but will keep an eye on winget with views to migrate later.

    5. Hallo! Wow tolle Anleitung.
      Bei Windows 11 ist der "App Installer" schon vorinstalliert. Wie kann man mit der vorinstallierten Version damit arbeiten? (bzw. bei Windows 10 mit der MS Store Version)
      LG Thomas

      1. Hallo Thomas, da ist das Verhalten dasselbe. Oft dauert es aber etwas, bis der App Installer ready ist, weshalb die Installatonen bei neunen Geräten in den ersten 30min fehlschlagen können.

    6. Thank you for this guide. I have tried to implement, and everything seems to work... except that the applications do not appear after they install. I tested with GIMP.
      At first I thought there was something wrong because both of my test computers were stuck on "Download pending" for hours. Then out of the blue they both installed the app.
      ...Except that they didn't. Company Portal reports that the app is installed. Intune reports that the app is installed (it even shows up on the "Discovered Apps" list). But the app is not on the computer. Even after an Administrator search of C:\, there's nothing.

      The installation log does not report anything amiss. I copy-pasted below:

      **********************
      Windows PowerShell transcript start
      Start time: 20221110151006
      Username: MYDOMAIN\SYSTEM
      RunAs User: MYDOMAIN\SYSTEM
      Configuration Name:
      Machine: MYCOMPUTER (Microsoft Windows NT 10.0.19044.0)
      Host Application: C:\windows\sysnative\WindowsPowerShell\v1.0\powershell.exe -windowstyle hidden -executionpolicy bypass -command .\install.ps1
      Process ID: 9244
      PSVersion: 5.1.19041.1682
      PSEdition: Desktop
      PSCompatibleVersions: 1.0, 2.0, 3.0, 4.0, 5.0, 5.1.19041.1682
      BuildVersion: 10.0.19041.1682
      CLRVersion: 4.0.30319.42000
      WSManStackVersion: 3.0
      PSRemotingProtocolVersion: 2.3
      SerializationVersion: 1.1.0.1
      **********************
      Transcript started, output file is C:\Program Files\_MEM\Log\GIMP.GIMP-install.log
      Failed in attempting to update the source: winget
      The `msstore` source requires that you view the following agreements before using.
      Terms of Transaction: https://aka.ms/microsoft-store-terms-of-transaction
      The source requires the current machine's 2-letter geographic region to be sent to the backend service to function prope
      rly (ex. "US").

      Found GIMP [GIMP.GIMP] Version 2.10.32
      This application is licensed to you by its owner.
      Microsoft is not responsible for, nor does it grant any licenses to, third-party packages.
      Downloading https://download.gimp.org/pub/gimp/v2.10/windows/gimp-2.10.32-setup-1.exe
      ██████████████████████████████ 252 MB / 252 MB
      Successfully verified installer hash
      Starting package install...
      Successfully installed
      **********************
      Windows PowerShell transcript end
      End time: 20221110151335
      **********************

      1. Gould you check two things for me?
        1. I've got a new commit for the install template, maybe this helps.
        2. Could you test another application? (I've had similar problem with GIMP a couple of weeks ago. )

        1. Thank you! FWIW, GIMP worked if I adjusted your templates to use local user Winget, and set Intune to install under User context (which is fine with me).

          I tried Kdenlive with your updated commit.

          This time it had a more conventional error.

          **********************
          Windows PowerShell transcript start
          Start time: 20221117161757
          Username: CASEIL\SYSTEM
          RunAs User: CASEIL\SYSTEM
          Configuration Name:
          Machine: CASE-001577 (Microsoft Windows NT 10.0.19044.0)
          Host Application: C:\windows\sysnative\WindowsPowerShell\v1.0\powershell.exe -windowstyle hidden -executionpolicy bypass -command .\install.ps1
          Process ID: 6384
          PSVersion: 5.1.19041.1682
          PSEdition: Desktop
          PSCompatibleVersions: 1.0, 2.0, 3.0, 4.0, 5.0, 5.1.19041.1682
          BuildVersion: 10.0.19041.1682
          CLRVersion: 4.0.30319.42000
          WSManStackVersion: 3.0
          PSRemotingProtocolVersion: 2.3
          SerializationVersion: 1.1.0.1
          **********************
          Transcript started, output file is C:\Program Files\_MEM\Log\KDE.Kdenlive-install.log
          No applicable installer found; see logs for more details.
          **********************
          Windows PowerShell transcript end
          End time: 20221117161758
          **********************

          Going to try with some others as well.

    7. Looks like that the ZIP file for the "Windows Package Manager" template, doesn't have the latest check.ps1 file. I replaced the file in the zip with the file in the repository and now it's working.

    8. Hallo,

      eins vorweg: Super Seite und super Beitrag. Respekt dafür!

      Generell verstehe ich den Artikel, es funktioniert soweit auch sofern winget auf er Maschine installiert ist. Jedoch scheitere ich bereits beim Verteilen des winget als Win32 App. Ich habe dabei deine Vorlage verwendet und deployed. Beim Client wird dies registriert und versucht auszuführe, jedoch schlägt die installation vom Windows Package Manager fehl. Leider sind die Fehler nicht gerade aussagekräftig. Ich habe versucht das install.ps1 direkt "auseinander" zu nehmen und am Client direkt auszuführen, leider keine Chance. Was mache ich falsch?
      Es scheint als wenn der Download nicht ausgeführt wird und daher die App nicht installiert werden kann. Der Download selbst funktioniert manuell ohne Probleme.

      Verzeichnis: C:\Program Files\_MEM\Data

      Mode LastWriteTime Length Name
      ---- ------------- ------ ----
      d----- 24.11.2022 14:46 WindowsPackageManager
      PS>TerminatingError(Add-AppxProvisionedPackage): "Element nicht gefunden.
      "
      C:\WINDOWS\IMECache\e8729d48-dba8-493f-9363-3c5f47e2629f_1\install.ps1 : Failed to install WindowsPackageManager!
      In Zeile:1 Zeichen:1

      Eine Idee? Danke für den Input! Grüsse Jan

      1. Hallo Jan, vielen Dank 🙂

        Leider habe ich aktuell dasselbe Problem. Wies aussieht ändert gerade nochmals etwas im Hintergrund.
        Gestern wurde gerade eine neue Ankündigung zur weiteren Integration von Intune/Winget/Store veröffentlicht. Vielleicht ist dann der Package manager bald komplett integriert: https://youtu.be/QtftJQn9WYQ

    Schreiben Sie einen Kommentar

    Ihre E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.