3.6.0pre1 PATCH: fix searching of days

Hi,

I noticed that when searching for tickets that have a due date on a given
date, the searched date is wrong by one day.
The problem lies in the timezone handling and how the range for the day
is calculated.

In Tickets_Overlay.pm there is the following code:

if we’re specifying =, that means we want everything on a

particular single day. in the database, we need to check for >

and < the edges of that day.

my $daystart = strftime( “%Y-%m-%d %H:%M”,
gmtime( $time - ( $time % 86400 ) ) );
my $dayend = strftime( “%Y-%m-%d %H:%M”,
gmtime( $time + ( 86399 - $time % 86400 ) ) );

Note that when you enter a date, it is parsed in the local time zone (which is
a good thing to do) and, unless you specify it, the time is set to 00:00:00.

So, if you search for 2006-04-14 in my timezone (+0200), it will be parsed as
2006-04-14 00:00:00 +0200. The Unix time is however stored in UTC, so
internally it is 2006-04-13 22:00:00 +0000. Using the above formulas, it gives:

daystart = 2006-04-13 00:00:00 +0000
dayend = 2006-04-13 23:59:59 +0000

… which is not what I expect when searching.

The attached patch fixes this problem.

Cheers
David

PS: Even better would be not to use the Unix time directly but instead
use a module like Date::Calc.
David Schweikert | phone: +41 44 632 7019
System manager ISG.EE | walk: ETH Zentrum, ETL F24.1
ETH Zurich, Switzerland | web: http://people.ee.ethz.ch/dws

Tickets_Overlay.pm.patch (931 Bytes)

David Schweikert wrote:

Hi,

I noticed that when searching for tickets that have a due date on a given
date, the searched date is wrong by one day.
The problem lies in the timezone handling and how the range for the day
is calculated.

Looking through the backlog, the reason I didn’t end up applying this
patch is due to the use of localtime(). Instead, it should use RT::Date,
as in RT 3.7, RT::Date should automatically handle the timezone
conversion to do the right thing for you. (Ruz, can you confirm that?)

Jesse

signature.asc (191 Bytes)

David Schweikert wrote:

Hi,

I noticed that when searching for tickets that have a due date on a given
date, the searched date is wrong by one day.
The problem lies in the timezone handling and how the range for the day
is calculated.

Looking through the backlog, the reason I didn’t end up applying this
patch is due to the use of localtime(). Instead, it should use RT::Date,
as in RT 3.7, RT::Date should automatically handle the timezone
conversion to do the right thing for you. (Ruz, can you confirm that?)
RT::Date has no interface for this even in 3.7. I suggested
SetToLocalMidnight several years ago:
http://marc.theaimsgroup.com/?t=107073178300004&r=1&w=2, but thread
end up with workaround for real problem. 3.7 branch has code to get
date in different timezone contexts: user, server and UTC, but set*
methods still use old magic assumptions about input data.

See comments about the patch below:

Jesse

In Tickets_Overlay.pm there is the following code:

if we’re specifying =, that means we want everything on a

particular single day. in the database, we need to check for >

and < the edges of that day.

my $daystart = strftime( “%Y-%m-%d %H:%M”,
gmtime( $time - ( $time % 86400 ) ) );
my $dayend = strftime( “%Y-%m-%d %H:%M”,
gmtime( $time + ( 86399 - $time % 86400 ) ) );

Note that when you enter a date, it is parsed in the local time zone (which is
a good thing to do) and, unless you specify it, the time is set to 00:00:00.

So, if you search for 2006-04-14 in my timezone (+0200), it will be parsed as
2006-04-14 00:00:00 +0200. The Unix time is however stored in UTC, so
Unix time has no timezone information, it’s number of seconds passed
since 1970-01-01 00:00, but you can tie the number to the timezone
when you call gmtime or localtime functions.

internally it is 2006-04-13 22:00:00 +0000. Using the above formulas, it gives:

daystart = 2006-04-13 00:00:00 +0000
dayend = 2006-04-13 23:59:59 +0000

… which is not what I expect when searching.
Yep, above formulas use GMT timezone to get start and end of the day
and it’s not what users expect.

The attached patch fixes this problem.

[snip]

I don’t think this patch should be applied, it’s a little bit hacky,
uses lazy date/time calcualtions, I would suggest attached patch as
equivalent that’s more descriptive and has comments that clarifies
SetToLocalMidnight block. I don’t think this method should be
introduced in RT-3.4 or 3.5, but in 3.7 I would like to implement
timezone context argument for all Set* methods, so it would be
possible to run something like $date->SetToMidnight( timezone =>
‘user’ ).

Best regards, Ruslan.

3.4-search_on_dates.patch (1.77 KB)