Export the list of installed programs to CSV with PowerShell
Reads the Windows uninstall registry keys and writes name, version, publisher and install date of every installed program to a CSV file. Useful for audits, migrations and support tickets.
Drafted with AI from official documentation. Scripts were run in a test environment and repository links verified. Awaiting a human check. Did it work for you? Last edited Outdated?
What this changes
Creates one CSV file (by default installed-programs.csv on your Desktop). The registry is only read; no program is installed, changed or removed.
How to undo it
Delete the CSV file. Nothing else was written.
Windows keeps the entries behind Settings, Apps, Installed apps in three places in the registry: machine-wide 64-bit programs, machine-wide 32-bit programs and programs installed just for the current user. This script reads all three, drops the hidden system components and writes a clean CSV you can open in Excel, attach to a ticket or compare between two machines.
The script
[CmdletBinding()]
param(
[string]$OutFile = (Join-Path ([Environment]::GetFolderPath('Desktop')) 'installed-programs.csv')
)
$keys = @(
'HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\*',
'HKLM:\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall\*',
'HKCU:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\*'
)
$programs = Get-ItemProperty -Path $keys -ErrorAction SilentlyContinue |
Where-Object { $_.DisplayName -and -not $_.SystemComponent } |
Select-Object `
@{ Name = 'Name'; Expression = { $_.DisplayName.Trim() } },
@{ Name = 'Version'; Expression = { $_.DisplayVersion } },
@{ Name = 'Publisher'; Expression = { $_.Publisher } },
@{ Name = 'InstallDate'; Expression = { $_.InstallDate } },
@{ Name = 'Scope'; Expression = { if ($_.PSPath -like '*HKEY_CURRENT_USER*') { 'User' } else { 'Machine' } } },
@{ Name = 'Architecture'; Expression = { if ($_.PSPath -like '*WOW6432Node*') { 'x86' } else { 'x64' } } } |
Sort-Object Name, Version -Unique
$programs | Export-Csv -LiteralPath $OutFile -NoTypeInformation -Encoding UTF8
Write-Host "$(@($programs).Count) programs written to $OutFile"
How to run it
.\Export-InstalledPrograms.ps1
.\Export-InstalledPrograms.ps1 -OutFile C:\Temp\laptop-ana.csv
Import-Csv C:\Temp\laptop-ana.csv | Where-Object Publisher -like '*Oracle*'
No administrator rights are needed; the uninstall keys are readable by every user. If PowerShell refuses to run the file, see the entry on execution policy.
How it works
Get-ItemPropertyon a registry path with\*returns one object per subkey, with the key’s values as properties. The three paths cover 64-bit, 32-bit (WOW6432Node) and per-user installs.- Entries without a
DisplayNameor withSystemComponent = 1are hidden in the Settings app too, so the script skips them. - The
ScopeandArchitecturecolumns come from the registry path each entry was read from. Sort-Object -Uniqueon name and version removes the duplicate rows that some installers create.Export-Csv -NoTypeInformationwrites plain CSV; in PowerShell 7 that is already the default but the switch keeps Windows PowerShell 5.1 from adding a#TYPEheader line.-Encoding UTF8keeps accented names intact in Excel.
What it does not list
Microsoft Store and other packaged apps do not use the uninstall keys. Add them with Get-AppxPackage, which lists the current user’s packages, or use winget which sees both worlds:
Get-AppxPackage | Select-Object Name, Version, Publisher | Export-Csv store-apps.csv -NoTypeInformation
winget list
winget export -o apps.json
Compare two machines
$old = Import-Csv .\old-pc.csv
$new = Import-Csv .\new-pc.csv
Compare-Object $old $new -Property Name | Where-Object SideIndicator -eq '<=' | Select-Object Name
Rows marked <= exist only in the first file: the programs still missing on the new machine.
Did this work for you?
No votes yet. Be the first.
If it did not work, the report form below tells the editors what went wrong.
See also
- 0396 PowerShell basics: cmdlets, objects and the pipeline PowerShell commands are called cmdlets, they return objects instead of text, and the pipeline passes those objects between them. Once that clicks,… Beginner · Explains an idea · Linux, macOS, Windows Article PowerShell 15 Oct 2026
- 0397 PowerShell cheat sheet The PowerShell cmdlets and patterns you use every day: files, text, processes, services, filtering, exporting, remoting and the operators that trip up… Beginner · Cheat sheet · Linux, macOS, Windows Article PowerShell 15 Oct 2026
- 0398 Install WSL2 and Ubuntu on Windows One command installs the Windows Subsystem for Linux and Ubuntu. Then learn how to pick a distribution, check which WSL version you… Beginner · Step by step · Windows Article Windows administration · WSL 15 Oct 2026
- 0399 Fix: running scripts is disabled on this system (execution policy) PowerShell refuses to run .ps1 files until the execution policy allows it. The usual fix is RemoteSigned for your own user; here… Beginner · Fixes an error · Windows Article PowerShell · Windows administration 15 Oct 2026
- 0400 winget: install and update software from the command line winget is the package manager built into Windows. Search for a program, install it by id, update everything with one command and… Beginner · Step by step · Windows Article Installing languages & tools · Windows administration 15 Oct 2026
- 0401 Windows services, Task Scheduler and event logs from PowerShell Manage the three things Windows administrators touch most: query and restart services, create and inspect scheduled tasks, and search the event logs… Intermediate · Step by step · Windows Article PowerShell · Windows administration 15 Oct 2026
Repos in the wild
- PowerShell: the cross-platform shell and scripting language PowerShell/PowerShell The open-source PowerShell 7 project from Microsoft: an object-based shell and automation language that runs on Windows, Linux and macOS and is the successor to Windows PowerShell 5.1. GitHub
- Windows Terminal: tabs, panes and profiles for every shell on Windows microsoft/terminal Microsoft's modern terminal for Windows, with tabs, split panes, GPU rendering, Unicode and emoji support and profiles for PowerShell, cmd, WSL distributions and SSH connections. GitHub
History
Every saved edit is kept. The plot on the sleeve draws one line per edit. Open any edit to see exactly what changed.
- Dominik +3,538 chars