I have a bit of a unique problem in that my quartz job scheduler implementation which build using the quartz.net code base ver 2.0.1, recently discovered that the time zone and utc offsets are being ignored while running and executing jobs. This is an inherit bug in this version of quartz.net and updating to version 2.1.1 is out of scope right now, so I wrote a quick and dirty way of calculating the offset using this algorithm:
(ServerTime - ClientTime) - TargetTime = New_TargetTime_With_Offset
The idea here is the client, who is say in NYC, makes a job at 5:00pm and wants it to run at 2:00pm. The Server (where this app and the job server runs) current time is 2:00pm, so we take the client time and server time to get the offset and apply that offset to the target time, which is the time the job should run.
My question is that this feels like a round about way of calculating the dates, but seems like it would do the job. Is there a better / more reliable way of doing this date math? Also this seems to be buggy in edge cases, what am I missing?
Here is the implementation:
/// <summary>
/// Takes three dates and returns the adjusted hour value.
/// All date data is ignored except for the hour.
/// </summary>
/// <param name="serverTime"></param>
/// <param name="clientTime"></param>
/// <param name="targetTime"></param>
/// <returns></returns>
private static DateTime OutputDate(DateTime serverTime, DateTime clientTime, DateTime targetTime)
{
DateTime? output = null;
TimeSpan? dateDiff;
if (serverTime < clientTime)
{
dateDiff = (clientTime - serverTime);
}
else
{
dateDiff = (serverTime - clientTime);
}
output = (targetTime - dateDiff);
return output.Value;
}
and here are two examples of leveraging it:
/// <summary>
/// -5 Offset (NYC)
/// </summary>
/// <returns></returns>
private static Int32 ZoneTest001()
{
var targetTime = DateTime.Parse("6/12/2013 5:00PM"); // NYC (est) [The time the report should be received in NYC]
var clientTime = DateTime.Parse("6/12/2013 5:00PM"); // NYC (est) [The time of the client when the report is created (now) ]
var serverTime = DateTime.Parse("6/12/2013 2:00PM"); // SEA (pst) [The time of the app server when the report is created (now) ]
//
// NYC Wants to send a report at 5:00pm EST
// The server time will be 2:00pm PST
// The client time will be 5:00pm EST
double outputHour = 0; // should end up as 2:00pm PST
//
// 1) Get offset (diff between client & server time)
// 2) Subtract offset from "targetTime"
// 3) Set the report to be sent at the new hour value.
outputHour = OutputDate(serverTime, clientTime, targetTime).Hour;
return (int)outputHour;
}
/// <summary>
/// +5 Offset (India)
/// </summary>
/// <returns></returns>
private static Int32 ZoneTest002()
{
var targetTime = DateTime.Parse("6/12/2013 5:00PM"); // IND (ist)
var clientTime = DateTime.Parse("6/12/2013 9:00AM"); // IND (ist)
var serverTime = DateTime.Parse("6/12/2013 2:00PM"); // SEA (pst)
//
// INDIA Wants to send a report at 5:00pm IST
// The server time will be 2:00pm PST
// The client time will be 9:00am PST
double outputHour = 0; // should end up as 2:00pm PST
outputHour = OutputDate(serverTime, clientTime, targetTime).Hour;
return (int)outputHour;
}
Thank you.