Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

AzureAuth Windows uninstall script #340

Merged
merged 15 commits into from
Oct 12, 2023
Merged
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
125 changes: 125 additions & 0 deletions install/uninstall.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
# Enable a default -Verbose flag for debug output.
[CmdletBinding()]

# Halt script execution at the first failed command.
$script:ErrorActionPreference='Stop'

$azureauthDefaultLocation = ([System.IO.Path]::Combine($Env:LOCALAPPDATA, "Programs", "AzureAuth"))

if (![string]::IsNullOrEmpty($Env:AZUREAUTH_INSTALL_DIRECTORY) `
-And $Env:AZUREAUTH_INSTALL_DIRECTORY -ne $azureauthDefaultLocation) {
Write-Warning "Ignoring AZUREAUTH_INSTALL_DIRECTORY environment variable. Custom uninstallation locations are not supported."
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
}
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved

function Uninstall {
Close-AzureauthInstances

$locations = Get-AzureauthsInPath
Remove-AzureauthDirectories $locations
Remove-FromPath $locations
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved

Write-Output "Uninstalled AzureAuth!"
}

function Get-AzureauthsInPath {
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
$allLocations = [System.Collections.ArrayList]@()
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
$azureauthsInPath = (Get-Command -Name azureauth -ErrorAction SilentlyContinue -CommandType Application -All).Source

# Uninstallation is only supported from the default AzureAuth location.
# We warn the user of any custom locations that are listed in the PATH.
# Installations in custom locations that are not listed in PATH cannot
# be found and uninstalled.
# We still...
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
ForEach($az in $azureauthsInPath) {
$tempDirectory = (Get-Item $az).Directory.FullName
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
if (!$az.Contains($azureauthDefaultLocation)) {
Write-Warning "Additional installation found in ${tempDirectory}"
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
} else {
# We add the PATH location to the list and not the default location to later
# remove it from the PATH (default location is the whole parent folder).
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
$_ = $allLocations.Add($tempDirectory)
}
}

return $allLocations
}

function Remove-AzureauthDirectories {
param([System.Collections.ArrayList]$locationsToDelete)

ForEach ($location in $locationsToDelete) {
Remove-InstallationFolder $location
}

# We also delte AzureAuth parent folder
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
Remove-InstallationFolder $azureauthDefaultLocation
}

function Remove-InstallationFolder {
param ([string]$directory)

if (Test-Path -Path $directory) {
Write-Verbose "Removing installations at '${directory}'"
Remove-Item -Force -Recurse $directory
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
} else {
Write-Verbose "There were no installations found at '${directory}'"
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
}
}

function Remove-FromPath {
param ([System.Collections.ArrayList]$locationsToDelete)

$registryPath = 'Registry::HKEY_CURRENT_USER\Environment'
$currentPath = (Get-ItemProperty -Path $registryPath -Name PATH -ErrorAction SilentlyContinue).Path

# Reconstruct the $PATH without any azureauth directories.
$updatedPath = "";
if (($null) -ne $currentPath) {
$paths = $currentPath.Split(";")
$pathArr = @()
ForEach($path in $paths){
if(!$path.Equals("") -And ($locationsToDelete.Count -eq 0 -Or !$locationsToDelete.Contains($path))) {
$pathArr += "${path}"
}
elseif (!$path.Equals("")) {
Write-Verbose "Removing '${path}' from `$env:PATH"
}
}
$updatedPath = ($pathArr -join ";") + ";"
}

Set-ItemProperty -Path $registryPath -Name PATH -Value $updatedPath
Send-SettingChange
}

function Close-AzureauthInstances {
Emilio0404 marked this conversation as resolved.
Show resolved Hide resolved
# Uninstall will fail if there are instances of AzureAuth running.
# We suppress taskkill output here because this is a best effort attempt and we don't want the user to see its output.
# Here, Get-Process is used to first determine whether there is an existing azureauth process. If there is, kill the existing process first.
$ProcessCheck = Get-Process -Name azureauth -ErrorAction SilentlyContinue -ErrorVariable ProcessError
if ($null -ne $ProcessCheck) {
Write-Verbose "Stopping any currently running azureauth instances"
taskkill /f /im azureauth.exe 2>&1 | Out-Null

# After killing the process it is still possible for there there to be locks on the files it was using (including
# its own DLLs). The OS may take an indeterminate amount of time to clean those up, but so far we've observed 1
# second to be enough.
Start-Sleep -Seconds 1
}
}

# Send WM_SETTINGCHANGE after changing Environment variables.
# Refer to https://gist.github.com/alphp/78fffb6d69e5bb863c76bbfc767effda
function Send-SettingChange {
Add-Type -Namespace Win32 -Name NativeMethods -MemberDefinition @"
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern IntPtr SendMessageTimeout(IntPtr hWnd, uint Msg, UIntPtr wParam, string lParam, uint fuFlags, uint uTimeout, out UIntPtr lpdwResult);
"@
$HWND_BROADCAST = [IntPtr] 0xffff;
$WM_SETTINGCHANGE = 0x1a;
$result = [UIntPtr]::Zero

[void] ([Win32.Nativemethods]::SendMessageTimeout($HWND_BROADCAST, $WM_SETTINGCHANGE, [UIntPtr]::Zero, "Environment", 2, 5000, [ref] $result))
}

Uninstall