using System.Collections.Generic;
public static class Program
public static void Main()
List<string> inputDatesPST = new List<string>{
"2024-02-19 6:00:00 AM","2024-02-19 6:00:00 PM",
"2024-02-20 6:00:00 AM","2024-02-20 6:00:00 PM",
"2024-02-21 6:00:00 AM","2024-02-21 6:00:00 PM",
"2024-02-22 6:00:00 AM","2024-02-22 6:00:00 PM",
"2024-02-23 6:00:00 AM","2024-02-23 6:00:00 PM",
"2024-02-24 6:00:00 AM","2024-02-24 6:00:00 PM",
"2024-02-25 6:00:00 AM","2024-02-25 6:00:00 PM"};
foreach(var inputDatePSTStr in inputDatesPST) {
var inputDatePST = DateTime.Parse(inputDatePSTStr);
var inputDateUTC = inputDatePST.AddHours(8);
var timeOfDayStr = "07:30:00";
Console.WriteLine("release timeOfDayPST 11:30:00 PM PST");
bool? ruleIncludeWeekends = null;
Console.WriteLine("delayDays "+delayDays);
Console.WriteLine("-----------------");
Console.WriteLine("For PST position creation date " + inputDatePST +" PST " +inputDatePST.DayOfWeek);
Console.WriteLine("-----------------");
var timeOfDay = TimeSpan.Parse(timeOfDayStr);
var releaseDateUTC = CalculateRuleEffectiveDate(inputDateUTC, delayDays, ruleIncludeWeekends, timeOfDay);
var releaseDateUTCNew = CalculateRuleEffectiveDateExcludeUSAWeekends(inputDateUTC, delayDays, ruleIncludeWeekends, timeOfDay);
var releaseDatePST = releaseDateUTC.AddHours(-8);
var releaseDatePSTNew = releaseDateUTCNew.AddHours(-8);
Console.WriteLine("Old Release Date would be " + releaseDatePST +" PST "+ releaseDatePST.DayOfWeek);
Console.WriteLine("New Release Date with USA weekends excluded would be " + releaseDateUTCNew +" PST "+ releaseDateUTCNew.DayOfWeek);
Console.WriteLine("-------------------------------------------------------------------------------------");
public static DateTime CalculateRuleEffectiveDate(DateTime date, int? ruleDelayDays, bool? ruleIncludeWeekends, TimeSpan? ruleTimeOfDay)
var ruleEffectiveDate = date;
var isImmediate = ruleDelayDays == null;
var includeWeekends = ruleIncludeWeekends.HasValue ? ruleIncludeWeekends.Value : isImmediate;
while (ruleEffectiveDate.Date.IsWeekend() && !includeWeekends)
ruleEffectiveDate = ruleEffectiveDate.Date.AddDays(1);
if (ruleDelayDays != null && ruleTimeOfDay != null)
var delayDays = ruleDelayDays.Value;
if (ruleEffectiveDate.TimeOfDay > ruleTimeOfDay.Value)
ruleEffectiveDate = ruleEffectiveDate.Date.AddDays(delayDays)
.Add(ruleTimeOfDay.Value);
ruleEffectiveDate = ruleEffectiveDate.Date.AddBusinessDays(delayDays)
.Add(ruleTimeOfDay.Value);
return ruleEffectiveDate;
public static DateTime CalculateRuleEffectiveDateExcludeUSAWeekends(DateTime date, int? ruleDelayDays, bool? ruleIncludeWeekends, TimeSpan? ruleTimeOfDay)
var ruleEffectiveDateUTC = date;
var isImmediate = ruleDelayDays == null;
var includeWeekends = ruleIncludeWeekends ?? isImmediate;
while (ruleEffectiveDateUTC.Date.IsWeekend() && !includeWeekends)
ruleEffectiveDateUTC = ruleEffectiveDateUTC.Date.AddDays(1);
TimeZoneInfo pacificTimeZone = TimeZoneInfo.FindSystemTimeZoneById("Pacific Standard Time");
DateTime ruleEffectiveDatePST = TimeZoneInfo.ConvertTimeFromUtc(ruleEffectiveDateUTC, pacificTimeZone);
if (ruleDelayDays != null && ruleTimeOfDay != null)
var delayDays = ruleDelayDays.Value;
DateTime effectiveRuleReleaseDateUTC = ruleEffectiveDateUTC.Date.Add(ruleTimeOfDay.Value);
DateTime effectiveRuleReleaseDatePST = TimeZoneInfo.ConvertTimeFromUtc(effectiveRuleReleaseDateUTC, pacificTimeZone);
Console.WriteLine("ruleEffectiveDateUTC "+ruleEffectiveDateUTC);
Console.WriteLine("effectiveRuleReleaseDateUTC "+effectiveRuleReleaseDateUTC);
Console.WriteLine("-------");
Console.WriteLine("ruleEffectiveDatePST "+ruleEffectiveDatePST);
Console.WriteLine("effectiveRuleReleaseDatePST "+effectiveRuleReleaseDatePST);
Console.WriteLine("-------");
if (ruleEffectiveDatePST.TimeOfDay > effectiveRuleReleaseDatePST.TimeOfDay) {
Console.WriteLine("Add 1 day \n");
ruleEffectiveDateUTC = ruleEffectiveDatePST.Date.AddDays(delayDays)
.Add(effectiveRuleReleaseDatePST.TimeOfDay);
ruleEffectiveDatePST = ruleEffectiveDatePST.Date.AddBusinessDays(delayDays)
.Add(effectiveRuleReleaseDatePST.TimeOfDay);
while (IsWithinUSAWeekendRange(ruleEffectiveDatePST))
ruleEffectiveDatePST = ruleEffectiveDatePST.Date.AddDays(1).Add(ruleTimeOfDay.Value);
return ruleEffectiveDatePST;
private static bool IsWithinUSAWeekendRange(DateTime utcDate)
Console.WriteLine("IsWithinUSAWeekendRange input utcDate " + utcDate + ' ' + utcDate.DayOfWeek);
var weekendStart = DayOfWeek.Saturday;
var weekendEnd = DayOfWeek.Monday;
var startTime = TimeSpan.FromHours(5);
var endTime = TimeSpan.FromHours(7) + TimeSpan.FromMinutes(59);
if (utcDate.DayOfWeek == weekendStart && utcDate.TimeOfDay >= startTime)
Console.WriteLine("YES it's a weekend on Saturday \n");
else if (utcDate.DayOfWeek == weekendEnd && utcDate.TimeOfDay < endTime)
Console.WriteLine("YES it's a weekend on Monday \n");
else if (utcDate.DayOfWeek == DayOfWeek.Sunday)
Console.WriteLine("YES it's a weekend on Sunday \n");
Console.WriteLine("NO not a weekend \n");
public static bool IsWeekend(this DateTime date)
return date.DayOfWeek == DayOfWeek.Saturday || date.DayOfWeek == DayOfWeek.Sunday;
public static bool IsHoliday(this DateTime date)
public static DateTime AddBusinessDays(this DateTime date, int days)
int direction = days < 0 ? -1 : 1;
newDate = newDate.AddDays(direction);
if (!newDate.IsWeekend() && !newDate.IsHoliday())