PS 2.0 – Remove and compress IIS logs automatically


I created a PS script for removing and compressing IIS log files.

Description

  • Define variables: the log folder $LogFolder (basically it could be %SYSTEMROOT%\System32\LogFiles\W3SVC) and the retention periods ($DeletionRetention = -120, $CompressionRetention = -60).
  • Scripts handles only files with expired retention for attribute LastWriteTime  (e.g. -120 = older than 120 days).
  • It deletes all* files with expired retention ($DeletionRetention) from the log folder. (* Be careful, the folder doesn’t have to contain only logs.)
  • It compresses log files with expired retention ($CompressionRetention) into one zip based on month number from LastWriteTime (IISLogs-Month2-2502132135.zip). Number 2502132135 is the time stamp.
  • The script can be simply scheduled via Windows Task Scheduler if needed (e.g. Trigger: Monthly – last day).HowToScheduleScript

Note

I used in my script zip functions from David Aiken – Compress Files with Windows PowerShell then package a Windows Vista Sidebar Gadget

Script

# VARIABLES
$LogPath = "D:\IISLogs"
$DeletionRetention = -120
$CompressionRetention = -60

# FUNCTIONS
function New-Zip
{
 param([string]$zipfilename)
 set-content $zipfilename ("PK" + [char]5 + [char]6 + ("$([char]0)" * 18))
 (dir $zipfilename).IsReadOnly = $false
}

function Add-Zip
{
 param([string]$zipfilename)

 if(-not (test-path($zipfilename)))
 {
 set-content $zipfilename ("PK" + [char]5 + [char]6 + ("$([char]0)" * 18))
 (dir $zipfilename).IsReadOnly = $false 
 }

 $shellApplication = new-object -com shell.application
 $zipPackage = $shellApplication.NameSpace($zipfilename)

 foreach($file in $input) 
 { 
 $zipPackage.CopyHere($file.FullName)
 Start-sleep -milliseconds 500
 }
}

function Get-Zip
{
 param([string]$zipfilename)
 if(test-path($zipfilename))
 {
 $shellApplication = new-object -com shell.application
 $zipPackage = $shellApplication.NameSpace($zipfilename)
 $zipPackage.Items() | Select Path
 }
}

# MAIN SCRIPT
$Items = get-childitem $LogPath

$DeleteLogs = $Items | ? {$_.LastWriteTime -le (Get-Date).adddays($DeletionRetention)}
if($DeleteLogs -ne $null) { $DeleteLogs | %{Remove-Item $_.fullname}}

$Items = get-childitem $LogPath |? {($_.extension -like "*.log") -and ($_.LastWriteTime -le (Get-Date).adddays($CompressionRetention))}

$GroupedItems = $Items | sort LastWriteTime | select @{n='Month';e={$_.LastWriteTime.month}},fullname,length,name | group month

if($GroupedItems -ne $null){
 foreach ($GroupedItem in $GroupedItems){
 $MonthNumber = $GroupedItem.Name
 $Time = Get-Date -Format ddMMyyHHss
 $ZipPath = "$LogPath\IISLogs-Month$MonthNumber-$Time.zip"
 New-Zip $ZipPath
 $GroupedItem.group | select fullname,length | %{
 Get-Item $_.fullname | Add-Zip $ZipPath
 start-sleep -s ($_.Length/20000000)
 }
 if((Get-Zip $ZipPath).length -eq $GroupedItem.Count){
 $GroupedItem.group | %{Remove-Item $_.fullname}
 }else{
 Write-Host "`nERROR - Files are not zipped correctly. Deletion process skipped."
 $GroupedItem.group | %{$_.name}
 }
 }
}

Download

IISLog-Removing&Compressing-v1.ps1

https://skydrive.live.com/redir?resid=E3BA57A6A24B6F3C!137

Note

We can remove logs also by command Forfiles (thank you Lukas).

 

 

Advertisements

8 thoughts on “PS 2.0 – Remove and compress IIS logs automatically

  1. Hi cool script!

    But I have a little problem….
    My ISS Logs are stored in the following folders:
    C:\inetpub\logs\LogFiles\W3SVC1
    C:\inetpub\logs\LogFiles\W3SVC784858138
    C:\inetpub\logs\LogFiles\W3SVC910188213
    C:\inetpub\logs\LogFiles\W3SVC1235617185
    C:\inetpub\logs\LogFiles\W3SVC1263836887
    C:\inetpub\logs\LogFiles\W3SVC1297401274
    C:\inetpub\logs\LogFiles\W3SVC2032727181

    I tried this: $LogPath = “C:\inetpub\logs\LogFiles\” but it didnt work.

    how can I indicate multiple folders in the variable LOG PATH?
    Hopefully you can help me 🙂

    • Hello,
      you should use for get-childitem command parameter -recurse (gets the items in the specified locations and in all child items of the locations.):

      $LogPath = “C:\inetpub\logs\LogFiles\”
      $Items = get-childitem $LogPath -recurse

      In this case is needed to change also the following:
      $Items = $Items |? {($_.extension -like “*.log”) -and ($_.LastWriteTime -le (Get-Date).adddays($CompressionRetention))}

      Filip

      • hi Filip,

        thx for the fast response.
        I have my script updated with your code, but now I am getting this error:

        You cannot call a method on a null-valued expression.
        At D:\SharePoint\Script\IIS_Logs\IISLog-Removing-Compressing-v1.ps1:29 char:22
        + $zipPackage.CopyHere <<<< ($file.FullName)
        + CategoryInfo : InvalidOperation: (CopyHere:String) [], RuntimeException
        + FullyQualifiedErrorId : InvokeMethodOnNull

        The archive was created but it includes no files(logs).

        -Alex

      • Hi,
        if you run only these lines in PS runspace, shall variables $Items and $GroupedItems contain any data?
        $LogPath = “C:\inetpub\logs\LogFiles\”
        $Items = get-childitem $LogPath -recurse
        $Items = $Items |? {($_.extension -like “*.log”) -and ($_.LastWriteTime -le (Get-Date).adddays($CompressionRetention))}
        $GroupedItems = $Items | sort LastWriteTime | select @{n=’Month’;e={$_.LastWriteTime.month}},fullname,length,name | group month

        Variables can be shown by using:
        $Items
        $GroupedItems

        Filip

  2. hi,
    somehow i cannot press reply on your last post……..

    I run these lines in as a new script. Then i let me show the variables $Items and $GroupedItems.
    I got a list of all the logfiles($Items).
    And the variable $GroupedItems contains this:
    Count Name Group
    —– —- —–
    5 4 {@{Month=4; FullName=C:\TEMP\IIS_LOG_BAK2\LogFiles\W3SVC1297401274\u_ex1…
    138 5 {@{Month=5; FullName=C:\TEMP\IIS_LOG_BAK2\LogFiles\W3SVC1235617185\u_ex1…
    23 6 {@{Month=6; FullName=C:\TEMP\IIS_LOG_BAK2\LogFiles\W3SVC1263836887\u_ex1…

    Is that correct? I think it is.

    Alex

  3. I am using the CopyHere() Method to extract a file from the Archive. The script runs great using PowerShell directly and runs from the scheduled task. When running from scheduled task, the CopyHere() Method never extracts any files.

    Any thoughts?

    Brooks

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s