You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PowerShell write-Log函数优化:日志归档与旧日志管理需求

PowerShell Log Function with Auto-Archiving

Alright, let's tackle this log rotation problem for your PowerShell script. Your current write-Log function appends to the log file, but you want to archive old logs to a subfolder with incrementing names while keeping the latest log in the script directory. Here's the revised solution with explanations:

Updated Code

First, set up your log variables and initialize a flag to prevent repeated archiving during the same script run:

# Log Variables
$Logfile = "C:\Scripts\powershellscript\logs.log" # Main log file path
# Initialize a script-level flag to track if we've already archived old logs in this session
$script:logArchived = $false

Now here's the modified write-Log function with archiving logic:

function write-Log {
 Param (
 [Parameter(Mandatory = $false)] # Message to log
 $Message,
 [Parameter(Mandatory = $false)] # Error message (triggers Type 3)
 $ErrorMessage,
 [Parameter(Mandatory = $false)] # Component generating the log entry
 $Component,
 [Parameter(Mandatory = $false)] # Log entry type (1=Info, 3=Error)
 [int]$Type,
 [Parameter(Mandatory = $true)] # Path to the main log file
 $LogFile
 )

 # --- Auto-Archiving Logic (New) ---
 # Only run this once per script execution
 if (-not $script:logArchived) {
     # Derive the archive folder path from the main log's directory
     $archiveFolder = Join-Path -Path (Split-Path -Path $LogFile -Parent) -ChildPath "logfolder"

     # Create the archive folder if it doesn't exist
     if (-not (Test-Path -Path $archiveFolder)) {
         New-Item -ItemType Directory -Path $archiveFolder | Out-Null
     }

     # If the main log file exists (from a previous script run), archive it
     if (Test-Path -Path $LogFile) {
         # Get all existing archived logs to find the next increment number
         $existingArchives = Get-ChildItem -Path $archiveFolder -Filter "logs*.log.old" | Sort-Object Name -Descending
         $nextArchiveNumber = 1

         # Extract the highest existing number to increment
         if ($existingArchives.Count -gt 0) {
             $latestArchive = $existingArchives[0].Name
             if ($latestArchive -match 'logs(\d+)\.log\.old') {
                 $nextArchiveNumber = [int]$matches[1] + 1
             }
         }

         # Define the path for the new archived log
         $archivedLogPath = Join-Path -Path $archiveFolder -ChildPath "logs$nextArchiveNumber.log.old"
         # Move and rename the old log file
         Move-Item -Path $LogFile -Destination $archivedLogPath -Force
     }

     # Mark archiving as complete for this script session
     $script:logArchived = $true
 }

 # --- Original Log Writing Logic (Unchanged) ---
 # Create timestamp for the log entry
 $Date = Get-Date -Format "MM/dd/yyyy"
 $time = Get-Date -Format "HH:mm:ss.fff"

 # Auto-set type to Error if an ErrorMessage is provided
 if ($null -ne $ErrorMessage) {
     $Type = 3
 }
 # Default component to empty space if not specified
 if ($null -eq $Component) {
     $Component = " "
 }
 # Default type to Info if not specified
 if ($null -eq $Type) {
     $Type = 1
 }

 # Build the log entry in the existing format
 $LogMessage = "<![LOG[$Message $ErrorMessage ]LOG]!>" + "<time=`"$time`" date=`"$Date`" component=`"$Component`" context=`"`" type=`"$Type`" thread=`"`" file=`">"
 # Append the entry to the main log file
 $LogMessage | Out-File -Append -Encoding UTF8 -FilePath $LogFile
}

Key Improvements Explained

  • Single-Run Archiving: The $script:logArchived flag ensures old logs are only archived once per script execution. This prevents repeatedly moving the current log file every time you call write-Log.
  • Dynamic Archive Path: The archive folder (logfolder) is automatically created in the same directory as your main log file, so you don't need to hardcode paths.
  • Incrementing Naming: The function scans existing archived logs, extracts the highest number, and increments it for the new archive (e.g., logs1.log.old → logs2.log.old).
  • Backward Compatibility: All your existing calls to write-Log will work exactly as before—no need to modify how you pass parameters.

How It Works

  1. When you first call write-Log in your script, it checks if the main log file exists (from a prior run).
  2. If it exists, it finds the next available increment number for archived logs.
  3. It moves the old log to logfolder with the incremented name.
  4. It then proceeds to write new log entries to the fresh main log file.
  5. Subsequent calls to write-Log during the same script run skip the archiving step and just append to the current log.

内容的提问来源于stack exchange,提问作者StackLad

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.08 11:47:27