Last active
January 26, 2025 12:21
-
-
Save nohwnd/5c07fe62c861ee563f69c9ee1f7c9688 to your computer and use it in GitHub Desktop.
Remove built-in version of Pester 3 (or -All) from Windows 10 Program Files and Program Files (x86).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#Requires -RunAsAdministrator | |
function Uninstall-Pester ([switch]$All) { | |
if ([IntPtr]::Size * 8 -ne 64) { throw "Run this script from 64bit PowerShell." } | |
#Requires -RunAsAdministrator | |
$pesterPaths = foreach ($programFiles in ($env:ProgramFiles, ${env:ProgramFiles(x86)})) { | |
$path = "$programFiles\WindowsPowerShell\Modules\Pester" | |
if ($null -ne $programFiles -and (Test-Path $path)) { | |
if ($All) { | |
Get-Item $path | |
} | |
else { | |
Get-ChildItem "$path\3.*" | |
} | |
} | |
} | |
if (-not $pesterPaths) { | |
"There are no Pester$(if (-not $all) {" 3"}) installations in Program Files and Program Files (x86) doing nothing." | |
return | |
} | |
foreach ($pesterPath in $pesterPaths) { | |
takeown /F $pesterPath /A /R | |
icacls $pesterPath /reset | |
# grant permissions to Administrators group, but use SID to do | |
# it because it is localized on non-us installations of Windows | |
icacls $pesterPath /grant "*S-1-5-32-544:F" /inheritance:d /T | |
Remove-Item -Path $pesterPath -Recurse -Force -Confirm:$false | |
} | |
} | |
Uninstall-Pester |
@jasonrush good point. I spent some time and refactored into a true cmdlet using advanced function syntax. The module name is Utils and must be installed in a location located within $env:PSModulePath. The file structure is:
Utils
Utils.psd1
Utils.psm1
/Public
- Uninstall-Pester.ps1
/Private
The Utils.psd1
@{ ModuleVersion = "1.0.0" GUID = "e38b14a6-0d85-4be5-869e-38ed7e270126" Author = "Your Name Here" CompanyName = "My Company" Copyright = "(c) 2021 My Company All rights reserved." RootModule = "Utils.psm1" }
Utils.ps1 file
Get-ChildItem -Filter *.ps1 -Path "$PSScriptRoot\public","$PSScriptRoot\private" -Recurse | ForEach-Object { . $_.FullName; Write-Verbose "Loaded $_.BaseName" } Get-ChildItem -Filter *.ps1 -Path "$PSScriptRoot\public" -Recurse | ForEach-Object { Export-ModuleMember $_.BaseName; Write-Verbose "Exported $_.BaseName" }
Uninstall-Pester.ps1 file
function Uninstall-Pester { [CmdletBinding()] [OutputType([ bool ])] param( [Parameter()] [switch] $All = $false ) begin { try { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )]-Begin Enter" $result = $true $pesterPath = 'WindowsPowerShell\Modules\Pester' if ( -not $All ) { $pesterPath += '\3.*' } # See if there is anything to do $paths = @() foreach ( $path in @(${env:ProgramFiles}, ${env:ProgramFiles(x86)} ) ) { if ( $path -and ( Test-Path -Path "$path\$pesterPath" ) ) { $paths += ( Get-ChildItem -Path "$path\$pesterPath" -Directory -ErrorAction SilentlyContinue ).FullName } } if ( -not $paths.Count ) { Write-Warning "There are no Pester$( if ( -not $All ) { " 3" } ) installations in Program Files and Program Files (x86)" $result = $false return } $isAdmin = (New-Object Security.Principal.WindowsPrincipal([Security.Principal.WindowsIdentity]::GetCurrent())).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator) $is32BitProcess = $pshome -like "*syswow64*" $is64BitOS = ( Get-WmiObject Win32_OperatingSystem ).OSArchitecture -like "64*" $filePath = $null switch ( $true ) { { ( $is32BitProcess -and -not $is64BitOS ) -or ( -not $isAdmin -and $is64BitOS ) } { Write-Warning "Restarting script under 64 bit powershell as admin" # relaunch this script under 64 bit shell as adminstrator $filePath = "$( $pshome -replace "syswow64", "System32" )\powershell.exe" break } { -not $isAdmin } { Write-Warning "Restarting script using admin privs" $filePath = 'powershell.exe' } } if ( $filePath ) { Start-Process -FilePath $filePath -Verb RunAs -ArgumentList "-NoLogo -NoExit -Command `" Import-Module -name Utils; Uninstall-Pester $( if( $All ) { "-All" } ) `"" $result = $false return } } catch { $result = $false Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )] Exception:`r`n$_" throw $_ } finally { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )]-Begin Exit" } } process { try { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )]-Process Enter" if ( -not $result ) { return } foreach ($path in $paths) { takeown /F $path /A /R icacls $path /reset # grant permissions to Administrators group, but use SID to do # it because it is localized on non-us installations of Windows icacls $path /grant "*S-1-5-32-544:F" /inheritance:d /T Remove-Item -Path $path -Recurse -Force -Confirm:$false -ErrorAction SilentlyContinue } } catch { $result = $false Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )] Exception:`r`n$_" throw $_ } finally { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )]-Process Exit" } } end { try { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )]-End Enter" return $result } catch { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )] Exception:`r`n$_" throw $_ } finally { Write-Verbose -Message "[$(( Get-Date ).TimeOfDay )][$( $MyInvocation.MyCommand )]-End Exit" } } }
Thanks your script worked out for to uninstall the module. And installing manually the newer version.
Thanks, helped me with this problem.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
@jcoryatjr my version is geared more towards non-interactive use. So I like that it fails when you are not admin. But thanks for sharing, hopefully someone will find it useful.