Django 3.11 において、複数データベースを使い分ける手段を調べていたときに Default Manager
Base Manager
の存在を知りました。時間が経つと存在自体忘れそうなため、自分用にメモしときます。
認識齟齬等ありましたら、コメント等いただけると幸いです。 🙏
複数データベースを利用する
複数のデータベース | Django ドキュメント | Django に記載されている通り、settings.py
に default
以外のデータベース情報を定義し、
ような方法があるのかな、と思います。
参考リソース
検証用コードが載っている記事がありました。
利用するDjangoのバージョンに注意しながら、参考にすると良さそうです。
Default Manger と Base Manager
リファレンスにDefault MangerとBase Mangerの説明が記載されています。
Default Manager は object
の代わりに Custom Manger を指定。
Base Manger は ForeignKey や OneToOneField で参照しているモデルで使用されるマネージャを指定...と解釈しています。
コード
リファレンスを見る限り Meta.default_manager_name Meta.base_manager_name を指定するっぽいです。
ざっくり書き起こすと、以下のようなイメージです。
from django.db import models
class GeneralUserManager(models.Manager):
def get_queryset(self):
return super().get_queryset().filter(owner=False)
class User(models.Model):
description = models.TextField()
owner = models.BooleanField(default=False)
objects = GeneralUserManager()
owner_objects = models.Manager()
class Meta:
base_manager_name = 'owner_objects'
class PcSkill(models.Model):
user = models.ForeignKey(User, on_delete=models.CASCADE, related_name='pc_skill')
level = models.IntegerField()
このようなモデルやマネージャを定義しておき...
skill = PcSkill.objects.get(pk=1)
skill.user.description
skill.user.description
のように関連オブジェクトを参照した際、User
のMeta.base_manager_name
に指定した"owner_objects"
が選択されます。
カスタムマネージャは、上記サンプルコードのようにfilter
したり、using
やdb_manager
を用いてデータベースの切り替えたりできます。
関連するオブジェクトから使用するマネージャをカスタムマネージャに変更したい場合は、Meta.base_manager_name
に指定すると良さそうです。
※ Meta.default_manager_name
Meta.base_manager_name
は、正しくは Option.default_manager_name
Option.base_manager_name
です。
コードで説明するため、あえて Meta
と書いています。
おわり
以上です。
繰り返しになりますが、認識齟齬等ありましたら、コメントなどフィードバックいただけると助かります 🙏