Customizing your shell environment
A PowerShell profile is a script that runs when PowerShell starts. You can use the profile to customize the environment. You can:
- add aliases, functions, and variables
- load modules
- create PowerShell drives
- run arbitrary commands
- and change preference settings
Putting these settings in your profile ensures that they're available whenever you start PowerShell on your system.
Note
To run scripts in Windows, the PowerShell execution policy needs to be set to RemoteSigned
at a
minimum. Execution policies don't apply to macOS and Linux. For more information, see
about_Execution_Policy.
The $PROFILE variable
The $PROFILE
automatic variable stores the paths to the PowerShell profiles that are available in
the current session.
There are four possible profiles available to support different user scopes and different PowerShell
hosts. The fully qualified paths for each profile script are stored in the following member
properties of $PROFILE
.
- AllUsersAllHosts
- AllUsersCurrentHost
- CurrentUserAllHosts
- CurrentUserCurrentHost
You can create profile scripts that run for all users or just one user, the CurrentUser. CurrentUser profiles are stored in the user's home directory.
There are also profiles that run for all PowerShell hosts or specific hosts. The profile script
for each PowerShell host has a name unique for that host. For example, the filename for the standard
Console Host on Windows or the default terminal application on other platforms is
Microsoft.PowerShell_profile.ps1
. For Visual Studio Code (VS Code), the filename is
Microsoft.VSCode_profile.ps1
.
For more information, see about_Profiles.
By default, referencing the $PROFILE
variable returns the path to the "Current User, Current Host"
profile. The other profiles path can be accessed through the properties of the $PROFILE
variable.
For example:
PS> $PROFILE
C:\Users\user1\Documents\PowerShell\Microsoft.PowerShell_profile.ps1
PS> $PROFILE.AllUsersAllHosts
C:\Program Files\PowerShell\7\profile.ps1
How to create your personal profile
When you first install PowerShell on a system, the profile script files and the directories they belong to don't exist. The following command creates the "Current User, Current Host" profile script file if it doesn't exist.
if (!(Test-Path -Path $PROFILE)) {
New-Item -ItemType File -Path $PROFILE -Force
}
The Force parameter of New-Item
cmdlet creates the necessary folders when they don't exist.
Once you have created the script file, you can use your favorite editor to customize your shell
environment.
Adding customizations to your profile
The previous articles talked about using tab completion, command predictors, and aliases. These articles showed the commands used to load the required modules, create custom completers, define keybindings, and other settings. These are the kinds of customizations that you want to have available in every PowerShell interactive session. The profile script is the place for these settings.
The simplest way to edit your profile script is to open the file in your favorite code editor. For example, the following command opens the profile in VS Code.
code $PROFILE
You could also use notepad.exe
on Windows, vi
on Linux, or any other text editor.
The following profile script has examples for many of the customizations mentioned in the previous articles. You can use any of these settings in your own profile.
## Map PSDrives to other registry hives
if (!(Test-Path HKCR:)) {
$null = New-PSDrive -Name HKCR -PSProvider Registry -Root HKEY_CLASSES_ROOT
$null = New-PSDrive -Name HKU -PSProvider Registry -Root HKEY_USERS
}
## Customize the prompt
function prompt {
$identity = [Security.Principal.WindowsIdentity]::GetCurrent()
$principal = [Security.Principal.WindowsPrincipal] $identity
$adminRole = [Security.Principal.WindowsBuiltInRole]::Administrator
$prefix = if (Test-Path variable:/PSDebugContext) { '[DBG]: ' } else { '' }
if ($principal.IsInRole($adminRole)) {
$prefix = "[ADMIN]:$prefix"
}
$body = 'PS ' + $PWD.path
$suffix = $(if ($NestedPromptLevel -ge 1) { '>>' }) + '> '
"${prefix}${body}${suffix}"
}
## Create $PSStyle if running on a version older than 7.2
## - Add other ANSI color definitions as needed
if ($PSVersionTable.PSVersion.ToString() -lt '7.2.0') {
# define escape char since "`e" may not be supported
$esc = [char]0x1b
$PSStyle = [pscustomobject]@{
Foreground = @{
Magenta = "${esc}[35m"
BrightYellow = "${esc}[93m"
}
Background = @{
BrightBlack = "${esc}[100m"
}
}
}
## Set PSReadLine options and keybindings
$PSROptions = @{
ContinuationPrompt = ' '
Colors = @{
Operator = $PSStyle.Foreground.Magenta
Parameter = $PSStyle.Foreground.Magenta
Selection = $PSStyle.Background.BrightBlack
InLinePrediction = $PSStyle.Foreground.BrightYellow + $PSStyle.Background.BrightBlack
}
}
Set-PSReadLineOption @PSROptions
Set-PSReadLineKeyHandler -Chord 'Ctrl+f' -Function ForwardWord
Set-PSReadLineKeyHandler -Chord 'Enter' -Function ValidateAndAcceptLine
## Add argument completer for the dotnet CLI tool
$scriptblock = {
param($wordToComplete, $commandAst, $cursorPosition)
dotnet complete --position $cursorPosition $commandAst.ToString() |
ForEach-Object {
[System.Management.Automation.CompletionResult]::new($_, $_, 'ParameterValue', $_)
}
}
Register-ArgumentCompleter -Native -CommandName dotnet -ScriptBlock $scriptblock
This profile script provides examples for the following customization:
- Adds two new PSDrives for the other root registry hives.
- Creates a customized prompt that changes if you are running in an elevated session.
- Configures PSReadLine and adds keybinding. The color settings use the $PSStyle feature to define the ANSI color settings.
- Adds tab completion for the dotnet CLI tool. The tool provides parameters to help resolve the command-line arguments. The script block for Register-ArgumentCompleter uses that feature to provide the tab completion.