by Klaus Graefensteiner
10. April 2012 05:18
Introduction
This script selects a file based on a date string that is part of the filename. Once the date has been determined, the script tries to find out whether this file is the latest of the week that the date belongs to. The first part of the script generates some sample files and the second part filters out the correct files and copies them into the export folder.
_thumb.jpg)
Figure 1: The Orange County Great Park from a helium balloon
The script uses a regular expression to parse the date and hashtables for grouping the files weeks based on the parsed date.
Set-StrictMode -Version "latest"
$DebugPreference = "Continue"
Remove-Item -Path "E:\Archive" -Recurse -Force
New-Item -Path "E:\Archive\Export\Final" -Type "Directory"
$FinalFolder = "E:\Archive\Export\Final"
$ArchiveFolder = "E:\Archive\Export\"
function CreateArchiveFile($Prefix, $Date, $ArchiveFolder)
{
$FileName = "{0}{1:yyyyMMdd}.txt" -f $Prefix, $Date
Write-Debug "Debug $FileName"
$FilePath = Join-Path -Path $ArchiveFolder -ChildPath $FileName
New-Item -Path $FilePath -Type "File"
}
#Create Archive Files
$Today = Get-Date
$TwoMonthsAgo = $Today.AddMonths(-2)
$CurrentDay = $TwoMonthsAgo
while($CurrentDay -le $Today.AddDays(-1))
{
CreateArchiveFile -Prefix "ExportPrevious" -Date $CurrentDay -ArchiveFolder $ArchiveFolder
$CurrentDay = $CurrentDay.AddDays(1)
}
CreateArchiveFile -Prefix "ExportCurrent" -Date $CurrentDay -ArchiveFolder $ArchiveFolder
$Files = Get-ChildItem -Path $ArchiveFolder
$WeeklyFileTable = @{}
function ParseDateFromFileName($FileName)
{
$FileName -match '^(?<PREFIX>ExportPrevious|ExportCurrent)(?<YEAR>\d{4})(?<MONTH>\d{2})(?<DAY>\d{2}).txt$' | Out-Null
$Date = New-Object -TypeName "System.DateTime" -ArgumentList $matches.YEAR, $matches.MONTH, $matches.DAY, 0, 0, 0, 0
return $Date
}
function CopyWeeklyFiles($FileTable, $Destination)
{
$FileTable.GetEnumerator() | ForEach-Object { Write-Debug ($_.Value.FullName);Copy-Item -Path ($_.Value.Fullname) -Destination $Destination -Force }
}
function GetNextSaturday($CurrentDay)
{
$LastSaturdayTable = @{"Saturday"=0; "Friday"=1; "Thursday"=2; "Wednesday" = 3; "Tuesday" = 4; "Monday"=5; "Sunday" = 6}
$DaysToNextSaturday = $LastSaturdayTable[($CurrentDay.DayOfWeek).ToString()]
$NextSaturday = $CurrentDay.AddDays($DaysToNextSaturday)
return $NextSaturday
}
foreach($file in $files)
{
Write-Debug $file.Fullname
#ParseFileDate String -> DateTime
$Date = ParseDateFromFileName -FileName $file.name
$NextSaturday = GetNextSaturday -CurrentDay $Date
if($WeeklyFileTable[$NextSaturday] -ne $Null)
{
$LatestFile = $WeeklyFileTable[$NextSaturday]
$LatestFileDate = ParseDateFromFileName -FileName $LatestFile.name
if($Date -gt $LatestFileDate)
{
$WeeklyFileTable[$NextSaturday] = $file
}
}
else
{
$WeeklyFileTable[$NextSaturday] = $file
}
$NextSaturday
}
$WeeklyFileTable
CopyWeeklyFiles -FileTable $WeeklyFileTable -Destination $FinalFolder
Ausblick
I actually needed to write this function as part of a .NET C# project, but I used PowerShell to prototype the algorithm. The .NET C# version will be published in the next blog post. Stay tuned!