遭遇したエラー

1#1690 - BIGINT UNSIGNED value is out of range in '(`after` - `before`)';

経緯

ポイントを管理するテーブルで 「キャンペーン中に増加したポイント数」 を集計したかった。

キャンペーン前の所持ポイントを before、 キャンペーン後の所持ポイントを after、

というカラムに入れ、キャンペーンでのポイント獲得数を diff カラムに保存しようとした。

実行した SQL はこちら。

1UPDATE `hoge` SET `diff` = `after` - `before`;

エラーの意味

after - before の計算結果が BIGINT UNSIGNED の扱える範囲にありませんよ、ということ。

BIGINT の最大値は次のとおりです。

bigint -9223372036854775808 9223372036854775807
bigint(unsigned) 0 18446744073709551615

なに、そんなにたくさんポイントを稼いだ人ががいるのか ?

と思いましたが、そうではありませんでした。


diff カラムは unsigned 、つまり符号なしでマイナスを扱うことができない型にしていました。

しかし after - before でマイナスになるケースがあったため、エラーになっていたのです。

このテーブルは 「増加のみで減らない」 と思いこんでいましたが、 実は「ポイント交換を行うと減少する」、ということがわかりました。

キャンペーン中にポイント交換を行った結果、キャンペーン開始前より、キャンペーン後のほうがポイントが少なくなるケースが有ったということでした。

わかってしまうと、何ということもないエラーでした。 反省です。

基礎からのMySQL 第3版

西沢 夢路
出版社:SBクリエイティブ 

Amazonで詳細を見る