如果新的会话覆盖文件,但是如果相同的会话覆盖文件

时间:2019-05-28 20:52:39

标签: powershell

我有一个功能可以将脚本中的任何write-hosts转换为tee对象(以后将它们保留以用于着色)

function Write-Host($object) 
{
    $object | tee .\LOG.txt -Append
}

如果文件存在,则当前添加到文件中(如果不存在,则创建一个文件)

我想在每次启动新会话时创建一个。仅在您处于同一会话中时才追加到文件中

我该怎么做?

3 个答案:

答案 0 :(得分:1)

这是全局变量有用的少数情况之一,因为它们可以在整个会话中持续存在。在此示例中,我使用它们来设置唯一的文件名(在本例中为今天的日期),以登录到:

function Write-Host($object) 
{
    if($global:LogFile -eq $null)
    {
        $global:LogFile = ".\LOG-$(Get-Date -Format 'yyyy-MM-dd').txt"
    }

    $object | tee $global:LogFile -Append
}

---编辑:---

从注释中,如果您希望在会话开始时有一个新文件并在会话期间追加,我们仍然可以使用全局变量来确定会话的开始,但是我们只是使用检查来删除文件开头,然后将“附加”保留在发球区域:

function Write-Host($object) 
{
    if($global:LogFile -eq $null)
    {
        $global:LogFile = ".\LOG.txt"
        Remove-Item $global:LogFile -ErrorAction SilentlyContinue
    }

    $object | tee $global:LogFile -Append
}

---编辑2:---

来自第二条评论:

Remove-Item是另一种动物,因为默认情况下它没有输出。实际上,获取任何输出的唯一方法是添加-Verbose参数。但是Tee-Object不能捕获详细流。为了解决这个问题,我们必须使用两个技巧。首先,我们使用重定向(about_Redirection)指定-Verbose参数(以获取输出),以将Verbose流(4)重定向到标准Success(1)/ Information流。这将允许Tee-ObjectRemove-Item cmdlet捕获信息:

Remove-Item test.txt -Verbose 4>&1 | Tee-Object out.txt

答案 1 :(得分:1)

您没有定义新的“会话”给您,所以让我们使用变量$PID,它是PowerShell运行时的进程ID。

理想情况下,您只需要将此部分作为文件名,以便每个进程都有自己的日志。但是您在评论中表示不想使用多个文件。在这种情况下,请将PID写入文件的第一行,然后每次读取。

function Write-Host($object) 
{
    $filename = '.\LOG.txt'

    $logPID = Get-Content -LiteralPath $filename -ReadCount 1 -ErrorAction Ignore
    $newSession = $logPID -ne $PID

    if ($newSession) {
        $PID | Set-Content -LiteralPath $filename
    }

    $object | Tee-Object -FilePath $filename -Append
}

答案 2 :(得分:1)

我将为以后的搜索者提供另一种方法。您可以获取当前进程的开始时间,将其与文件创建时间进行比较,如果文件是在当前PID启动之前创建的,则将其删除。

function Write-Host
{
[cmdletbinding()]
Param([parameter(ValueFromPipeline=$true)]$object)
Begin{
    $allObjects=New-Object System.Collections.ArrayList
}
Process{
    $allObjects.Add($object)|out-null
}
End{
    if((test-path .\log.txt) -and (get-item '.\LOG.txt').CreationTime -lt (Get-Process -Id $PID).StartTime){Remove-Item .\LOG.txt}
    $allObjects | tee .\LOG.txt -Append
}
}

加上向高级功能的转换,您可以将内容通过管道传递给它,例如:

Get-Process | Write-Host

或者我想最简单的事情就是删除日志文件,就像脚本执行的第一件事一样。