| Bug #28869 | Broken DATE and DATETIME comparisons | ||
|---|---|---|---|
| Submitted: | 4 Jun 2007 8:40 | Modified: | 5 Jun 2007 14:45 |
| Reporter: | Domas Mituzas | Email Updates: | |
| Status: | Duplicate | Impact on me: | |
| Category: | MySQL Server: Data Types | Severity: | S1 (Critical) |
| Version: | 5.0-bk, 5.1-bk | OS: | Any |
| Assigned to: | Assigned Account | CPU Architecture: | Any |
| Tags: | regression | ||
[4 Jun 2007 14:16]
Geert Vanderkelen
Other test case: Works fine in 5.0.41, but breaks in 5.0.42: CREATE TABLE `t1` ( `today` date default NULL ); mysql> INSERT INTO t1 VALUES (NOW()); Query OK, 1 row affected (0.00 sec) mysql> SELECT * FROM t1 WHERE today = NOW(); Empty set (0.01 sec) mysql> SELECT * FROM t1 WHERE today = CURDATE(); +------------+ | today | +------------+ | 2007-06-04 | +------------+
[5 Jun 2007 13:30]
Evgeny Potemkin
mysql> select
-> '2007-06-30' + interval 1 hour < cast('2007-07-05' as date),
-> '2007-06-30' + interval 1 hour < cast('2007-07-05' as date),
-> '2007-06-30' + interval 1 hour <= cast('2007-07-05' as date),
-> '2007-06-30' + interval 1 hour <= cast('2007-07-05' as datetime),
-> '2007-06-30' + interval 1 hour = cast('2007-07-05' as datetime),
-> '2007-06-30' + interval 1 hour = cast('2007-07-05' as date) \G
*************************** 1. row ***************************
'2007-06-30' + interval 1 hour < cast('2007-07-05' as date): 1
'2007-06-30' + interval 1 hour < cast('2007-07-05' as date): 1
'2007-06-30' + interval 1 hour <= cast('2007-07-05' as date): 1
'2007-06-30' + interval 1 hour <= cast('2007-07-05' as datetime): 1
'2007-06-30' + interval 1 hour = cast('2007-07-05' as datetime): 0
'2007-06-30' + interval 1 hour = cast('2007-07-05' as date): 0
1 row in set (0.00 sec)
mysql> select version();
+--------------+
| version() |
+--------------+
| 5.0.44-debug |
+--------------+
1 row in set (0.00 sec)
[5 Jun 2007 13:54]
Evgeny Potemkin
CREATE TABLE `t1` (`today` date default NULL); mysql> INSERT INTO t1 VALUES (NOW()); mysql> SELECT * FROM t1 WHERE today = NOW(); Empty set (0.01 sec) This is expected behaviour. You save DATETIME value in a DATE field and thus the TIME part gets stripped. DATE is treated as a DATETIME with zero TIME part i.e. DATE 00:00:00. NOW() returns DATETIME value with non-zero TIME part and obviously it's greater than the same DATE with zero TIME part. mysql> SELECT * FROM t1 WHERE today = CURDATE(); [1 row] It's correct as values are the same.
[5 Jun 2007 14:45]
Domas Mituzas
Apparently this bug is a duplicate of #21103
[6 Jun 2007 16:07]
Axel Schwenke
with latest bk (2007-06-06 18:00:00) I get now:
mysql> select
-> '2007-06-30' + interval 1 hour < cast('2007-07-05' as date),
-> '2007-06-30' + interval 1 hour < cast('2007-07-05' as date),
-> '2007-06-30' + interval 1 hour <= cast('2007-07-05' as date),
-> '2007-06-30' + interval 1 hour <= cast('2007-07-05' as datetime),
-> '2007-06-30' + interval 1 hour = cast('2007-07-05' as datetime),
-> '2007-06-30' + interval 1 hour = cast('2007-07-05' as date) \G
*************************** 1. row ***************************
'2007-06-30' + interval 1 hour < cast('2007-07-05' as date): 1
'2007-06-30' + interval 1 hour < cast('2007-07-05' as date): 1
'2007-06-30' + interval 1 hour <= cast('2007-07-05' as date): 1
'2007-06-30' + interval 1 hour <= cast('2007-07-05' as datetime): 1
'2007-06-30' + interval 1 hour = cast('2007-07-05' as datetime): 0
'2007-06-30' + interval 1 hour = cast('2007-07-05' as date): 0
1 row in set (0,00 sec)
[6 Jun 2007 16:17]
Axel Schwenke
However there is still the problem of comparing DATE columns with DATETIME literals: mysql> create table t1 (c1 date); insert into t1 values (now()); Query OK, 0 rows affected (0,01 sec) Query OK, 1 row affected (0,00 sec) mysql> select * from t1 where c1=now(); Empty set (0,00 sec) mysql> select * from t1 where c1=cast(now() as date); +------------+ | c1 | +------------+ | 2007-06-06 | +------------+ 1 row in set (0,02 sec)

Description: Datetime and Date comparison operations are broken: How to repeat: mysql> select '2007-06-30' + interval 1 hour < cast('2007-07-05' as date), '2007-06-30' + interval 1 hour < cast('2007-07-05' as date), '2007-06-30' + interval 1 hour <= cast('2007-07-05' as date), '2007-06-30' + interval 1 hour <= cast('2007-07-05' as datetime), '2007-06-30' + interval 1 hour = cast('2007-07-05' as datetime), '2007-06-30' + interval 1 hour = cast('2007-07-05' as date) \G *************************** 1. row *************************** '2007-06-30' + interval 1 hour < cast('2007-07-05' as date): 0 '2007-06-30' + interval 1 hour < cast('2007-07-05' as date): 0 '2007-06-30' + interval 1 hour <= cast('2007-07-05' as date): 1 '2007-06-30' + interval 1 hour <= cast('2007-07-05' as datetime): 1 '2007-06-30' + interval 1 hour = cast('2007-07-05' as datetime): 1 '2007-06-30' + interval 1 hour = cast('2007-07-05' as date): 1 1 row in set (0.00 sec) Suggested fix: This behavior could have been introduced by: * Comparison of a DATE with a DATETIME did not treat the DATE as having a time part of 00:00:00. (Bug#27590) * Comparisons of DATE or DATETIME values for the IN() function could yield incorrect results. (Bug#28133) (both in 5.0.40) It is a REGRESSION that appeared in 5.0.42