首页 > 解决方案 > 使用powershell从文件中提取数据并在新文件中排序

问题描述

我正在编写一个脚本,它应该给我一个调用 ID 的每个请求的时间。短线保存调用 ID。在长行中,我收到了服务器的消息。

我需要通过获取 ID 和 ApplicationGatewayID 以及发送和接收之间的时间差来构造文件。

我的计划是在一行上获取请求和响应,尽管文件是按 invokeID 排序的,但模式不是规则的。此外,还有一些只有响应而没有请求的 ID,这使得它变得更加困难。

11:20:36:645 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:645 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:645 ra-agi Trace:     InvokeID =             11359017 
11:20:36:645 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:645 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:645 ra-agi Trace:     InvokeID =             11359018 
11:20:36:739 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:739 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:739 ra-agi Trace:     InvokeID =             11359026 
11:20:36:723 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:723 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:723 ra-agi Trace:     InvokeID =             11359027 
11:20:36:739 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:739 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:739 ra-agi Trace:     InvokeID =             11359028 
11:20:36:739 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:739 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:739 ra-agi Trace:     InvokeID =             11359029 
11:20:36:848 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:848 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:848 ra-agi Trace:     InvokeID =             11359031 
11:20:36:645 11359032
11:20:36:645 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:645 ra-agi Trace:     ApplicationGatewayID = 5000  11:20:36:645 ra-agi Trace:     InvokeID =             11359032 
11:20:36:645 11359033
11:20:36:676 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:676 ra-agi Trace:     ApplicationGatewayID = 5000  11:20:36:676 ra-agi Trace:     InvokeID =             11359033 
11:20:36:848 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:848 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:848 ra-agi Trace:     InvokeID =             11359034 
11:20:36:645 11359034
11:20:36:676 11359035
11:20:36:848 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:848 ra-agi Trace:     ApplicationGatewayID = 5001  11:20:36:848 ra-agi Trace:     InvokeID =             11359035 
11:20:36:739 ra-agi Trace: Received Query Confirm message from application gateway host.  11:20:36:739 ra-agi Trace:     ApplicationGatewayID = 5000  11:20:36:739 ra-agi Trace:     InvokeID =             11359036 
11:20:36:739 11359036
11:20:36:739 11359037

最终产品应如下所示:第一列 InvokeID,第二列 ApplicationGatewayID,第三列:发送和接收之间的时间

11359017    5001    127
11359018    5000    114
11359019    5001    105

标签: powershell

解决方案


看到您的最后评论,如果我正确理解了这个问题,应该这样做:

$result = (Get-Content -Path 'X:\TheInputFile.txt').Trim() | Where-Object { $_.Length -gt 8 } |
    Group-Object @{Expression = {$_.Substring($_.Length - 8)}} |  # group by InvokeID (last 8 characters of the trimmed line)
    Where-Object {$_.Count -eq 2 } |                              # select only groups with two items in it (one long and one short line)
    ForEach-Object {
        $invokeID  = $_.Name
        $millisOne = $millisTwo = 0   # two variables to store the parsed milliseconds from the time stamps
        foreach ($line in $_.Group) {
            $timeToParse = $line.Substring(0,12) -replace ':(\d{3}$)', '.$1' # replace the last colon ':' into a dot '.' for parsing
            if ($line -match 'ApplicationGatewayID\s+=\s+(\d+)') {           # if this is the long line..
                $gatewayID = $Matches[1]
                $millisOne = [TimeSpan]::Parse($timeToParse).TotalMilliSeconds
            }
            else {
                $millisTwo = [TimeSpan]::Parse($timeToParse).TotalMilliSeconds
            }
        }
        # output an object with the properties you need
        [PsCustomObject]@{
            'InvokeID'             = $invokeID
            'ApplicationGatewayID' = $gatewayID
            'ProcessTime'          = [Math]::Abs($millisOne - $millisTwo)
        }
    }

# output the result on screen
$result

# write the resukt to a new CSV file
$result | Export-Csv -Path 'X:\TheOutputFile.csv' -NoTypeInformation

使用您的示例输入文件会产生以下结果:

InvokeID ApplicationGatewayID ProcessTime
-------- -------------------- -----------
11359032 5000                           0
11359033 5000                          31
11359034 5001                         203
11359035 5001                         172
11359036 5000                           0

推荐阅读