We've got some scripts that run inside of scheduled tasks that send us email alerts to remind us to take action on some things in our environment daily. I'd like to prefix the script(s) with logic to determine if today is a company observed holiday and not send the email if it is, because no one wants to think about work on a holiday! Here's what I've come up with.
I'm only running the code if today is not a weekend day. I'm creating an array with a list of set holidays that don't vary. I'm then checking to see if today is one of those set holidays and if it is then I return true. If it's not a set holiday, I'm then checking to see if it's a holiday that varies like Memorial, Labor, and Thanksgiving days. Last, I'm checking to see if it's Friday or Monday, and if it is - check to see if a set holiday falls on the weekend and is therefore observed a day early or a day late.
<#
Company Holidays:
• New Year’s Day – 1st day of January
• Memorial Day – Last Monday in May
• Independence Day – 4th day of July
• Labor Day – 1st Monday in September
• Thanksgiving Day – 4th Thursday in November
• Christmas Day – 25th day of December
Day of Observance: A holiday will be observed on the holiday itself, except when the following conditions apply:
1. A holiday falling on a Saturday will be observed on the preceding Friday.
2. A holiday falling on Sunday will be observed on the following Monday.
#>
#We already know it's not a weekend because this code is only invoked if the day of the week does not start with S*.
function fn-get-variable-holiday ($Month, $DayofWeek, $DayofMonth, $IsHoliday)
{
if ($Month -eq 5)
{
if ($DayofWeek -eq 'Monday' -and $DayofMonth -ge 25)
{
#it's the first Monday of September, Labor Day
$IsHoliday = $true
Return $IsHoliday
Break
}
}
if ($Month -eq 9)
{
if ($DayofWeek -eq 'Monday' -and $DayofMonth -le 7)
{
#it's the first Monday of September, Labor Day
$IsHoliday = $true
Return $IsHoliday
Break
}
}
if ($Month -eq 11)
{
if ($DayofWeek -eq 'Thursday' -and ($DayofMonth -ge 22 -and ($DayofMonth -le 28)))
{
#it's the fourth Thursday of November, Thanksgiving Day
$IsHoliday = $true
Return $IsHoliday
}
}
}
Function fn-get-weekend-set-holiday ($DayofWeek, $DayofMonth, $IsHoliday) {
if ($DayofWeek -eq 'Monday') #Check to see if yesterday was a Holiday that we observe today
{
$IsHoliday = fn-get-set-holiday -Today $Today.AddDays(-1)
}
elseif ($DayofWeek -eq 'Friday') #Check to see if tomorrow is a Holiday that we observe today
{
$IsHoliday = fn-get-set-holiday -Today $Today.AddDays(1)
}
Return $IsHoliday
}
Function fn-get-set-holiday ($Today, $SetHolidays, $IsHoliday)
{
$SetHolidays = @("01/01","07/04","12/25")
foreach ($H in $SetHolidays)
{
if ($today -like "*$H*")
{
$IsHoliday = $true
Return $IsHoliday
Break
}
}
}
Function Main
{
#$Today = Get-Date
$Today = (Get-Date).AddDays(67)
$IsHoliday = $false
Write-Host "`nToday is $($Today.ToLongDateString())..."
if (fn-get-set-holiday -Today $Today -SetHolidays $SetHolidays -IsHoliday $IsHoliday)
{
Write-Host "It's a set holiday"
Return $true
}
elseif (fn-get-variable-holiday -Month $Today.Month -DayofWeek $today.DayOfWeek -DayofMonth $Today.Day -IsHoliday $IsHoliday)
{
Write-Host "It's a variable holiday"
Return $true
}
elseif (fn-get-weekend-holiday -DayofWeek $today.DayOfWeek -DayofMonth $Today.Day -IsHoliday $IsHoliday)
{
Write-Host "It's a weekend holiday"
Return $true
}
}
Main
I expect the script to output True if today is the observance of a holiday, and nothing if it is not.
Feel free to provide feedback on how to improve the script for syntax or efficiency.