Public/Set-EnvironmentVariable.ps1
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 |
<#
.SYNOPSIS A PowerShell module to handle environment variables, supporting variable expansion. This function handles SETTING environment variables. .DESCRIPTION This module is capable of setting Environment Variables in any scope (Process, User, Machine). It will return the value of the Envrionment Variable on completion. .PARAMETER Name [String] Specify the name of the Environment Variable to be set. .PARAMETER Value [String] Specify the value to set in the target Environment Variable. .PARAMETER Scope [System.EnvironmentVariableTarget], [String] Specify the scope in which to affect the target Environment Variable. Process : Environment Variables in the CURRENT process will be affected. Other processes will not be 'aware' of this change. User : Environment Variables in the User Scope affect the Global Environment Variables for the current user. Other users who log on to the machine will not be affected by these changes. Machine : Environment Variables in the Machine Scope change the settings in the registry for all users. These changes will be visible to all processes. .PARAMETER ValueType String : A simple string value ExpandString : A string value which contains unexpanded environment variables in the syntax of %VARIABLENAME%. These variables will NOT be expanded when the value is set in the registry. .PARAMETER Inherit Always, Never, Auto If Set Always, the current process will inherit the changes applied to the User or Machine Variables. This is set to Auto by default. When set to Auto, the command will determine whether or not to update the setting. If the current (pre-operation) value of the variable in Process is equal to that in the target scope, the changes will be inherited. .EXAMPLE PS C:\> Set-EnvironmentVariable -name TestVar -Value 'TestValue' -Scope Machine -ValueType String -Inherit Auto Name : TestVar Value : TestValue Scope : Machine ValueType : String BeforeExpansion : .EXAMPLE PS C:\> Set-EnvironmentVariable -name TestPathVar -Value '%TEMP%\TestValue' -Scope Machine -ValueType ExpandString -Inherit Auto Name : TestPathVar Value : C:\Users\USERNAME\AppData\Local\Temp\TestValue Scope : Machine ValueType : ExpandString BeforeExpansion : %TEMP%\TestValue .EXAMPLE PS C:\> Set-EnvironmentVariable -name TestPathVar -Value '%TEMP%\TestValue' -Scope Machine -ValueType String -Inherit Auto Name : TestPathVar Value : C:\Users\USERNAME\AppData\Local\Temp\TestValue Scope : Machine ValueType : String BeforeExpansion : C:\Users\USERNAME\AppData\Local\Temp\TestValue Because we set the ValueType to ExpandString, the value was set without expanding the string PS C:\> Get-EnvironmentVariable -Name TestPathVar -Scope Machine %TEMP%\TestValue PS C:\> Get-EnvironmentVariable -Name TestPathVar -Scope Process Because there is no Variable called TestPathVar in the Process Scope, it did not inherit the value. .INPUTS [String] .OUTPUTS [Hashtable],[String] .NOTES .LINK https://github.com/rbleattler/xEnvironmentVariables #> function Set-EnvironmentVariable { [CmdletBinding()] param ( # Name of the environment variable [Parameter(Position = 0, Mandatory)] [ValidatePattern("[^=]+")] [String] $Name, # Value of the environment variable [Parameter(Position = 1, Mandatory)] [String] $Value, # Scope of the environment variable [Parameter()] [System.EnvironmentVariableTarget] [System.String] $Scope = [System.EnvironmentVariableTarget]::Process, # Type of the environment variable [Parameter()] [ValidateSet("String", "ExpandString")] [String] $ValueType = "String", # Inheritance method for the environment variable [Parameter()] [ValidateSet("Always", "Auto", "Never")] [String] $Inherit = "Auto" ) try { # Inheritance condition if ($Scope.GetTypeCode() -eq 'String') { $Scope = [System.EnvironmentVariableTarget]::$Scope } if ($Scope -eq "Process") { $Inheritance = $false } else { $Inheritance = switch ($Inherit) { "Never" { $false } "Always" { $true } "Auto" { $CurrentProcessValue = [System.Environment]::GetEnvironmentVariable($Name, "Process") if ($Name -eq "Path") { $CurrentMachineValue = [System.Environment]::GetEnvironmentVariable($Name, "Machine") $CurrentUserValue = [System.Environment]::GetEnvironmentVariable($Name, "User") $CurrentValue = $CurrentMachineValue + $CurrentUserValue } else { $CurrentValue = [System.Environment]::GetEnvironmentVariable($Name, $Scope) } if ($CurrentValue -eq $CurrentProcessValue) { $true } else { $false } } Default { } } } if ($ValueType -ne "ExpandString" -or $Scope -eq 'Process') { $EnvironmentVariableValue = [System.Environment]::ExpandEnvironmentVariables($Value) [System.Environment]::SetEnvironmentVariable($Name, $EnvironmentVariableValue , $Scope) } else { $EnvironmentPath = Get-EnvironmentPath -Scope $Scope Set-ItemProperty -Path $EnvironmentPath -Name $Name -Value $Value -Type $ValueType } Update-EnvironmentVariableSettings # inherit if ($Inheritance) { if ($Name -eq "Path") { $CurrentMachineValue = [System.Environment]::GetEnvironmentVariable($Name, "Machine") $CurrentUserValue = [System.Environment]::GetEnvironmentVariable($Name, "User") $CurrentValue = $CurrentMachineValue + $CurrentUserValue } else { $CurrentValue = [System.Environment]::GetEnvironmentVariable($Name, $Scope) } [System.Environment]::SetEnvironmentVariable($Name, $CurrentValue, "Process") } if ($ValueType -eq 'ExpandString') { Get-EnvironmentVariable -Name $Name -Scope $Scope -ShowProperties } else { Get-EnvironmentVariable -Name $Name -Scope $Scope -Expanded -ShowProperties } } catch { $ScriptName = $_.InvocationInfo.ScriptName $Position = 'In {2} At Line: {0} Char: {1}' -f $_.InvocationInfo.ScriptLineNumber, $_.InvocationInfo.OffsetInLine, $ScriptName $Category = $_.CategoryInfo.Category Write-Error -Message "Error was `"$_`"" -Category $Category -CategoryTargetName $Position } } |