PowerShell function to find information about module updates
I decided to update the one liner from my blog article last week and take it a step further by turning it into a reusable tool that displays information about module updates that are available regardless of where they were installed from.
1#Requires -Version 3.0 -Modules PowerShellGet
2function Find-MrModuleUpdate {
3
4<#
5.SYNOPSIS
6 Finds updates for installed modules from an online gallery that matches the specified criteria.
7
8.DESCRIPTION
9 Find-MrModuleUpdate is a PowerShell advanced function that finds updates from an online gallery for locally installed modules
10 regardless of whether or not they were originally installed from an online gallery or from the same online gallery where the
11 update is found.
12
13.PARAMETER Name
14 Specifies the names of one or more modules to search for.
15
16.PARAMETER Scope
17 Specifies the search scope of the installed modules. The acceptable values for this parameter are: AllUsers and CurrentUser.
18
19.EXAMPLE
20 Find-MrModuleUpdate
21
22.EXAMPLE
23 Find-MrModuleUpdate -Name PSScriptAnalyzer, PSVersion
24
25.EXAMPLE
26 Find-MrModuleUpdate -Scope CurrentUser
27
28.EXAMPLE
29 Find-MrModuleUpdate -Name PSScriptAnalyzer, PSVersion -Scope CurrentUser
30
31.INPUTS
32 None
33
34.OUTPUTS
35 Mr.ModuleUpdate
36
37.NOTES
38 Author: Mike F Robbins
39 Website: http://mikefrobbins.com
40 Twitter: @mikefrobbins
41#>
42
43 [CmdletBinding()]
44 [OutputType('Mr.ModuleUpdate')]
45 param (
46 [ValidateNotNullOrEmpty()]
47 [string[]]$Name,
48
49 [ValidateSet('AllUsers', 'CurrentUser')]
50 [string]$Scope
51 )
52
53 $AllUsersPath = "$env:ProgramFiles\WindowsPowerShell\Modules\*"
54 $CurrentUserPath = "$env:USERPROFILE\Documents\WindowsPowerShell\Modules\*"
55
56 switch ($Scope) {
57 'AllUsers' {$Path = $AllUsersPath; break}
58 'CurrentUser' {$Path = $CurrentUserPath; break}
59 Default {$Path = $AllUsersPath, $CurrentUserPath}
60 }
61
62 $Params = @{
63 ListAvailable = $true
64 }
65
66 if ($PSBoundParameters.Name) {
67 $Params.Name = $Name
68 }
69
70 $Modules = Get-Module @Params
71
72 foreach ($p in $Path) {
73
74 $ScopedModules = $Modules |
75 Where-Object ModuleBase -like $p |
76 Sort-Object -Property Name, Version -Descending |
77 Get-Unique
78
79 foreach ($Module in $ScopedModules) {
80
81 Remove-Variable -Name InstallInfo -ErrorAction SilentlyContinue
82 $Repo = Find-Module -Name $Module.Name -ErrorAction SilentlyContinue
83
84 if ($Repo) {
85 $Diff = Compare-Object -ReferenceObject $Module -DifferenceObject $Repo -Property Name, Version |
86 Where-Object SideIndicator -eq '=>'
87
88 if ($Diff) {
89 $PSGetModuleInfoPath = "$($Module.ModuleBase)\PSGetModuleInfo.xml"
90
91 if (Test-Path -Path $PSGetModuleInfoPath) {
92 $InstallInfo = Import-Clixml -Path $PSGetModuleInfoPath
93 }
94
95 switch ($Module.ModuleBase) {
96 {$_ -like $AllUsersPath} {$Location = 'AllUsers'; break}
97 {$_ -like $CurrentUserPath} {$Location = 'CurrentUser'; break}
98 Default {Throw 'An unexpected error has occured.'}
99 }
100
101 [pscustomobject]@{
102 Name = $Module.Name
103 InstalledVersion = $Module.Version
104 InstalledLocation = $Location
105 Repository = $Repo.Repository
106 RepositoryVersion = $Diff.Version
107 InstalledFromRepository = $InstallInfo.Repository
108 PSTypeName = 'Mr.ModuleUpdate'
109 }
110
111 }
112
113 }
114
115 }
116
117 }
118
119}
1Find-MrModuleUpdate
As shown in the previous results, the function lists modules that have updates available regardless of where they were originally installed from. It also lists the installed version and location along with the repository where the updated version resides and the updated version number. It also lists where the module was originally installed from by reading the contents of the hidden XML file in the module directory if it was installed using PowerShellGet.
You can narrow your search down to specific modules:
1Find-MrModuleUpdate -Name PSScriptAnalyzer, PSVersion
To a specific scope:
1Find-MrModuleUpdate -Scope CurrentUser
Use a combination of specific modules and scope to narrow the search down even further:
1Find-MrModuleUpdate -Name PSScriptAnalyzer, PSVersion -Scope AllUsers
The function also uses custom formatting to allow for table output with more than four columns by
default without having to pipe to Format-Table
. The relevant portion of the PS1XML file used for
the custom formatting is shown in the code example below:
1<View>
2 <Name>Mr.ModuleUpdate</Name>
3 <ViewSelectedBy>
4 <TypeName>Mr.ModuleUpdate</TypeName>
5 </ViewSelectedBy>
6 <TableControl>
7 <TableHeaders>
8 <TableColumnHeader>
9 <Width>30</Width>
10 </TableColumnHeader>
11 <TableColumnHeader>
12 <Width>16</Width>
13 </TableColumnHeader>
14 <TableColumnHeader>
15 <Width>17</Width>
16 </TableColumnHeader>
17 <TableColumnHeader>
18 <Width>10</Width>
19 </TableColumnHeader>
20 <TableColumnHeader>
21 <Width>17</Width>
22 </TableColumnHeader>
23 <TableColumnHeader>
24 <Width>23</Width>
25 </TableColumnHeader>
26 </TableHeaders>
27 <TableRowEntries>
28 <TableRowEntry>
29 <TableColumnItems>
30 <TableColumnItem>
31 <PropertyName>Name</PropertyName>
32 </TableColumnItem>
33 <TableColumnItem>
34 <PropertyName>InstalledVersion</PropertyName>
35 </TableColumnItem>
36 <TableColumnItem>
37 <PropertyName>InstalledLocation</PropertyName>
38 </TableColumnItem>
39 <TableColumnItem>
40 <PropertyName>Repository</PropertyName>
41 </TableColumnItem>
42 <TableColumnItem>
43 <PropertyName>RepositoryVersion</PropertyName>
44 </TableColumnItem>
45 <TableColumnItem>
46 <PropertyName>InstalledFromRepository</PropertyName>
47 </TableColumnItem>
48 </TableColumnItems>
49 </TableRowEntry>
50 </TableRowEntries>
51 </TableControl>
52</View>
The Find-MrModuleUpdate
function shown in this blog article is part of my MrToolkit module which
can be downloaded from
my PowerShell repository on GitHub.
µ