LoginSignup
5
5

More than 5 years have passed since last update.

MySQL 5.6 の時間式の限界について

Last updated at Posted at 2016-06-21

概要

  • MySQL 5.6.26 では時間式の限界は 34 22:59:59 のようです。
    • リファレンス838:59:59 の記載があるため、その通りの挙動です。
  • INTERVAL 35 DAY とかで回避。

再現した環境

MySQL 5.6.19 と 5.6.26 と 5.6.30

起きた事

MySQL の datetime 型から SUBTIME 関数で引き算をやろうとした結果、Python-MySQL から _mysql_exceptions.Warning: Truncated incorrect time value: '60 00:00' と怒られました。MySQL クライアントで直接入力してる限りエラーは見当たらないんだけど・・・と思っていたのですが、中身をよく見るとおかしなことが起きていました。

SELECT SUBTIME('2007-12-31 00:00:00', '60 00:00');
+--------------------------------------------+
| SUBTIME('2007-12-31 00:00:00', '60 00:00') |
+--------------------------------------------+
| 2007-11-26 01:00:01                        |
+--------------------------------------------+
1 row in set, 1 warning (0.00 sec)

ここで求められる正解は 2007-11-01 00:00:00 のはずだけど、実際には 2007-11-26 01:00:01 が返却されている。

ここで MySQL の関数リファレンスを調べると

SUBTIME(expr1,expr2)

SUBTIME() は、expr1 と同じ書式で表現される expr1 と expr2 を返します。expr1 は時間または日付時間式であり、expr2 は時間式です。

とありますが、時間式とされている方に限界がありそうです。恐らく '34 22:59:59' が限界。

SELECT SUBTIME('2007-12-31 00:00:00', '34 22:00');
SELECT SUBTIME('2007-12-31 00:00:00', '34 23:00');
+--------------------------------------------+
| SUBTIME('2007-12-31 00:00:00', '34 22:00') |
+--------------------------------------------+
| 2007-11-26 02:00:00                        |
+--------------------------------------------+
1 row in set (0.00 sec)

+--------------------------------------------+
| SUBTIME('2007-12-31 00:00:00', '34 23:00') |
+--------------------------------------------+
| 2007-11-26 01:00:01                        |
+--------------------------------------------+
1 row in set, 1 warning (0.00 sec)

概ね想定通りの結果です。せっかくなので足し算も試してみよう

SELECT ADDTIME('2007-12-31 00:00:00', '60 00:00');
+--------------------------------------------+
| ADDTIME('2007-12-31 00:00:00', '60 00:00') |
+--------------------------------------------+
| 2008-02-03 22:59:59                        |
+--------------------------------------------+
1 row in set, 1 warning (0.00 sec)

そうなると思ってた。ADDTIMESUBTIME に問題があるのではなくて、expr2 の方に入るべき時間式の方に問題がありそう。

追記

コメント欄で教えていただきました。TIME型のリファレンス にバッチリ記載されています。

TIME 値の範囲は、'-838:59:59' から '838:59:59' です

rryu さんありがとうございます。

どうやって回避するか?

INTERVAL でチマチマ回避することにします。

SELECT '2007-12-31 00:00:00' - INTERVAL 60 DAY;

+-----------------------------------------+
| '2007-12-31 00:00:00' - INTERVAL 60 DAY |
+-----------------------------------------+
| 2007-11-01 00:00:00                     |
+-----------------------------------------+
1 row in set (0.01 sec)

問題ない。

5
5
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
5