Skip to content

Instantly share code, notes, and snippets.

@thimslugga
Forked from tonysneed/windows-terminal-setup.md
Last active January 2, 2026 19:42
Show Gist options
  • Select an option

  • Save thimslugga/463cae9821ee567e95d87c1b65012239 to your computer and use it in GitHub Desktop.

Select an option

Save thimslugga/463cae9821ee567e95d87c1b65012239 to your computer and use it in GitHub Desktop.
Windows Terminal Setup

Windows Terminal Setup

Overview

winver
Set-ExecutionPolicy RemoteSigned -Scope CurrentUser
Set-ExecutionPolicy -ExecutionPolicy RemoteSigned -Scope CurrentUser
$ErrorActionPreference = "Stop"
Set-ExecutionPolicy Bypass -Scope Process -Force;

winget install -e --id Microsoft.PowerToys -h
winget install -e --id Microsoft.WindowsTerminal -h
winget install -e --id Microsoft.Powershell --source winget -h
winget install -e --id Microsoft.VisualStudioCode -h
winget install -e --id Notepad++.Notepad++ -h

# Install-Module oh-my-posh -Scope CurrentUser -Force
#winget install -e --id JanDeDobbeleer.OhMyPosh -h
#oh-my-posh font install "CascadiaCode (MS)"

winget install -e --id Git.Git
winget install --id GitHub.cli
#winget install -e --id Microsoft.Bicep -h

winget install -e --id AgileBits.1Password -s winget
git config --global user.name "First Last"
git config --global user.email <email>

git config --global alias.lg "log --color --graph --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit"
notepad $PROFILE
New-Item -Path $PROFILE -Type File -Force
. $PROFILE
# Terminal Icons
# https://github.com/devblackops/Terminal-Icons
# Install-Module -Name Terminal-Icons -Repository PSGallery
if (Get-Module -ListAvailable -Name Terminal-Icons) {
    Import-Module -Name Terminal-Icons
} 
else {
    Write-Host "Install Terminal Icons"
    Set-PSRepository -Name PSGallery -InstallationPolicy Trusted
    Install-Module -Name Terminal-Icons -Repository PSGallery -Scope CurrentUser
    Import-Module -Name Terminal-Icons
}

# Install PSReadLine
Install-Module -Name PSReadLine -AllowPrerelease -Scope CurrentUser -Force -SkipPublisherCheck

# Install PackageManagement
Install-Module -Name PackageManagement -Repository PSGallery -Force

# Install PowerShellGet
Install-Module -Name PowerShellGet -Force -AllowClobber
notepad $PROFILE
#code $PROFILE
#Requires -Version 7.0
# PowerShell 7 Profile

#region Immediate (fast, essential)
[Console]::OutputEncoding = [Text.Encoding]::UTF8
#endregion

#region PSReadLine Configuration (load early, already in memory)
Set-PSReadLineOption -EditMode Windows
Set-PSReadLineOption -BellStyle None
Set-PSReadLineOption -PredictionSource History
#Set-PSReadLineOption -PredictionSource HistoryAndPlugin
Set-PSReadLineOption -PredictionViewStyle ListView
Set-PSReadLineOption -HistoryNoDuplicates
Set-PSReadLineOption -HistorySearchCursorMovesToEnd
Set-PSReadLineOption -MaximumHistoryCount 10000

Set-PSReadLineKeyHandler -Key UpArrow -Function HistorySearchBackward
Set-PSReadLineKeyHandler -Key DownArrow -Function HistorySearchForward
Set-PSReadLineKeyHandler -Key Tab -Function MenuComplete
Set-PSReadLineKeyHandler -Chord "Ctrl+f" -Function ForwardWord
Set-PSReadLineKeyHandler -Chord "Ctrl+RightArrow" -Function ForwardWord
#endregion

#region Functions
# --- Quick directory navigation ---
function .. { Set-Location .. }
function ... { Set-Location ..\.. }
function .... { Set-Location ..\..\.. }
function ~ { Set-Location ~ }
#function workspace { Set-Location D:\Users\<username>\workspace }
#function workplace { Set-Location D:\Users\<username>\workplace }

# --- Show current path ---
function pwd { Get-Location }

# --- Clear screen properly ---
function c { Clear-Host }

# --- List files and directories ---
function ls { Get-ChildItem @args }
function ll { Get-ChildItem -Force @args }
function lst { Get-ChildItem @args | Sort-Object LastWriteTime -Descending }
function lsf { Get-ChildItem -File @args }
function lsd { Get-ChildItem -Directory @args }

# --- Git shortcuts ---
function gs { git status }
function gst { git status -sb }
function gl { git log --oneline --graph --decorate --all }
function glog { git log --oneline -20 }
function gd { git diff $args }
function gco { git checkout $args }
function gpl { git pull }
function gps { git push }
function gb { git branch $args }
function ga { git add $args }
function gaa { git add -A }
function gcm { param($m) git commit -m $m }

# --- Helper functions ---
function Get-ChildItemPretty {
    Get-ChildItem | Format-Table -AutoSize
}

function Reload-Profile {
    . $PROFILE  # source to reload in the current scope
}

# --- Copy output to clipboard ---
function clip { $input | Set-Clipboard }

# --- Quick system info ---
function sysinfo {
    $os = Get-CimInstance Win32_OperatingSystem
    $uptime = (Get-Date) - $os.LastBootUpTime
    $cpu = Get-CimInstance Win32_Processor
    $gpu = (Get-CimInstance Win32_VideoController | Where-Object {$_.Name -notlike "*Monitor*"} | Select-Object -First 1)
    $totalMem = [math]::Round($os.TotalVisibleMemorySize / 1MB, 2)
    $freeMem = [math]::Round($os.FreePhysicalMemory / 1MB, 2)
    $usedMem = [math]::Round($totalMem - $freeMem, 2)
    $storageC = Get-CimInstance Win32_LogicalDisk -Filter "DeviceID='C:'"
    $storageTotalC = [math]::Round($storageC.Size / 1GB, 2)
    $storageFreeC = [math]::Round($storageC.FreeSpace / 1GB, 2)

    [PSCustomObject]@{
        'Computer Name'      = $env:COMPUTERNAME
        'System Uptime' = "$($uptime.Days)d $($uptime.Hours)h $($uptime.Minutes)m"
        'OS'            = $os.Caption
        'Architecture'  = $os.OSArchitecture
        'CPU'           = $cpu.Name
        'Cores / Threads' = "$($cpu.NumberOfCores)c/$($cpu.NumberOfLogicalProcessors)t"
        'Memory Use'    = "$usedMem GB / $totalMem GB"
        'Storage Use (C:)' = "$([math]::Round($storageTotalC - $storageFreeC, 2)) GB / $storageTotalC GB"
        'Storage Free (C:)'  = "$storageFreeC GB"
        'GPU'           = $gpu.Name
        'IP Address'    = (Get-NetIPAddress -AddressFamily IPv4 | Where-Object {$_.InterfaceAlias -notlike "*Loopback*"} | Select-Object -First 1).IPAddress
        'PowerShell'        = $PSVersionTable.PSEdition
        'PowerShell Version' = $PSVersionTable.PSVersion.ToString()
    } | Format-List
}

function whereis ($command) {
    Get-Command -Name $command -ErrorAction SilentlyContinue |
    Select-Object -ExpandProperty Path -ErrorAction SilentlyContinue
}

function mkcd ($dir) {
    New-Item -ItemType Directory -Path $dir -Force | Out-Null
    Set-Location $dir
}

function touch {
    param([string]$Path)
    if (Test-Path $Path) { (Get-Item $Path).LastWriteTime = Get-Date }
    else { New-Item -ItemType File -Path $Path | Out-Null }
}

function grep {
    param(
        [Parameter(Position=0)]$Pattern,
        [Parameter(Position=1, ValueFromPipeline)]$InputObject
    )
    process {
        if ($InputObject) {
            $InputObject | Select-String $Pattern
        } else {
            Select-String $Pattern
        }
    }
}

# --- Quick directory bookmark system ---
function mark {
    param([string]$name)
    $global:DirMarks = @{}
    if (-not $name) { $global:DirMarks; return }
    $global:DirMarks[$name] = Get-Location
    Write-Host "Marked current directory as '$name'"
}

function jump {
    param([string]$name)
    if ($global:DirMarks[$name]) {
        Set-Location $global:DirMarks[$name]
    } else {
        Write-Host "No mark found for '$name'"
    }
}

# --- Open file in editor ---
function edit {
    param([string]$file)
    if (Get-Command code -ErrorAction SilentlyContinue) {
        code $file
    } elseif (Get-Command notepad++ -ErrorAction SilentlyContinue) {
        notepad++ $file
    } else {
        notepad $file
    }
}

# --- Kill process by name ---
function pkill {
    param([string]$name)
    Get-Process -Name "*$name*" | Stop-Process -Force
    Write-Host "Killed processes matching: $name"
}

# --- Flush DNS cache ---
function flushdns {
    Clear-DnsClientCache
    Write-Host "DNS cache flushed."
}

# --- Get local interface IP ---
function localip {
    Get-NetIPAddress -AddressFamily IPv4 |
        Where-Object {$_.InterfaceAlias -notlike "*Loopback*"} |
        Select-Object IPAddress, InterfaceAlias
}

# --- Base64 encode and decode ---
function b64encode {
    param([string]$text)
    [Convert]::ToBase64String([Text.Encoding]::UTF8.GetBytes($text))
}

function b64decode {
    param([string]$encoded)
    [Text.Encoding]::UTF8.GetString([Convert]::FromBase64String($encoded))
}
#endregion

#region Aliases
Set-Alias -Name g -Value git
#Set-Alias -Name lg -Value lazygit
#Set-Alias -Name vim -Value nvim -ErrorAction SilentlyContinue
#endregion

#region Async Module Loading (deferred until idle)
$global:__deferredLoadComplete = $false

Register-EngineEvent -SourceIdentifier PowerShell.OnIdle -MaxTriggerCount 1 -Action {
    # Oh-my-posh
    #oh-my-posh init pwsh | Invoke-Expression

    # Winget CommandNotFound
    if (Get-Module -ListAvailable -Name Microsoft.WinGet.CommandNotFound) {
        Import-Module -Name Microsoft.WinGet.CommandNotFound -ErrorAction SilentlyContinue
    }

    # Terminal-Icons
    if (Get-Module -ListAvailable -Name Terminal-Icons) {
        Import-Module -Name Terminal-Icons -Global -ErrorAction SilentlyContinue
    }

    # Starship prompt
    #Invoke-Expression (&starship init powershell)

    $global:__deferredLoadComplete = $true

    # Refresh prompt
    [Microsoft.PowerShell.PSConsoleReadLine]::InvokePrompt()
} | Out-Null
#endregion
. $PROFILE
Get-InstalledModule | Update-Module -Force
Set-ExecutionPolicy -Scope CurrentUser -ExecutionPolicy Restricted

Enable-UAC
Enable-MicrosoftUpdate
Install-WindowsUpdate -acceptEula

Enable WSL

This feature is disabled by default and you must activate it:

  • You can do this with PowerShell (with administrator privileges):
dism.exe /online /enable-feature /featurename:Microsoft-Windows-Subsystem-Linux /all /norestart
dism.exe /online /enable-feature /featurename:VirtualMachinePlatform /all /norestart
  • Or change it manually in:
Control-Panel -> Programs -> Turn Windows feature on or off, and click the "Windows subsystem for linux" and "Virtual Machine Platform" buttons.

Then restart your computer to finish installing the requested changes.

Update to WSL2

In order to update WSL you need to download the Linux kernel update package. After installing the add-on, go into PowerShell and paste:

wsl --set-default-version 2

With this command, all our new distributions will be installed with version two.

Resources

References

Windows Terminal Setup

References:

Prerequisites

  1. Set default terminal application to Windows Terminal.

    • Settings, Startup.
    terminal-startup
  2. Install Caskaydia Cove Nerd Font for Glyphs

    • Extract and copy to c:\windows\fonts
    • Settings, Profiles, PowerShell, Appearance, Fontface, select CaskaydiaCove NF
    • VS Code Settings, Text Editor, Font, add 'CaskaydiaCove NF',
  3. Install Oh My Posh for Windows.

    • Install Oh My Posh using winget with the command: winget install JanDeDobbeleer.OhMyPosh
    • Browse prompt themes: https://ohmyposh.dev/docs/themes
    • Choose a theme and edit your PowerShell $PROFILE: code $PROFILE
    • Paste (replacing theme): oh-my-posh --init --shell pwsh --config ~/AppData/Local/Programs/oh-my-posh/themes/jandedobbeleer.omp.json | Invoke-Expression
  4. Install Terminal Icons

    • Install-Module -Name Terminal-Icons -Repository PSGallery
    • code $profile, paste Import-Module -Name Terminal-Icons
  5. Optional: Install Oh My Posh on WSL Ubuntu.

    • Follow instructions for manual Linux installation.
    • Edit .bashrc file: code ~/.bashrc
    • Paste eval "$(oh-my-posh --init --shell bash --config ~/.poshthemes/jandedobbeleer.omp.json)"
    • Windows Terminal Settings, Profiles, Ubuntu, Appearance, Font face, select CaskaydiaCove NF.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment