PowerShell 技能连载 - 提示符与界面定制

适用于 PowerShell 7.0 及以上版本

每天在终端里敲命令数小时,默认的 PS C:\> 提示符只能告诉你当前路径,其他信息一概欠奉。当你在多个 Git 仓库之间切换、管理不同的 Azure 订阅、激活不同的 Python 虚拟环境时,一个信息丰富的提示符可以让你瞬间掌握上下文状态,减少低级错误。

PowerShell 的提示符本质上就是一个名为 prompt 的函数——你可以自由重写它。无论是显示 Git 分支和脏状态、上一次命令的执行耗时、当前用户权限级别,还是用颜色区分不同的服务器环境,都可以通过几行代码实现。本文将带你从手写 prompt 函数开始,再到集成 Oh My Posh 这类成熟框架,最后补充一套提升日常效率的实用工具函数。

手写自定义 prompt 函数

最直接的方式是重写 prompt 函数。下面这段代码实现了一个多行提示符,第一行显示时间、路径和 Git 状态,第二行是实际的输入光标。同时它还记录上一条命令的执行时间,方便你判断某个操作是否太慢。

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
# 保存到 $PROFILE 中即可生效
# 记录命令开始时间
$global:__LastCommandStart = $null

# 在命令执行前记录时间
$ExecutionContext.SessionState.InvokeCommand.AddEventHandler(
'CommandSearchAction', {
$global:__LastCommandStart = [DateTime]::Now
}
)

# 获取 Git 分支与状态信息
function Get-GitStatus {
try {
$branch = git rev-parse --abbrev-ref HEAD 2>$null
if (-not $branch) { return '' }

$status = git status --porcelain 2>$null
$dirty = if ($status) { '*' } else { '' }

$ahead = git log "@{upstream}..HEAD" --oneline 2>$null
$aheadCount = ($ahead | Where-Object { $_ }).Count

$aheadMark = if ($aheadCount -gt 0) { "+$aheadCount" } else { '' }

return " [$branch$dirty$aheadMark]"
} catch {
return ''
}
}

# 获取上一次命令执行耗时
function Get-LastCommandDuration {
if (-not $global:__LastCommandStart) { return '' }
$duration = [DateTime]::Now - $global:__LastCommandStart
if ($duration.TotalSeconds -gt 1) {
return " ($([math]::Round($duration.TotalSeconds, 1))s)"
}
return ''
}

# 自定义 prompt 函数
function prompt {
$path = Get-Location
$homePrefix = $HOME -replace '\\', '\\'
$displayPath = $path.Path -replace "^$homePrefix", '~'
$gitInfo = Get-GitStatus
$duration = Get-LastCommandDuration
$timeStamp = Get-Date -Format 'HH:mm:ss'

# 第一行:时间戳 + 路径 + Git 状态 + 执行耗时
Write-Host "`n" -NoNewline
Write-Host $timeStamp -ForegroundColor DarkGray -NoNewline
Write-Host " " -NoNewline
Write-Host $displayPath -ForegroundColor Cyan -NoNewline
Write-Host $gitInfo -ForegroundColor Yellow -NoNewline
Write-Host $duration -ForegroundColor DarkYellow -NoNewline

# 权限提示
if (
$IsWindows -and
([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()
).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)
) {
Write-Host " [ADMIN]" -ForegroundColor Red -NoNewline
}

# 第二行:输入提示符
Write-Host ""
Write-Host ">" -ForegroundColor Green -NoNewline
return ' '
}

执行后的终端效果如下(纯文本模拟):

1
2
14:32:05 ~/projects/my-app [main*+2] (3.2s)
>

第一行显示了当前时间、相对主目录的路径、Git 分支名称(main)、脏标记(*表示有未提交的更改)、领先远程的提交数(+2)以及上一条命令耗时 3.2 秒。如果在管理员模式下运行,还会出现红色的 [ADMIN] 标记。

集成 Oh My Posh

手动写 prompt 函数虽然灵活,但维护成本不低——尤其是当你想要图标、颜色主题、多种 Segment(环境变量、云平台信息等)时。Oh My Posh 是一个跨 Shell 的提示符渲染引擎,配合 Nerd Font 可以实现非常精美的终端外观。

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
# 安装 Oh My Posh(Windows 推荐使用 winget)
# winget install JanDeDobbeleer.OhMyPosh -s winget

# macOS / Linux 使用 Homebrew
# brew install jandedobbeleer/oh-my-posh/oh-my-posh

# 在 $PROFILE 中初始化 Oh My Posh
oh-my-posh init pwsh --config "$env:POSH_THEMES_PATH\jandedobbeleer.omp.json" |
Invoke-Expression

# 如果想使用自定义配置文件
# $ompConfig = Join-Path $HOME '.config' 'oh-my-posh' 'my-theme.omp.json'
# oh-my-posh init pwsh --config $ompConfig | Invoke-Expression

# 查看所有内置主题
Get-ChildItem -Path $env:POSH_THEMES_PATH -Filter '*.omp.json' |
Select-Object -ExpandProperty Name |
Sort-Object

# 快速预览主题(逐个浏览)
function Show-PoshThemePreview {
param([int]$Index = 0)

$themes = Get-ChildItem -Path $env:POSH_THEMES_PATH -Filter '*.omp.json' |
Sort-Object Name
$theme = $themes[$Index]
Write-Host "Theme [$Index/$($themes.Count)]: $($theme.Name)" -ForegroundColor Cyan
oh-my-posh init pwsh --config $theme.FullName | Invoke-Expression
}

# 导出当前配置并按需修改
function Export-PoshConfig {
param(
[string]$OutputPath = (Join-Path $HOME '.config' 'oh-my-posh')
)

$null = New-Item -ItemType Directory -Path $OutputPath -Force
$defaultConfig = Join-Path $env:POSH_THEMES_PATH 'jandedobbeleer.omp.json'
Copy-Item $defaultConfig (Join-Path $OutputPath 'my-theme.omp.json') -Force
Write-Host "配置已导出到 $OutputPath\my-theme.omp.json" -ForegroundColor Green
Write-Host '修改后更新 $PROFILE 中的 init 命令指向新文件即可。'
}

执行 Get-ChildItem 查看主题列表的部分输出:

1
2
3
4
5
6
1_shell.omp.json
agnoster.omp.json
agnosterplus.omp.json
atomic.omp.json
atomicBit.omp.json
...(共 100+ 内置主题)

执行 Export-PoshConfig 的输出:

1
2
配置已导出到 C:\Users\victor\.config\oh-my-posh\my-theme.omp.json
修改后更新 $PROFILE 中的 init 命令指向新文件即可。

Oh My Posh 的 JSON 配置文件支持丰富的 Segment 类型——Git、Az(Azure)、Python、Node、Docker、Kubectl 等等,你可以按需启用或禁用,调整颜色和图标。推荐从默认主题复制一份然后逐步微调,而不是从零开始编写。

实用工具函数集

提示符之外,Profile 里还可以放一些高频使用的辅助函数,它们与提示符配合让日常操作更加流畅。下面这组函数涵盖了目录快速跳转、增强的命令历史搜索,以及别名管理。

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
# --- 目录快速跳转 ---
# 使用书签机制在常用目录间跳转
$global:DirectoryBookmarks = @{}

function Set-Bookmark {
param([string]$Name)
$global:DirectoryBookmarks[$Name] = (Get-Location).Path
Write-Host "书签 '$Name' 已保存: $($global:DirectoryBookmarks[$Name])" -ForegroundColor Green
}

function Enter-Bookmark {
param([string]$Name)
if ($global:DirectoryBookmarks.ContainsKey($Name)) {
Set-Location $global:DirectoryBookmarks[$Name]
} else {
Write-Warning "书签 '$Name' 不存在。已保存的书签:"
$global:DirectoryBookmarks.GetEnumerator() |
ForEach-Object { Write-Host " $($_.Key) => $($_.Value)" }
}
}

# 简写别名
Set-Alias -Name bm -Value Set-Bookmark
Set-Alias -Name gb -Value Enter-Bookmark

# --- 增强的历史搜索 ---
# 使用 fzf(可选)或 PSFzf 模块进行模糊搜索
# 这里提供一个不依赖外部工具的方案
function Search-History {
param([string]$Pattern = '*')

Get-Content (Get-PSReadlineOption).HistorySavePath |
Where-Object { $_ -like "*$Pattern*" } |
Select-Object -Unique -Last 20
}

Set-Alias -Name hh -Value Search-History

# --- 别名管理 ---
# 列出所有自定义别名及其来源
function Get-MyAliases {
$builtIn = Get-Alias |
Where-Object { $_.Options -notcontains 'UserDefined' } |
Select-Object -ExpandProperty Name

Get-Alias |
Where-Object { $_.Name -notin $builtIn } |
Select-Object Name, Definition, Source |
Sort-Object Name |
Format-Table -AutoSize
}

# 快速进入 Profile 编辑模式
function Edit-Profile {
param([switch]$OpenFolder)
if ($OpenFolder) {
Invoke-Item (Split-Path $PROFILE)
} else {
code $PROFILE
}
}

Set-Alias -Name ep -Value Edit-Profile

使用书签功能的交互示例:

1
2
3
4
5
6
7
8
9
10
PS ~/projects/my-app> bm work
书签 'work' 已保存: /Users/victor/projects/my-app

PS ~> gb work
PS /Users/victor/projects/my-app>

PS ~> hh git
git status
git log --oneline -10
git push origin main

书签机制不依赖外部工具,设置简单,适合在少数几个高频目录之间切换。如果你的目录结构比较复杂,也可以考虑搭配 zzoxide 这类基于频率的跳转工具使用。

注意事项

  1. prompt 函数必须返回字符串:即使你只用 Write-Host 输出内容,函数也必须 return 一个字符串(哪怕是一个空格或空字符串),否则 PowerShell 会使用默认的提示符。
  2. Git 状态检测有性能开销:在大型仓库中,git status --porcelain 可能较慢。如果感到提示符延迟,可以在 Get-GitStatus 中加一个超时判断,或改用 git diff --quiet 做轻量级检测。
  3. Oh My Posh 需要 Nerd Font:图标符号依赖 Nerd Font 字体。如果终端中看到方框或乱码,说明字体未正确安装。推荐使用 CaskaydiaCove Nerd FontFiraCode Nerd Font
  4. Profile 分模块管理:随着自定义内容增多,建议把 prompt、别名、函数拆到不同的 .ps1 文件中,在 $PROFILE 里用 . $path 点源加载,保持主文件简洁。
  5. 跨平台兼容性:本文代码同时适配 Windows、macOS 和 Linux,但管理员检测部分([Security.Principal.WindowsIdentity])只在 Windows 上生效,非 Windows 平台会自动跳过该逻辑。
  6. PSReadLine 是好搭档:提示符定制之外,Set-PSReadlineOption 可以配置预测文本来源、颜色主题和快捷键。结合 CommandPrediction 插件,终端体验可以接近 IDE 级别。

PowerShell 技能连载 - Windows Terminal 与 PowerShell 环境配置

适用于 Windows 10/11,PowerShell 7.0 及以上版本

为什么终端环境如此重要

作为 PowerShell 用户,终端是每天打交道最多的工具。一个配置得当的终端环境不仅能让你心情愉悦,更能显著提升工作效率。试想一下:当你打开终端,迎接你的是清晰的配色、醒目的 Git 状态提示、智能的命令补全,和一系列顺手可用的自定义函数——是不是比面对默认的蓝底白字更有动力?

传统的 Windows PowerShell 5.1 控制台(conhost)功能有限,不支持多标签、缺乏自定义能力。而 Windows Terminal 的出现彻底改变了这一局面:它是开源的、高度可定制的、支持 GPU 加速渲染的现代终端应用。配合 PowerShell 7 和 Oh My Posh,我们可以打造一个不输 macOS/Linux 的终端体验。

本文将从 Windows Terminal 配置、PowerShell 7 Profile 定制、Oh My Posh 美化、PSReadLine 增强以及常用别名函数五个方面,带你一步步搭建理想的终端环境。

Windows Terminal 基础配置

Windows Terminal 的配置存储在一个 JSON 文件中,通过 Ctrl+Shift+, 可以快速打开。以下是一个经过优化的配置片段,涵盖默认配置文件、启动目录、字体和配色方案。

1
2
3
4
5
6
7
8
9
10
11
12
# 查看 Windows Terminal settings.json 的路径
$settingsPath = "$env:LOCALAPPDATA\Packages\Microsoft.WindowsTerminal_8wekyb3d8bbwe\LocalState\settings.json"
Write-Host "Windows Terminal 配置文件路径: $settingsPath"

# 如果文件存在,读取当前默认配置
if (Test-Path $settingsPath) {
$settings = Get-Content $settingsPath -Raw | ConvertFrom-Json
$defaultProfile = $settings.profiles.list | Where-Object { $_.guid -eq $settings.defaultProfile }
Write-Host "当前默认配置文件: $($defaultProfile.name)"
} else {
Write-Host "未找到 Windows Terminal 配置文件,请确认已安装 Windows Terminal"
}

执行结果示例:

1
2
Windows Terminal 配置文件路径: C:\Users\dev\AppData\Local\Packages\Microsoft.WindowsTerminal_8wekyb3d8bbwe\LocalState\settings.json
当前默认配置文件: PowerShell 7

settings.json 中,以下几项配置值得优先调整:

  • defaultProfile:设置为 PowerShell 7 的 GUID,确保默认打开的是 PS7
  • startingDirectory:设定为你常用的工作目录
  • font.face:推荐使用 Nerd Font,以支持 Oh My Posh 的图标显示
  • colorScheme:选择一个护眼且对比度适中的配色方案

PowerShell 7 Profile 定制

PowerShell 的 Profile 文件类似于 bash 的 .bashrc,每次启动 PowerShell 时自动执行。PS7 的 Profile 路径与 PS5.1 不同,互不干扰。

1
2
# 查看 PowerShell 7 的所有 Profile 路径
$PROFILE | Format-List -Force

执行结果示例:

1
2
3
4
AllUsersAllHosts       : C:\Program Files\PowerShell\7\profile.ps1
AllUsersCurrentHost : C:\Program Files\PowerShell\7\Microsoft.PowerShell_profile.ps1
CurrentUserAllHosts : C:\Users\dev\Documents\PowerShell\profile.ps1
CurrentUserCurrentHost : C:\Users\dev\Documents\PowerShell\Microsoft.PowerShell_profile.ps1

最常用的是 CurrentUserCurrentHost,即当前用户、当前宿主的 Profile。我们来创建一个基础 Profile,包含环境变量设置和模块导入:

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
# 确保 Profile 目录存在
$profileDir = Split-Path $PROFILE -Parent
if (-not (Test-Path $profileDir)) {
New-Item -ItemType Directory -Path $profileDir -Force | Out-Null
Write-Host "已创建 Profile 目录: $profileDir"
}

# 创建初始 Profile 文件
$profileContent = @'
# === 环境变量 ===
$env:EDITOR = "code"
$env:PYTHONIOENCODING = "utf-8"

# === 编码设置 ===
[Console]::OutputEncoding = [System.Text.Encoding]::UTF8
[Console]::InputEncoding = [System.Text.Encoding]::UTF8
$OutputEncoding = [System.Text.Encoding]::UTF8

# === 常用模块自动导入 ===
$modulesToImport = @(
"PSReadLine",
"Terminal-Icons"
)

foreach ($mod in $modulesToImport) {
if (Get-Module -ListAvailable -Name $mod) {
Import-Module $mod -ErrorAction SilentlyContinue
}
}

Write-Host "Profile 加载完成 - $(Get-Date -Format 'HH:mm:ss')" -ForegroundColor DarkGray
'@

Set-Content -Path $PROFILE -Value $profileContent -Encoding UTF8
Write-Host "Profile 文件已写入: $PROFILE"

执行结果示例:

1
Profile 文件已写入: C:\Users\dev\Documents\PowerShell\Microsoft.PowerShell_profile.ps1

这段 Profile 做了几件关键的事:统一了编码为 UTF-8(避免中文乱码)、设置了默认编辑器、自动导入常用模块。编码问题是 Windows 下开发最常遇到的坑之一,在 Profile 中统一处理可以省去大量排查时间。

Oh My Posh 终端美化

Oh My Posh 是 Windows 上最流行的终端提示符美化工具,它能为你的终端添加 Git 状态、语言版本、执行时间等信息。配合 Nerd Font,还可以显示丰富的图标。

1
2
3
4
5
6
7
8
9
# 安装 Oh My Posh(推荐通过 winget)
winget install JanDeDobbeleer.OhMyPosh -s winget

# 安装推荐的 Nerd Font
oh-my-posh font install FiraCode

# 查看可用的主题列表
oh-my-posh get shell
Write-Host "可用主题数量: $((oh-my-posh get themes).Count)"

执行结果示例:

1
2
3
4
已成功安装 Oh My Posh
正在安装 FiraCode Nerd Font...
已完成字体安装
可用主题数量: 87

在 Profile 中初始化 Oh My Posh。注意不要在 here-string 中使用三反引号,我们用变量拼接的方式来设置主题路径:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
# 将 Oh My Posh 初始化代码添加到 Profile
$ompInit = @'
# === Oh My Posh 初始化 ===
if (Get-Command oh-my-posh -ErrorAction SilentlyContinue) {
$ompTheme = Join-Path $env:POSH_THEMES_PATH "jandebuhr.omp.json"
if (-not (Test-Path $ompTheme)) {
$ompTheme = "jandedeurbel"
}
oh-my-posh init pwsh --config $ompTheme | Invoke-Expression
}
'@

# 追加到 Profile 末尾
Add-Content -Path $PROFILE -Value "`n$ompInit" -Encoding UTF8
Write-Host "Oh My Posh 初始化代码已添加到 Profile"

执行结果示例:

1
Oh My Posh 初始化代码已添加到 Profile

Oh My Posh 的主题文件是 JSON 格式,你也可以自定义主题。推荐先用内置主题找到喜欢的风格,再在此基础上微调颜色和段落的显示顺序。一个好主题应该在美观和信息密度之间取得平衡——信息太少不实用,太多则显得杂乱。

常用别名与自定义函数

Profile 中最实用的部分之一就是定义别名和函数,把日常高频操作压缩成简短的命令。以下是笔者常用的配置:

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
# 定义常用别名和函数
$aliasAndFuncs = @'
# === 常用别名 ===
Set-Alias -Name ll -Value Get-ChildItem
Set-Alias -Name which -Value Get-Command
Set-Alias -Name touch -Value New-Item
Set-Alias -Name cat -Value Get-Content

# === 自定义函数 ===

# 快速进入项目目录
function projects {
Set-Location "D:\Projects"
}

# 快速查看端口占用
function port {
param([int]$PortNumber)
Get-NetTCPConnection -LocalPort $PortNumber -ErrorAction SilentlyContinue |
Select-Object LocalPort, OwningProcess, State |
Format-Table -AutoSize
}

# 快速查看系统信息
function sysinfo {
$os = Get-CimInstance Win32_OperatingSystem
$cpu = Get-CimInstance Win32_Processor
$mem = [math]::Round($os.FreePhysicalMemory / 1MB, 2)
[PSCustomObject]@{
ComputerName = $env:COMPUTERNAME
OS = $os.Caption
CPU = $cpu.Name
FreeMem_GB = $mem
Uptime = (Get-Date) - $os.LastBootUpTime
} | Format-List
}

# Git 快捷操作
function gs { git status }
function gl { git log --oneline -15 }
function gp { git push }
function gd { git diff $args }

# Docker 快捷操作
function dps { docker ps --format "table {{.ID}}\t{{.Names}}\t{{.Status}}\t{{.Ports}}" }
function dex {
param([string]$ContainerName)
docker exec -it $ContainerName /bin/sh
}
'@

Add-Content -Path $PROFILE -Value "`n$aliasAndFuncs" -Encoding UTF8
Write-Host "别名和函数已添加到 Profile"

执行结果示例:

1
别名和函数已添加到 Profile

这些函数的设计原则是”短小精悍”:每个函数只做一件事,名字尽量简短但能望文生义。比如 port 8080 比输入完整的 Get-NetTCPConnection -LocalPort 8080 简洁得多,gs 则是 git status 的经典缩写。你可以根据自己的工作流继续扩展这个列表。

PSReadLine 增强补全

PSReadLine 是 PowerShell 的命令行编辑模块,PS7 已内置 2.x 版本。合理配置后,它能提供类似 fish shell 的自动补全体验——输入时实时预测、历史命令搜索、语法高亮一应俱全。

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
# 配置 PSReadLine
$psreadlineConfig = @'
# === PSReadLine 配置 ===
if ($host.Name -eq 'ConsoleHost') {
# 预测文本来源:历史记录 + 插件
Set-PSReadLineOption -PredictiveSource HistoryAndPlugin
# 预测文本显示方式:列表视图(类似 fish)
Set-PSReadLineOption -PredictiveStyle ListView
# 历史记录去重
Set-PSReadLineOption -HistoryNoDuplicates
# 保存历史记录条数
Set-PSReadLineOption -MaximumHistoryCount 10000
# 历史记录保存路径
Set-PSReadLineOption -HistorySavePath (Join-Path $env:USERPROFILE ".ps_history")
# 编辑模式设为 Emacs(更符合开发习惯)
Set-PSReadLineOption -EditMode Emacs
# 颜色主题
Set-PSReadLineOption -Colors @{
Command = 'Yellow'
Parameter = 'Green'
String = 'Cyan'
Comment = 'DarkGray'
Operator = 'Magenta'
Prediction = 'DarkGray'
InlinePrediction = 'DarkGray'
}

# Ctrl+d 删除字符(类似 bash)
Set-PSReadLineKeyHandler -Chord 'Ctrl+d' -Function DeleteChar
# Ctrl+w 删除前一个单词
Set-PSReadLineKeyHandler -Chord 'Ctrl+w' -Function BackwardKillWord
# 上下箭头在预测列表中导航
Set-PSReadLineKeyHandler -Chord UpArrow -Function HistorySearchBackward
Set-PSReadLineKeyHandler -Chord DownArrow -Function HistorySearchForward
# Tab 补全显示菜单
Set-PSReadLineKeyHandler -Chord Tab -Function MenuComplete
Set-PSReadLineKeyHandler -Chord Shift+Tab -Function Complete
}
'@

Add-Content -Path $PROFILE -Value "`n$psreadlineConfig" -Encoding UTF8
Write-Host "PSReadLine 配置已添加到 Profile"

执行结果示例:

1
PSReadLine 配置已添加到 Profile

PSReadLine 的预测补全功能是提升效率的关键。当你开始输入命令时,它会根据历史记录实时显示匹配建议,按右箭头即可接受。ListView 模式下还会显示一个下拉列表供你选择,配合 HistoryAndPlugin 来源,补全的准确度非常高。

完整 Profile 模板

经过以上各部分的配置,下面给出一个完整的 Profile 模板,方便你一次性部署。建议按需修改目录路径和主题名称。

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
# 生成完整 Profile 模板
$templateContent = @'
# ============================================
# PowerShell 7 Profile - 完整模板
# 生成日期: 2025-04-25
# ============================================

# === 编码设置 ===
[Console]::OutputEncoding = [System.Text.Encoding]::UTF8
[Console]::InputEncoding = [System.Text.Encoding]::UTF8
$OutputEncoding = [System.Text.Encoding]::UTF8

# === 环境变量 ===
$env:EDITOR = "code"

# === Oh My Posh ===
if (Get-Command oh-my-posh -ErrorAction SilentlyContinue) {
$ompTheme = Join-Path $env:POSH_THEMES_PATH "jandebuhr.omp.json"
if (-not (Test-Path $ompTheme)) { $ompTheme = "jandedeurbel" }
oh-my-posh init pwsh --config $ompTheme | Invoke-Expression
}

# === 模块导入 ===
$autoModules = @("Terminal-Icons")
foreach ($m in $autoModules) {
if (Get-Module -ListAvailable -Name $m) {
Import-Module $m -ErrorAction SilentlyContinue
}
}

# === PSReadLine ===
if ($host.Name -eq 'ConsoleHost') {
Set-PSReadLineOption -PredictiveSource HistoryAndPlugin
Set-PSReadLineOption -PredictiveStyle ListView
Set-PSReadLineOption -HistoryNoDuplicates
Set-PSReadLineOption -MaximumHistoryCount 10000
Set-PSReadLineOption -HistorySavePath (Join-Path $env:USERPROFILE ".ps_history")
Set-PSReadLineOption -EditMode Emacs
Set-PSReadLineOption -Colors @{
Command = 'Yellow'
Parameter = 'Green'
String = 'Cyan'
Comment = 'DarkGray'
Prediction = 'DarkGray'
InlinePrediction = 'DarkGray'
}
Set-PSReadLineKeyHandler -Chord UpArrow -Function HistorySearchBackward
Set-PSReadLineKeyHandler -Chord DownArrow -Function HistorySearchForward
Set-PSReadLineKeyHandler -Chord Tab -Function MenuComplete
}

# === 别名 ===
Set-Alias ll Get-ChildItem
Set-Alias which Get-Command
Set-Alias touch New-Item

# === 自定义函数 ===
function projects { Set-Location "D:\Projects" }
function port([int]$p) { Get-NetTCPConnection -LocalPort $p -ErrorAction SilentlyContinue | Format-Table -AutoSize }
function sysinfo {
$os = Get-CimInstance Win32_OperatingSystem
[PSCustomObject]@{
Computer = $env:COMPUTERNAME
OS = $os.Caption
FreeMemGB = [math]::Round($os.FreePhysicalMemory / 1MB, 2)
Uptime = (Get-Date) - $os.LastBootUpTime
} | Format-List
}

# === Git 快捷命令 ===
function gs { git status }
function gl { git log --oneline -15 }
function gp { git push }

Write-Host "Profile loaded - $(Get-Date -Format 'HH:mm:ss')" -ForegroundColor DarkGray
'@

# 写入 Profile
$profileDir = Split-Path $PROFILE -Parent
if (-not (Test-Path $profileDir)) {
New-Item -ItemType Directory -Path $profileDir -Force | Out-Null
}
Set-Content -Path $PROFILE -Value $templateContent -Encoding UTF8
Write-Host "完整 Profile 模板已写入: $PROFILE"

执行结果示例:

1
完整 Profile 模板已写入: C:\Users\dev\Documents\PowerShell\Microsoft.PowerShell_profile.ps1

部署完成后,重新打开 Windows Terminal 或执行 . $PROFILE 即可生效。首次加载时 Oh My Posh 会编译主题缓存,之后启动速度很快。如果遇到图标显示为方块,说明 Nerd Font 未正确安装或 Windows Terminal 未配置使用该字体。

注意事项

  1. Profile 加载顺序:Oh My Posh 初始化应放在 PSReadLine 配置之前,否则预测补全的颜色设置可能被覆盖。
  2. Nerd Font 必须在 Windows Terminal 中指定:仅安装字体不够,还需要在 settings.json 的 profile 中设置 "font": { "face": "FiraCode Nerd Font" }
  3. Profile 修改后别忘重载:修改 Profile 后,在当前会话中执行 . $PROFILE 重新加载,避免关闭重开。
  4. 编码一致性:确保 settings.json、Profile 文件和系统区域设置都使用 UTF-8,否则中文可能显示为乱码。
  5. 备份你的配置:建议将 Profile 文件和 settings.json 纳入 Git 管理,换机器时一键恢复。
  6. PSReadLine 插件模式PredictiveSource HistoryAndPlugin 需要安装补全模块(如 CompletionPredictor),如果未安装则回退到纯历史记录模式,不会报错。