djangoモデルのIntegerField上限値に関するコラム

スポンサードリンク



こんにちは。sinyです。

この記事では、DjangoのIntegerFieldモデルフィールドの上限値に関する注意点についてのまとめ記事です。

一般的にDjangoで数値型のモデルフィールドを定義する場合はIntegerFieldを使うと思います。

以下のような簡単な製品マスターテーブルを例にして説明します。

class Product(models.Model):

    class Meta:
        #カテゴリ
        verbose_name ="製品マスター"
        verbose_name_plural ="製品マスター"
      
#カラム名の定義
    product_name = models.CharField(max_length=255)
    jancode = models.IntegerField("janコード")

 

上記例では、製品を一意に特定するためのカラムjancodeを数値型(IntegerField)で定義しています。
一般的なJanコードは13桁の数値です。
一方、DjangoのIntegerFiledの幅は-2147483648 ~ 2147483647(=MAX10桁)となっています。(下記リンク参照)

 

ここで疑問なのですが、DjangoのIntegerFiledフィールドの仕様は-2147483648 ~ 2147483647なのに上記モデル定義をマイグレーションしてadmin画面で13桁のjancodeを登録すると普通に登録できてしまいます。

 IntegerFieldなのになぜ13桁の数字が登録できてしまうか?の理由がよくわからないので、もしご存知の方がいましたら共有いただけると助かります。

 

ここで本記事のメインポイントになりますが、別環境DBに登録済みの13桁のjancodeを含むレコードをpython manage.py dumpdataコマンドでjson形式で出力したものを、別のDBにpython manage.py loaddataコマンドでインポートしようとしたところ以下のようなエラーが発生しました。

発生したエラー内容
django.db.utils.DataError: Problem installing fixture 'C:\Users\sample\app\fixtures\sample.json': Could not load app.Product(pk=1) integerの範囲外です。
エラーを見る限り、「integerフィールドの値が範囲外なため登録に失敗している・・・」と言っている模様。

そういえばjancodeってモデルでIntegerFieldを指定していたな・・・
そこで、改めてDjangoモデルフィールドのIntegerField上限値を確認したら2147483647(10桁)だったわけです。

でもadmin画面では13桁の数値で登録できてたよな・・・
仕様と状況が矛盾していてよくわかりませんでしたが、他に悪さしていそうな部分が見当たらなかったため、以下の通りカラムjancodeのデータ型をBigIntegerFieldに変更。
ちなみにBigIntegerFIeldは64 ビットの数値で範囲は-9223372036854775808 ~ 9223372036854775807です。
class Product(models.Model):

    class Meta:
        #カテゴリ
        verbose_name ="製品マスター"
        verbose_name_plural ="製品マスター"
      
#カラム名の定義
    product_name = models.CharField(max_length=255)
    jancode = models.BigIntegerField("janコード")

その後、python manage.py loaddataコマンドを実行することで、以下のようにエラーなくインポートできるようになりました。
python manage.py loaddata sample.json --app app
Installed 92 object(s) from 1 fixture(s)

 

まとめ
  • python manage.py loaddataコマンドで integerの範囲外エラーが発生した場合はmodels.pyのカラム定義を確認する。
  • IntegerFieldを指定していて10桁を超えるデータを登録しようとしていた場合はBigIntegerFieldに変えてみる。

 

以上、「djangoモデルのIntegerField上限値に関するコラム」でした。

 

おすすめの記事