Powershell - 输出颜色以获得某些结果

时间:2017-09-02 18:07:00

标签: powershell

我正在运行下面的代码并且它有效。我想要做的是,在结果中,当Enabled属性为True时,我想要文本' True'前景色为绿色,否则如果' false'颜色红色。

与密码永不过期属性相同,如果结果是“真实”。我想要的文字' True'前景色为红色,否则如果其为“假”'颜色绿色。

我正在尝试在代码中使用if-else语句,但还没有成功。

代码:

Get-ADUser "user name"  -Properties Enabled,LockedOut,DisplayName,GivenName, SurName,Mail,LastLogon, Created,passwordlastset,Passwordneverexpires,msDS-UserPasswordExpiryTimeComputed, Description, office, Canonicalname | `
        Select-Object Enabled, 
        @{Expression={$_.LockedOut};Label='Locked';}, 
        @{Expression={$_.DisplayName};Label='Display Name';},
        @{Expression ={$_.GivenName};Label='Name';}, `
        @{Expression ={$_.SurName}; Label='Last Name'; }, 
        Mail, 
        @{Expression ={[DateTime]::FromFileTime($_.LastLogon)}; Label='Last Logon';}, 
        @{Expression={$_.Created};Label='Date Created';}, 
        @{Expression={$_.passwordlastset};Label='PW Last Reset';}, 
        @{Expression={$_.Passwordneverexpires};Label='PW Never Expires';},
        @{Name="PW Exp Date";Expression={[datetime]::FromFileTime($_."msDS-UserPasswordExpiryTimeComputed")}}  ,
        Description, 
        Office,
        Canonicalname 
        Format-list

enter image description here

有什么建议吗?

3 个答案:

答案 0 :(得分:4)

在下方找到高级函数Out-HostColored ,您可以管道输出任何命令,并根据正则表达式/子串<选择性地为其输出着色< /强>

通过模拟输入应用于您的案例:

@'
Enabled          : True
Locked           : False
Display Name     : foo
Name             : bar
Last Name        : baz
Mail             : bar.baz@example.org
Last Logon       : 9/1/2017 7:33:30 PM
Date Created     : 11/21/2014 6:04:54 AM
PW Last Reset    : 9/2/2015
PW Never Expires : False
Description      : Technician
Office           : IT
Canonical Name   : CORPORATE.LOCAL/foo Users/bar
'@ | Out-HostColored '(?<=Enabled\s+: )True|(?<=PW Never Expires\s+: )False' Green

传递一个正则表达式,它只匹配感兴趣的标记并将它们标记为绿色 请注意使用后视断言((?<=...))来匹配正确的上下文,而不在匹配中包含它。

以上产量:

sample output

Out-HostColored功能:

  • 您可以管道任何命令 - 无论您是依赖于其隐式格式还是首先显式地将其管道传输到Format-* cmdlet。

  • 匹配仅限于一行,但支持在给定行上着色多个匹配。

  • 如果需要,您可以明确指定前景色(-ForegroundColor)和(-BackgroundColor);默认情况下,匹配颜色为绿色。

  • 如果找到匹配项,请为整行着色,请传递-WholeLine

  • 要传递文字子字符串以匹配而不是正则表达式,请传递-SimpleMatch

Out-HostColored源代码(PSv2 +):

<#
.SYNOPSIS
Colors portions of the default host output that match a pattern.

.DESCRIPTION
Colors portions of the default-formatted host output based on either a
regular expression or a literal substring, assuming the host is a console or
supports colored output using console colors.

Matching is restricted to a single line at a time, but coloring multiple
matches on a given line is supported.

.PARAMETER Pattern
The regular expression specifying what portions of the input should be
colored. Do not use named capture groups in the regular expression, unless you
also specify -WholeLine.
If -SimpleMatch is also specified, the pattern is interpreted as a literal
substring to match.

.PARAMETER ForegroundColor
The foreground color to use for the matching portions.
Defaults to green.

.PARAMETER BackgroundColor
The optional background color to use for the matching portions.

.PARAMETER WholeLine
Specifies that the entire line containing a match should be colored, 
not just the matching portion.

.PARAMETER SimpleMatch
Interprets the -Pattern argument as a literal substring to match rather than
as a regular expression.

.PARAMETER InputObject
Specifies what to output. Typically, the output form a command provided
via the pipeline.

.NOTES
Requires PSv2 or above.
All pipeline input is of necessity collected first before output is produced.

.EXAMPLE
Get-Date | Out-HostColored '\bSeptember\b' red white

Outputs the current date with the word 'September' printed in red on a white background, if present.
#>
Function Out-HostColored {
  # Note: The [CmdletBinding()] and param() block are formatted to be PSv2-compatible.
  [CmdletBinding()]
  param(
    [Parameter(Position=0, Mandatory=$True)] [string] $Pattern,
    [Parameter(Position=1)] [ConsoleColor] $ForegroundColor = 'Green',
    [Parameter(Position=2)] [ConsoleColor] $BackgroundColor,
    [switch] $WholeLine,
    [switch] $SimpleMatch,
    [Parameter(Mandatory=$True, ValueFromPipeline=$True)] $InputObject
  )

  # Wrap the pattern / literal in an explicit capture group.
  try { 
    $re = [regex] ('(?<sep>{0})' -f $(if ($SimpleMatch) { [regex]::Escape($Pattern) } else { $Pattern }))
  } catch { Throw }

  # Build a parameters hashtable specifying the colors, to be use via
  # splatting with Write-Host later.
  $htColors = @{
    ForegroundColor = $ForegroundColor
  }
  if ($BackgroundColor) {
    $htColors.Add('BackgroundColor', $BackgroundColor)
  }  

  # Use pipeline input, if provided.
  if ($MyInvocation.ExpectingInput) { $InputObject = $Input }

  # Apply default formatting to each input object, and look for matches to
  # color line by line.
  $InputObject | Out-String -Stream | ForEach-Object {
    $line = $_
    if ($WholeLine){ # Color the whole line in case of match.
      if ($havePattern -and $line -match $re) {
        Write-Host @htColors $line
      } else {
        Write-Host $line
      }
    } else {
      # Split the line by the regex and include what the regex matched.
      $segments = $line -split $re, 0, 'ExplicitCapture'
      if ($segments.Count -eq 1) { # no matches -> output line as-is
        Write-Host $line
      } else { # at least 1 match, as a repeating sequence of <pre-match> - <match> pairs
        $i = 0
        foreach ($segment in $segments) {
          if ($i++ % 2) { # matching part
            Write-Host -NoNewline @htColors $segment
          } else { # non-matching part
            Write-Host -NoNewline $segment
          }
        }
        Write-Host '' # Terminate the current output line with a newline.
      }
    }
  }
}

答案 1 :(得分:2)

这是一个可能的解决方案:

$Highlight = @{
    True = 'Red'
    False = 'Green'
}

$User = Get-ADUser "user name"  -Properties Enabled,LockedOut,DisplayName,GivenName,SurName,Mail,LastLogon,Created,passwordlastset,Passwordneverexpires,msDS-UserPasswordExpiryTimeComputed, Description, office, Canonicalname |
        Select-Object Enabled, 
        @{Expression={$_.LockedOut};Label='Locked';}, 
        @{Expression={$_.DisplayName};Label='Display Name';},
        @{Expression ={$_.GivenName};Label='Name';}, `
        @{Expression ={$_.SurName}; Label='Last Name'; }, 
        Mail, 
        @{Expression ={[DateTime]::FromFileTime($_.LastLogon)}; Label='Last Logon';}, 
        @{Expression={$_.Created};Label='Date Created';}, 
        @{Expression={$_.passwordlastset};Label='PW Last Reset';}, 
        @{Expression={$_.Passwordneverexpires};Label='PW Never Expires';},
        @{Name="PW Exp Date";Expression={[datetime]::FromFileTime($_."msDS-UserPasswordExpiryTimeComputed")}},
        Description, 
        Office,
        Canonicalname | Format-list | Out-String

$User -split "`n" | ForEach-Object {
    $Output = $False
    If ($_ -match 'Enabled|PW Never Expires') {
        ForEach ($Entry in $Highlight.Keys){
            $Text = $_ -split $Entry
            If ($Text.count -gt 1) { 
                Write-Host $Text[0] -NoNewline
                Write-Host $Entry -ForegroundColor $Highlight.$Entry
                $Output = $true
                Break
            }
        }
    }

    If (-not $Output) { Write-Host $_ }
}

请注意,这应该适用于您使用Format-List获得的输出类型,但特别注意不要突出显示功能:例如,这不会处理可能出现多个的单词在同一行文本中的时间。

另外,以这种方式使用PowerShell的FYI通常不是最佳实践。您应该考虑编写输出到管道而不是Write-Host的PowerShell工具,这样您就可以在其他命令中操作结果,或者将其转换(例如CSV等)。

答案 2 :(得分:2)

使用this link中的Format-Color函数,其RegEx与您的行匹配。

$String = @"
Enabled          : True
Locked           : False
Display Name     : empty
Last Logon       : 9/1/2017
PW Last Reset    : 9/2/2015
PW Never Expires : False
Description      : Technician
Offic            : IT
"@

$String  | Format-Color @{'^PW Never Expires\s+: False|^Enabled\s+: True' = 'Green'}

enter image description here