Public/Pop-VarStash.ps1
<#
.SYNOPSIS Pops a variable stash. .DESCRIPTION Pops a variable stash. This command restores all variables from a variable stash and then removes the stash from storage. The stash can optionally be kept using the -Keep parameter. .EXAMPLE Pop-VarStash Pops the variables from the top of the stash (latest stash, index 0). .EXAMPLE Pop-VarStash -Name MyStash Pops the variables from the stash with name 'MyStash'. .EXAMPLE Pop-VarStash -Index 2 Pops the variables from the stash with index position 2 (lates stash has index 0). .EXAMPLE Pop-VarStash -Keep Pops the variables from the top of the stash (latest stash, index 0). When using parameter -Keep, the stash will not be removed from storage (and the verb pop does not make any sense :) ). #> function Pop-VarStash { [CmdletBinding(DefaultParameterSetName = 'Keep')] param( [parameter(ParameterSetName = 'Name', ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)] [ValidateNotNullOrEmpty()] [string]$Name, [parameter(ParameterSetName = 'Index', ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)] [ValidateRange(0, [int]::MaxValue)] [int]$Index, [parameter(ParameterSetName = 'Name')] [parameter(ParameterSetName = 'Index')] [parameter(ParameterSetName = 'Keep')] [switch]$Keep ) Process { switch ($PSCmdlet.ParameterSetName) { 'Name' { $Stash = Get-VarStash -Name $Name } 'Index' { $Stash = Get-VarStash -Index $Index } Default { $Stash = Get-VarStash -Index 0 } } $StashPath = "$env:APPDATA\VariableStash\VariableStash_$($Stash.Name).xml" # Check if we have a file to import if (Test-Path -Path $StashPath -PathType 'Leaf') { # Import the variables $ImportedVariables = Import-Clixml -Path $StashPath # Set each variable in parent scope foreach ($var in $ImportedVariables) { try { $null = Get-Variable -Name $var.Name -Scope 2 -ErrorAction Stop Write-Verbose "Scope 2: Variable '$($var.Name)' will be overwritten." } catch [System.Management.Automation.PSArgumentOutOfRangeException] { # If we get here, the scope number 2 exceeds the number of active scopes # This can happen if the function is not executing within a module. # (This probably only happens during development) # In that case we use Scope 1 instead try { $null = Get-Variable -Name $var.Name -Scope 1 -ErrorAction Stop Write-Verbose "Scope 1: Variable '$($var.Name)' will be overwritten." Set-Variable -Name $var.Name -Scope 1 -Value $var.Value } catch [System.Management.Automation.PSArgumentOutOfRangeException] { Throw "Unable to get current variables. Have tried both scope 2 and 1. Error: $_" } catch [System.Management.Automation.ItemNotFoundException] { # Scope works. Variable not found in current session Write-Verbose "Scope 1: Variable '$($var.Name)' will be created." Set-Variable -Name $var.Name -Scope 1 -Value $var.Value } catch { Throw "Unable to get current variables in scope 1. Unhandled error. Error: $_" } } catch { # Scope works. Variable not found in current session Write-Verbose "Scope 2: Variable '$($var.Name)' will be created." Set-Variable -Name $var.Name -Scope 2 -Value $var.Value } } if (-not $Keep.IsPresent) { Remove-VarStash -Name $Stash.Name } } else { Write-Error -Category ObjectNotFound -Message 'Stash not found.' } } } |