django同一个项目中连接多个数据库

╰半橙微兮° 2021-12-11 11:41 367阅读 0赞

一、场景与思路

同一个项目中需要连接多个数据库。

二、代码

代码中主要是三个部分,settings、models以及自己写的一个类。

1.自己写的文件:database_app_router.py 类名:DatabaseAppsRouter

  1. # database_app_router.py
  2. # -*- coding: utf-8 -*-
  3. from django.conf import settings
  4. DATABASE_MAPPING = settings.DATABASES_APPS_MAPPING
  5. class DatabaseAppsRouter(object):
  6. """
  7. A router to control all database operations on models for different
  8. databases.
  9. In case an app is not set in settings.DATABASE_APPS_MAPPING, the router
  10. will fallback to the `default` database.
  11. Settings example:
  12. DATABASE_APPS_MAPPING = {'app1': 'db1', 'app2': 'db2'}
  13. """
  14. def db_for_read(self, model, **hints):
  15. """"Point all read operations to the specific database."""
  16. """将所有读操作指向特定的数据库。"""
  17. if model._meta.app_label in DATABASE_MAPPING:
  18. return DATABASE_MAPPING[model._meta.app_label]
  19. return None
  20. def db_for_write(self, model, **hints):
  21. """Point all write operations to the specific database."""
  22. """将所有写操作指向特定的数据库。"""
  23. if model._meta.app_label in DATABASE_MAPPING:
  24. return DATABASE_MAPPING[model._meta.app_label]
  25. return None
  26. def allow_relation(self, obj1, obj2, **hints):
  27. """Allow any relation between apps that use the same database."""
  28. """允许使用相同数据库的应用程序之间的任何关系"""
  29. db_obj1 = DATABASE_MAPPING.get(obj1._meta.app_label)
  30. db_obj2 = DATABASE_MAPPING.get(obj2._meta.app_label)
  31. if db_obj1 and db_obj2:
  32. if db_obj1 == db_obj2:
  33. return True
  34. else:
  35. return False
  36. else:
  37. return None
  38. def allow_syncdb(self, db, model):
  39. """Make sure that apps only appear in the related database."""
  40. """确保这些应用程序只出现在相关的数据库中。"""
  41. if db in DATABASE_MAPPING.values():
  42. return DATABASE_MAPPING.get(model._meta.app_label) == db
  43. elif model._meta.app_label in DATABASE_MAPPING:
  44. return False
  45. return None
  46. def allow_migrate(self, db, app_label, model=None, **hints):
  47. """Make sure the auth app only appears in the 'auth_db' database."""
  48. """确保身份验证应用程序只出现在“authdb”数据库中。"""
  49. if db in DATABASE_MAPPING.values():
  50. return DATABASE_MAPPING.get(app_label) == db
  51. elif app_label in DATABASE_MAPPING:
  52. return False
  53. return None

settings.py文件中修改

  1. # settings.py
  2. DATABASES = {
  3. "default": {
  4. "ENGINE": "django.db.backends.mysql",
  5. "NAME": "integral_wall",
  6. "USER": "root",
  7. "PASSWORD": "123456",
  8. "HOST": "127.0.0.1",
  9. "PORT": "3306",
  10. },
  11. "sdk_51zhuan": {
  12. "ENGINE": "django.db.backends.mysql",
  13. "NAME": "sdk_51zhuan",
  14. "USER": "root",
  15. "PASSWORD": "123456",
  16. "HOST": "127.0.0.1",
  17. "PORT": "3306",
  18. },
  19. }
  20. DATABASES_APPS_MAPPING = {
  21. 'integral_wall': 'default',
  22. 'sdk_db': 'sdk_51zhuan',
  23. 'admin': 'sdk_51zhuan',
  24. 'auth': 'sdk_51zhuan',
  25. } DATABASE_ROUTERS = ['integral_wall_manager.database_app_router.DatabaseAppsRouter']

models.py文件修改

  1. # models.py
  2. class SdkApplication(models.Model):
  3. """
  4. 应用程序列表
  5. """
  6. sdk_type_choices = (
  7. (0, '不合作'),
  8. (1, '一定时间内合作'),
  9. (2, '永久合作'),
  10. )
  11. id = models.AutoField(primary_key=True)
  12. app_id = models.CharField('苹果商店里的APP id', max_length=16, default='')
  13. app_name = models.CharField('应用名称', max_length=64)
  14. bundle_id = models.CharField('包ID,域名倒序', max_length=64, default='')
  15. create_time = models.DateTimeField('创建时间', auto_now_add=True)
  16. class Meta:
  17. app_label = 'sdk_db' # 连接的数据库
  18. db_table = "sdk_application" # 表名
  19. class AdRecord(models.Model):
  20. """
  21. 广告记录
  22. """
  23. type = models.CharField('操作类型', max_length=16)
  24. action = models.CharField('操作、行为', max_length=16)
  25. create_time = models.DateTimeField('创建时间', auto_now_add=True)
  26. class Meta:
  27. # app_label 不写,使用默认
  28. db_table = "ad_record" # 表名

三、执行

执行的顺序就是大家熟悉的了:

1.python manage.py makemigrations

之后的稍有不同:

2.python manage.py migrate —database=sdk_51zhuan

……

python manage.py migrate(只有默认数据库不为空时才可以这么实用,若为空则是用上面的方法)

其实在这里没有特别的执行顺序,但是我个人建议大家是最后执行migrate(即默认数据库)。另外要注意一点,admin、auth是一定要在一个app里被makemigrations放到一个XXXX_initial.py文件中的,不然你怎么migrate都不会有这些Django自建的表的!


****最后的最后一定要注意:不在一个库里了,没法跨库建立约束关系,放弃外键,老老实实一步步查!****

转载于:https://www.cnblogs.com/aaron-agu/p/11019226.html

发表评论

表情:
评论列表 (有 0 条评论,367人围观)

还没有评论,来说两句吧...

相关阅读