Unix tail odpowiednik polecenia w Windows Powershell

Muszę spojrzeć na kilka ostatnich linijek dużego pliku (typowy rozmiar to 500MB-2GB). Szukam odpowiednika polecenia Unix tail Dla Windows Powershell. Kilka alternatyw dostępnych na są,

Http://tailforwin32.sourceforge.net/

I

Get-Content [filename] | Select-Object -Last 10

Dla mnie nie wolno używać pierwszej alternatywy, a druga alternatywa jest powolna. Czy ktoś wie o wydajnej implementacji tail dla PowerShell.

Author: Gabe, 2010-12-13

10 answers

Użyj parametru -wait z Get-Content, który wyświetla wiersze dodawane do pliku. Funkcja ta była obecna w PowerShell v1, ale z jakiegoś powodu nie została dobrze udokumentowana w v2.

Oto przykład

Get-Content -Path "C:\scripts\test.txt" -Wait

Po uruchomieniu, zaktualizuj i zapisz plik, a zobaczysz zmiany na konsoli.

 377
Author: ravikanth,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-05 15:05:55

Dla kompletności wspomnę, że Powershell 3.0 ma teraz flagę-Tail Na Get-Content

Get-Content ./log.log -Tail 10

Pobiera ostatnie 10 linii pliku

Get-Content ./log.log -Wait -Tail 10

Pobiera ostatnie 10 linii pliku i czeka na więcej

 119
Author: George Mauer,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-13 20:48:18

W PowerShell w wersji 3.0 cmdlet Get-Content ma parametr -Tail, który powinien pomóc. Zobacz pomoc online biblioteki technet dla Get-Content.

 110
Author: Dan Blanchard,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-10-31 12:33:46

PowerShell Community Extensions (PSCX) zapewnia Get-FileTail cmdlet . Wygląda to na odpowiednie rozwiązanie dla zadania. Uwaga: nie próbowałem z bardzo dużymi plikami, ale opis mówi, że skutecznie ogarnia zawartość i jest przeznaczony do dużych plików dziennika.

NAME
    Get-FileTail

SYNOPSIS
    PSCX Cmdlet: Tails the contents of a file - optionally waiting on new content.

SYNTAX
    Get-FileTail [-Path] <String[]> [-Count <Int32>] [-Encoding <EncodingParameter>] [-LineTerminator <String>] [-Wait] [<CommonParameters>]

    Get-FileTail [-LiteralPath] <String[]> [-Count <Int32>] [-Encoding <EncodingParameter>] [-LineTerminator <String>] [-Wait] [<CommonParameters>]

DESCRIPTION
    This implentation efficiently tails the cotents of a file by reading lines from the end rather then processing the entire file. This behavior is crucial for ef
    ficiently tailing large log files and large log files over a network.  You can also specify the Wait parameter to have the cmdlet wait and display new content
    as it is written to the file.  Use Ctrl+C to break out of the wait loop.  Note that if an encoding is not specified, the cmdlet will attempt to auto-detect the
     encoding by reading the first character from the file. If no character haven't been written to the file yet, the cmdlet will default to using Unicode encoding
    . You can override this behavior by explicitly specifying the encoding via the Encoding parameter.
 17
Author: Roman Kuzmin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-06-23 14:42:41

Użyłem niektórych odpowiedzi podanych tutaj, ale tylko ostrzeżenie, że

Get-Content -Path Yourfile.log -Tail 30 -Wait 

Będzie przeżuwać pamięć po jakimś czasie. Kolega zostawił taki" ogon " w ciągu ostatniego dnia i poszedł do 800 MB. Nie wiem, czy uniksowy ogon zachowuje się tak samo (ale wątpię). Jest więc w porządku używać do zastosowań krótkoterminowych, ale uważaj na to.

 15
Author: John Lockwood,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-05-23 15:08:34

Tylko kilka dodatków do poprzednich odpowiedzi. Istnieją aliasy zdefiniowane dla Get-Content, na przykład jeśli używasz Uniksa, możesz polubić cat, a także type i gc. Więc zamiast

Get-Content -Path <Path> -Wait -Tail 10

Możesz napisać

# Print whole file and wait for appended lines and print them
cat <Path> -Wait
# Print last 10 lines and wait for appended lines and print them
cat <Path> -Tail 10 -Wait
 13
Author: Mikael Sundberg,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-06-08 08:08:34

Wziąłem rozwiązanie @ hajamie i owinąłem je w nieco wygodniejszy skrypt.

Dodałem opcję rozpoczynania od offsetu przed końcem pliku, dzięki czemu można korzystać z funkcji tail-like odczytu pewnej ilości z końca pliku. Uwaga przesunięcie jest w bajtach, a nie w liniach.

Istnieje również opcja dalszego oczekiwania na więcej treści.

Przykłady (zakładając, że zapiszesz to jako TailFile. ps1):

.\TailFile.ps1 -File .\path\to\myfile.log -InitialOffset 1000000
.\TailFile.ps1 -File .\path\to\myfile.log -InitialOffset 1000000 -Follow:$true
.\TailFile.ps1 -File .\path\to\myfile.log -Follow:$true

A oto skrypt siebie...

param (
    [Parameter(Mandatory=$true,HelpMessage="Enter the path to a file to tail")][string]$File = "",
    [Parameter(Mandatory=$true,HelpMessage="Enter the number of bytes from the end of the file")][int]$InitialOffset = 10248,
    [Parameter(Mandatory=$false,HelpMessage="Continuing monitoring the file for new additions?")][boolean]$Follow = $false
)

$ci = get-childitem $File
$fullName = $ci.FullName

$reader = new-object System.IO.StreamReader(New-Object IO.FileStream($fullName, [System.IO.FileMode]::Open, [System.IO.FileAccess]::Read, [IO.FileShare]::ReadWrite))
#start at the end of the file
$lastMaxOffset = $reader.BaseStream.Length - $InitialOffset

while ($true)
{
    #if the file size has not changed, idle
    if ($reader.BaseStream.Length -ge $lastMaxOffset) {
        #seek to the last max offset
        $reader.BaseStream.Seek($lastMaxOffset, [System.IO.SeekOrigin]::Begin) | out-null

        #read out of the file until the EOF
        $line = ""
        while (($line = $reader.ReadLine()) -ne $null) {
            write-output $line
        }

        #update the last max offset
        $lastMaxOffset = $reader.BaseStream.Position
    }

    if($Follow){
        Start-Sleep -m 100
    } else {
        break;
    }
}
 3
Author: Brian Reischl,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-06-11 16:10:23

Używając Powershell V2 i poniżej, get-content odczytuje cały plik, więc mi się nie przydał. Poniższy kod działa na to, czego potrzebowałem, chociaż prawdopodobnie są pewne problemy z kodowaniem znaków. W rzeczywistości jest to tail-f, ale można go łatwo zmodyfikować, aby uzyskać Ostatnie x bajty lub ostatnie x linii, jeśli chcesz szukać podziałów linii wstecz.

$filename = "\wherever\your\file\is.txt"
$reader = new-object System.IO.StreamReader(New-Object IO.FileStream($filename, [System.IO.FileMode]::Open, [System.IO.FileAccess]::Read, [IO.FileShare]::ReadWrite))
#start at the end of the file
$lastMaxOffset = $reader.BaseStream.Length

while ($true)
{
    Start-Sleep -m 100

    #if the file size has not changed, idle
    if ($reader.BaseStream.Length -eq $lastMaxOffset) {
        continue;
    }

    #seek to the last max offset
    $reader.BaseStream.Seek($lastMaxOffset, [System.IO.SeekOrigin]::Begin) | out-null

    #read out of the file until the EOF
    $line = ""
    while (($line = $reader.ReadLine()) -ne $null) {
        write-output $line
    }

    #update the last max offset
    $lastMaxOffset = $reader.BaseStream.Position
}

Większość kodu do tego znalazłem tutaj .

 2
Author: hajamie,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-17 16:05:34

Bardzo prosty, ale robi to, czego potrzebujesz, bez żadnych modułów dodatkowych lub wymagań wersji PS:

while ($true) {Clear-Host; gc E:\test.txt | select -last 3; sleep 2 }

 1
Author: Jesse,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-12-24 03:10:52

Try Windows Server 2003 Resource Kit Tools

Zawiera tail.exe, które można uruchomić w systemie Windows.

Https://www.microsoft.com/en-us/download/details.aspx?id=17657

 0
Author: starshine wang,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-11-22 09:14:43