在 PowerShell 中按列拆分文本

Sua*_*Swe 4 regex powershell awk select

我是 PowerShell 新手(Bash 通常是我的东西),他目前正在尝试获取 qwinsta 输出以显示谁以“rdpwd”(rdesktop)用户身份登录,以便我可以根据用户名列表检查每个用户名,如果它们不匹配,将它们注销。

我目前正在解决两个问题:

  1. 我无法将 qwinsta 输出拆分为只留下用户名 - 我已经尝试过“拆分”功能,但到目前为止我遇到了语法问题或奇怪的结果;一个抱怨似乎是 '\s+' 匹配字母 S 而不是空格;其他时候我设法拆分到第二列,但只出现第 1 行的输出
  2. 虽然我还没有到那里,但我感觉我在第二步中也会遇到问题,即遍历不可注销用户的数组(将从本地用户组获取)

我现在将重点放在问题 1 上!

我得到的文字是:

SESSIONNAME       USERNAME        ID     STATE   TYPE      DEVICE
services                          0      Disc
console                           1      Conn
rdp-tcp#0         user.name1      2      Active  rdpwd
rdp-tcp#1         user.name2      3      Active  rdpwd
rdp-tcp#1         user.name3      4      Active  rdpwd
rdp-tcp                           65536  Listen
Run Code Online (Sandbox Code Playgroud)

我想要的输出是:

user.name1
user.name2
user.name3
Run Code Online (Sandbox Code Playgroud)

(目的是创建一个循环,简而言之,“列表中的每个用户,如果不在本地组中,则注销用户”。)

到目前为止,我已经使用“rdpwd”选择文本,但是使用“split”的各种变体,我还没有更进一步。

我很高兴分享我已经拥有的东西,但可惜我认为它不会帮助任何人!

任何帮助将不胜感激。:)

arc*_*444 5

老实说,我会寻找一种更好的方法来做到这一点,但您可以通过一些文本操作和ConvertFrom-Csvcmdlet来捏造它:

$(qwinsta.exe) -replace "^[\s>]" , "" -replace "\s+" , "," | ConvertFrom-Csv | select username
Run Code Online (Sandbox Code Playgroud)

首先用空替换任何前导空格或>字符,然后用逗号替换任何空格。然后,您可以通过管道ConvertFrom-Csv将数据作为对象进行处理。

编辑

实际上,上面有一些问题,主要是\s+因为如果列是空白的,它不会被正确识别为空白字段,并且下一个文本被错误地提升到当前字段。

下面是此命令的完整解析器,可能适用于本机 Windows exe 的任何类型的表格输出:

$o = @()
$op = $(qwinsta.exe)

$ma = $op[0] | Select-String "(?:[\s](\w+))" -AllMatches
$ErrorActionPreference = "Stop"

for($j=1; $j -lt $op.length; $j++) {
    $i = 0
    $obj = new-object pscustomobject
    while ($i -lt $ma.matches.count) { 
      $prop = $ma.matches[$i].groups[1].value; 
      $substrStart = $ma.matches[$i].index 
      $substrLen = $ma.matches[$i+1].index - $substrStart
      try {
        $obj | Add-Member $prop -notepropertyvalue $op[$j].substring($substrStart,$substrLen).trim() 
      }
      catch [ArgumentOutOfRangeException] {
        $substrLen = $op[$j].length - $substrStart 
        if($substrLen -gt 0) {
          $obj | Add-Member $prop -notepropertyvalue $op[$j].substring($substrStart,$substrLen).trim()
        }
        else {
          $obj | Add-Member $prop -notepropertyvalue ""
        }
      }
      $i++
    }
    $o += ,$obj
}

$o | ? { $_.type -eq 'rdpwd'} | select username

USERNAME
--------
user.name1
user.name2
user.name3
Run Code Online (Sandbox Code Playgroud)