我对PSReadLine
历史记录在Powershell中跨会话的工作方式感到困惑。我可以在PS 5.1版中看到我以前的命令历史记录自动存储在
%userprofile%\AppData\Roaming\Microsoft\Windows\PowerShell\PSReadline\
但是,如果我运行get-history
,则只会看到当前的会话命令历史记录。我认为在更高版本的Powershell中不再需要钩子来保存跨会话的命令历史记录。我想念什么?
答案 0 :(得分:1)
文件
%userprofile%\AppData\Roaming\Microsoft\Windows\PowerShell\PSReadline\ConsoleHost_history.txt
仅包含输入的命令(此处为ATM 22k行),
和当前会话历史记录
Get-History | Format-List -Property *
Id : 88
CommandLine : get-help Get-History -online
ExecutionStatus : Completed
StartExecutionTime : 2018-12-14 16:16:49
EndExecutionTime : 2018-12-14 16:16:49
完全不同。
答案 1 :(得分:0)
Get-History访问 PowerShell 历史记录(仅限当前会话)。
PSReadLine使用其自己的历史记录(在内存中并保存在(Get-PSReadLineOption).HistorySavePath
中)。使用PSReadLine输入的命令通常会在输入时附加到历史记录文件中(此行为也可以使用Set-PSReadLineOption -HistorySaveStyle
进行控制)。然后,各种搜索和导航键可以将任何历史记录条目带到当前命令行中。请注意,使用向上箭头或向下箭头访问历史记录时,会跳过并发会话中的新命令(即,在当前会话开始后的 之后输入的命令)(design decision)。但是,可以使用历史记录搜索功能(F8,SHIFT-F8,CTRL-R和CTRL-S)访问这些命令 。不幸的是,搜索后,您无法通过使用向下箭头来检索要搜索的命令之后的命令列表。
如果您(非常)真的(非常)需要使用箭头键从其他会话中访问较新的命令,则可以启动一个新会话,但随后您将失去(访问)任何变量(并重新输入功能)。一种解决方案是使用export-clixml
来传递一些(全部?)变量/函数,方法是创建一个以变量/函数名称作为键的哈希表,然后使用import-clixml
并从生成的哈希表中重新创建变量/函数。在新的会话中。但是,根据要传输的数据的类型和数量,临时文件可能很大,导出速度非常慢,并且只能获取可见数据,因此您可能会丢失方法(因为它们可以依赖内部隐藏成员,而后者可以不能复制)。
另一种方法是简单地重建当前会话中的历史记录,如下所示:
[Microsoft.Powershell.PSConsoleReadLine]::ClearHistory()
$nulhist=($histfile=(Get-PSReadLineOption).HistorySavePath)+".NUL"
Set-PSReadLineOption -historysavepath $nulhist
(gc -raw $histfile) -split "[^```r]`r?`n" | foreach {[Microsoft.Powershell.PSConsoleReadline]::AddToHistory($_) }
Set-PSReadLineOption -HistorySavePath $histfile
Remove-Item $nulhist
这个想法是,我们清除该会话的内存历史记录(ClearHistory()
不会影响历史记录文件),然后再次添加历史记录文件的全部内容,确保跨多行的命令保持不变。临时文件是必需的,因为添加会话历史记录条目还将其添加到历史记录文件中。不幸的是,这也不是特别快,但至少可以维护您的变量。