- DatetimeFieldの現在日時設定用のプロパティを解説して!
このような疑問にお答えします。
DateTimeFieldには以下のプロパティが用意されています。
- auto_now_add
- auto_now
auto_now_addは新しく追加されたタイミングの時刻を自動的に追加します。
一方で、auto_nowは更新のたびに現在時刻を設定するプロパティです。
パッと見ではどれがどっちか分からなくなってしまうので、本記事で整理しておきましょう。
auto_now_addとauto_nowの違いについて
どちらも日時を自動的に取得して保存するものです。
auto_nowやauto_now_addを使うと、プログラム内から直接値を設定できなくなります。
手動で値を設定する必要がある場合はdefaultを使用するか、別の方法でフィールドを定義することになります。
具体的な設定例
作成日と更新日だけを設定したモデルを例示します。
from django.db import models
class ExampleModel(models.Model):
created_at = models.DateTimeField(auto_now_add=True) # 作成日時
updated_at = models.DateTimeField(auto_now=True) # 更新日時
class Meta:
ordering = ["-created_at"] # デフォルトの並び順(最新が上)
def __str__(self):
return f"ExampleModel created on {self.created_at}"今回説明するのは、DateTimeFieldに設定したauto_now_addとauto_nowの二つです。
auto_now_add=Trueについて
インスタンスの作成時に、一度だけ日時を設定したいとき用のものです。
作成日時は、このauto_now_add=Trueとすることが多いかと思います。
auto_now=Trueについて
インスタンスが更新されるたびに、自動的に現在日時を取得します。
つまり、更新日時を表すupdated_atなどのフィールドに多く使われます。
auto_now / auto_now_add の補足知識
ここからは両者の理解を深めるために、それぞれのプロパティを少し突っ込んで解説します。
二つのプロパティが分かれている理由
以下の二つを区別して、簡潔に扱うためです。
- 作成時のタイムスタンプ
- 更新時のタイムスタンプ
どのタイミングでタイムスタンプが反映されるかが一目でわかります。
注意点
auto_now, auto_now_addを使うと、手動で値を設定することができません。
もし手動設定したい場合には、defaultか他の方法でフィールドを定義する必要があります。
補足: タイムスタンプは抽象基底クラスで一括管理するのがベスト
Django では「作成日時(created_at)」と「更新日時(updated_at)」を ほぼすべてのモデルで使う場面が出てきます。
でも、各モデルに次のようなフィールドを毎回書くのは非効率です。
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)- コピペが増える
- 書き忘れが起こる
- モデルによって仕様が揃わなくなる
こうした問題を避けるために、タイムスタンプは 抽象基底クラス(abstract base class)で共通化するのが実務で最もよく使われる方法です。
共通の TimeStampedModel を作る
from django.db import models
class TimeStampedModel(models.Model):
created_at = models.DateTimeField(auto_now_add=True) # レコード作成日時を自動保存
updated_at = models.DateTimeField(auto_now=True) # レコード更新日時を自動更新
class Meta:
abstract = True # このクラス自体はDBにテーブルを作らない各モデルでは継承するだけで OKです。
class Article(TimeStampedModel):
title = models.CharField(max_length=255)
content = models.TextField()これだけで、どのモデルにも created_at / updated_at が保証されるようになります。
この方法により、次のメリットがあります。
- モデルごとにタイムスタンプを書かなくて済む(DRY)
- 書き忘れゼロでデータの一貫性が保たれる
- 全モデルの仕様が揃うため保守しやすい
- どんなアプリでもほぼ必須のパターンとして使える
Django アプリを中規模以上で運用するならTimeStampedModel を定義しておくのは本当に便利です。

コメント