PowerShell格式化Cmdlet输出

PowerShell格式化Cmdlet输出,powershell,syntax,formatting,cmdlet,Powershell,Syntax,Formatting,Cmdlet,当我运行以下Get命令Get ChildItem-SyntaxI Get时: <... empty line here ...> Get-ChildItem [[-Path] <string[]>] [[-Filter] <string>] [-Include <string[]>] [-Exclude <string[]>] [-Recurse] [-Depth <uint32>] [-Force] [-Name] [-U

当我运行以下
Get命令Get ChildItem-Syntax
I Get时:

<... empty line here ...>
Get-ChildItem [[-Path] <string[]>] [[-Filter] <string>] [-Include <string[]>] [-Exclude <string[]>] [-Recurse] [-Depth <uint32>] [-Force] [-Name] [-UseTransaction] [-Attributes <FlagsExpression[FileAttributes]>] [-Directory] [-File] [-Hidden] [-ReadOnly] [-System] [<CommonParameters>]
<... empty line here ...>
Get-ChildItem [[-Filter] <string>] -LiteralPath <string[]> [-Include <string[]>] [-Exclude <string[]>] [-Recurse] [-Depth <uint32>] [-Force] [-Name] [-UseTransaction] [-Attributes <FlagsExpression[FileAttributes]>] [-Directory] [-File] [-Hidden] [-ReadOnly] [-System] [<CommonParameters>]
<... empty line here ...>
有谁能提供一个简单的方法来实现这样的格式化输出吗?

给你

(Get-Command Get-ChildItem -Syntax) -split '\r\n' |
    where {$_} | foreach {"# $_"}

# Get-ChildItem [[-Path] <string[]>] [[-Filter] <string>] [-Include <string[]>] [-Exclude <string[]>] [-Recurse] [-Depth <uint32>] [-Force] [-Name] [-UseTransaction] [-Attributes <FlagsExpression[FileAttributes]>] [-Directory] [-File] [-Hidden] [-ReadOnly] [-System] [<CommonParameters>]
# Get-ChildItem [[-Filter] <string>] -LiteralPath <string[]> [-Include <string[]>] [-Exclude <string[]>] [-Recurse] [-Depth <uint32>] [-Force] [-Name] [-UseTransaction] [-Attributes <FlagsExpression[FileAttributes]>] [-Directory] [-File] [-Hidden] [-ReadOnly] [-System] [<CommonParameters>]

太棒了,谢谢道格,真的很有用。我还使用了一个小函数来帮助我很好地格式化换行,这样我就可以使用您的代码来绕过最大宽度:

(Get-Command Get-ChildItem -Syntax) -split '\r\n' | where {$_} | foreach {"# $_"} | Write-Wrap
其中,
Write Wrap
函数的格式始终与控制台的宽度一致(使用下面的mklment0点和他指出的基本流程块进行编辑):


这是我目前的用法。我发现导航模块很笨拙,需要一种更好/更快的方式来获得紧凑的概览。我将它们保存在我的个人
定制工具.psm1
模块中,它可以帮助我快速查看系统上的内容

键入
mods
查看所有已安装的模块及其位置

键入
mods
查看所有匹配项。e、 g.
mods话筒
mods软

键入
mod
查看给定模块内容的快速详细信息

键入
mod-i | more
以获取该模块内容的所有语法详细信息

我发现这是一个非常快速和方便的方式来询问模块。希望对一些人有用

mods

function mods ($search) {
    ""
    ":: Complete `$env:PSModulePath string:`n"
    $env:PSModulePath
    $env:PSModulePath -Split ";" -replace "\\+$", "" | sort
    ""
    ""
    $PathArray = $env:PSModulePath -Split ";" -replace "\\+$", "" | sort
    ""
    foreach ($Path in $PathArray) {
        if ($Path -ne '') {
            $Path = $Path.TrimEnd('\')
            echo ":: Modules under '$Path':`n"
            # if (Test-Path $Path) {
            $temp = (dir "$Path\*$search*" -Directory -EA Silent | Select -ExpandProperty Name) -join ", "   # mods w*  => mods w** which resolves fine
            if ($temp -eq "") { "No matches for '$search' exist in this path" }
            # } else { "This path is in `$env:PSModulePath but the folder does not exist"}
            Write-Wrap $temp
            ""
        }
    }
    ""
}
mod

function mod ($Module, $def, [switch]$ShowModulesHere, [switch]$Info) {
    if ($null -eq $Module) { "You must specify a Module to examine. Run 'mods' to see available Modules." ; break }
    ""
    if ([bool](Get-Module $Module -ListAvailable) -eq $true) {
        if ([bool](Get-Module $Module) -eq $true) { ":: Module '$Module' is already imported, so all functions are available`n" }
        else { ":: Module '$Module' was not imported, running import now ..." ; Import-Module $Module }
    }
    else { "Could not find Module in available Module folders`n" ; break }
    
    $ModulePath = ((Get-Module $Module | select Path).Path).TrimEnd('\')
    $ModuleVer = (Get-Module $Module -ListAvailable | select Version).Version | sls "\d"
    ":: '$Module' is version $($ModuleVer)`n`n$ModulePath"
    
    $ModuleRoot = Split-Path ((Get-Module $Module | select Path).Path).TrimEnd("\")
    $ModulesHere = (dir $Path -Directory | Select -ExpandProperty Name) -join ", "
    
    if ($Info) {
        ""
        foreach ($i in (Get-Command -Module $Module).Name) { 
            $out = $i   # Parse the info string from after the "{" 
            $type = "" ; try { $type = ((gcm $i -EA silent).CommandType); } catch { $deferr = 1 }
            $out += "   # $type"
            $syntax = Get-Command $i -Syntax
            $definition = "" ; if ($type -eq "Alias") { $definition = (get-alias $i).Definition }
            $syntax = $syntax -replace $definition, ""
            if ($type -eq "Alias") { $out += " for '$definition'" }
            $out
            if ($type -eq "Function") { $syntax = $syntax -replace $i, "" }
            if ($type -eq "Cmdlet") { $syntax = $syntax -replace $i, "" }
            if (!([string]::IsNullOrWhiteSpace($syntax))) { 
                $syntax -split '\r\n' | where {$_} | foreach { "Syntax =>   $_" | Write-Wrap }
            }
            ""
        }
        ""
    }
    else {
        ""
        ":: Module functions:"
        $out = ""; foreach ($i in (Get-Command -Module $Module).Name) { $out += " $i," } ; "" ; Write-Wrap $out.TrimEnd(", ")
        ""
    }
    $ModPaths = $env:PSModulePath -Split ";" -replace "\\+$", "" | sort
    ":: Module Paths (`$env:PSModulePath):"
    foreach ($i in $ModPaths) { "   $i"}
    ""
    ":: '$Module' Path:`n`n   $ModulePath"
    ""
    foreach ($i in $ModPaths) {
        if (!([string]::IsNullOrWhiteSpace($i))) {
           if ($ModulePath | sls $i -SimpleMatch) { $ModRoot = $i ; ":: `$env:PSModulePath parent location is:`n`n   $i" }
        }
    }
    ""

    if ($def -ne $null) {
        ":: Press any key to open '$def' definition:"
        pause
        ""
        def $def
        ""
    }

    if ($ShowModulesHere -eq $true) {
        ":: This `$env:PSModulePath root also contains the following Modules:"
        ""
        (dir $ModRoot -Directory | Select -ExpandProperty Name) -join ", "
        ""
    }
}
另外:在循环中以增量方式“扩展”数组是低效的,因为在每次迭代中都必须在幕后创建一个新数组,因为数组是不可变的;更有效的方法是使用
foreach
循环作为表达式,让PowerShell自动收集数组中的输出:
[array]$outputs=foreach(…){…}
-请参阅。您使用的PowerShell主机(如ISE)与该行为无关(版本-PS核心的行为也不相同)。正如预期的那样,无论我在何处运行此程序,我都只看到一个管道输入得到处理,使用当前发布的函数定义和我之前评论中的
1,2,3…
test命令。原因是函数体中没有
begin
/
进程
/
结束
块与运行相同在
end
块中,此时只有最后一个输入对象绑定到参数变量。请参见下面注释中的最小示例。
function Write-Wrap {
    [CmdletBinding()]Param( [parameter(Mandatory, ValueFromPipeline, ValueFromPipelineByPropertyName)] [Object[]]$chunk )
    PROCESS {
        $Lines = @()
        foreach ($line in $chunk) {
            $str = ''; $counter = 0
            $line -split '\s+' | % {
                $counter += $_.Length + 1
                if ($counter -gt $Host.UI.RawUI.BufferSize.Width) {
                    $Lines += ,$str.trim()
                    $str = ''
                    $counter = $_.Length + 1
                }
                $str = "$str$_ "
            }
            $Lines += ,$str.trim()
        }
        $Lines
    }
}
function mods ($search) {
    ""
    ":: Complete `$env:PSModulePath string:`n"
    $env:PSModulePath
    $env:PSModulePath -Split ";" -replace "\\+$", "" | sort
    ""
    ""
    $PathArray = $env:PSModulePath -Split ";" -replace "\\+$", "" | sort
    ""
    foreach ($Path in $PathArray) {
        if ($Path -ne '') {
            $Path = $Path.TrimEnd('\')
            echo ":: Modules under '$Path':`n"
            # if (Test-Path $Path) {
            $temp = (dir "$Path\*$search*" -Directory -EA Silent | Select -ExpandProperty Name) -join ", "   # mods w*  => mods w** which resolves fine
            if ($temp -eq "") { "No matches for '$search' exist in this path" }
            # } else { "This path is in `$env:PSModulePath but the folder does not exist"}
            Write-Wrap $temp
            ""
        }
    }
    ""
}
function mod ($Module, $def, [switch]$ShowModulesHere, [switch]$Info) {
    if ($null -eq $Module) { "You must specify a Module to examine. Run 'mods' to see available Modules." ; break }
    ""
    if ([bool](Get-Module $Module -ListAvailable) -eq $true) {
        if ([bool](Get-Module $Module) -eq $true) { ":: Module '$Module' is already imported, so all functions are available`n" }
        else { ":: Module '$Module' was not imported, running import now ..." ; Import-Module $Module }
    }
    else { "Could not find Module in available Module folders`n" ; break }
    
    $ModulePath = ((Get-Module $Module | select Path).Path).TrimEnd('\')
    $ModuleVer = (Get-Module $Module -ListAvailable | select Version).Version | sls "\d"
    ":: '$Module' is version $($ModuleVer)`n`n$ModulePath"
    
    $ModuleRoot = Split-Path ((Get-Module $Module | select Path).Path).TrimEnd("\")
    $ModulesHere = (dir $Path -Directory | Select -ExpandProperty Name) -join ", "
    
    if ($Info) {
        ""
        foreach ($i in (Get-Command -Module $Module).Name) { 
            $out = $i   # Parse the info string from after the "{" 
            $type = "" ; try { $type = ((gcm $i -EA silent).CommandType); } catch { $deferr = 1 }
            $out += "   # $type"
            $syntax = Get-Command $i -Syntax
            $definition = "" ; if ($type -eq "Alias") { $definition = (get-alias $i).Definition }
            $syntax = $syntax -replace $definition, ""
            if ($type -eq "Alias") { $out += " for '$definition'" }
            $out
            if ($type -eq "Function") { $syntax = $syntax -replace $i, "" }
            if ($type -eq "Cmdlet") { $syntax = $syntax -replace $i, "" }
            if (!([string]::IsNullOrWhiteSpace($syntax))) { 
                $syntax -split '\r\n' | where {$_} | foreach { "Syntax =>   $_" | Write-Wrap }
            }
            ""
        }
        ""
    }
    else {
        ""
        ":: Module functions:"
        $out = ""; foreach ($i in (Get-Command -Module $Module).Name) { $out += " $i," } ; "" ; Write-Wrap $out.TrimEnd(", ")
        ""
    }
    $ModPaths = $env:PSModulePath -Split ";" -replace "\\+$", "" | sort
    ":: Module Paths (`$env:PSModulePath):"
    foreach ($i in $ModPaths) { "   $i"}
    ""
    ":: '$Module' Path:`n`n   $ModulePath"
    ""
    foreach ($i in $ModPaths) {
        if (!([string]::IsNullOrWhiteSpace($i))) {
           if ($ModulePath | sls $i -SimpleMatch) { $ModRoot = $i ; ":: `$env:PSModulePath parent location is:`n`n   $i" }
        }
    }
    ""

    if ($def -ne $null) {
        ":: Press any key to open '$def' definition:"
        pause
        ""
        def $def
        ""
    }

    if ($ShowModulesHere -eq $true) {
        ":: This `$env:PSModulePath root also contains the following Modules:"
        ""
        (dir $ModRoot -Directory | Select -ExpandProperty Name) -join ", "
        ""
    }
}