Django - 多数据库 + 多模型
我有两个数据库和两个模型:一个是管理员模型,另一个是用户模型。
我想把这两个模型同步到两个数据库:管理员模型同步到数据库A,用户模型同步到数据库B。
所以我的问题是,如何把这两个模型同步到两个数据库呢?用户模型应该在默认数据库里,而管理员模型在管理员模型里。
这是我尝试过的:
class User(models.Model):
job_id = models.CharField(max_length = 255)
time = models.DateTimeField( auto_now_add = True, db_index = True)
class Meta:
app_label = 'user_data'
class Admin(models.Model):
barcode = models.CharField(max_length = 255)
weight = models.CharField(max_length = 255)
length = models.CharField(max_length = 255)
breadth = models.CharField(max_length = 255)
height = models.CharField(max_length = 255)
dsp_name = models.CharField(max_length = 255)
time = models.DateTimeField( auto_now_add = True, db_index = True)
class Meta:
app_label = 'admin_data'
这是我的设置:
DATABASE_ROUTERS = ['manager.router.DatabaseAppsRouter']
DATABASE_APPS_MAPPING = {
'user_data': 'default',
'admin_data':'admin_db'
}
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'gor_vms',
'USER': 'root',
'PASSWORD': '',
'HOST': '127.0.0.1',
'PORT': '',
},
'admin_db': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'admin_vms_db',
'USER': 'root',
'PASSWORD': '',
'HOST': '127.0.0.1',
'PORT': '',
}
}
使用south的时候,迁移文件是创建出来了,但当我执行迁移时,它返回一个错误,提示 south.db.db = south.db.dbs[database] KeyError: 'gor_vms'
另外,DATABASE_ROUTERS = ['manager.router.DatabaseAppsRouter']
也报错,提示 No named module manager.router
我该如何把这两个数据库和两个不同的模型同步起来呢?
附注:我在StackOverflow上看了很多帖子,但没有找到正确的答案。请帮帮我。
编辑
我也尝试过这个。
AdminRouter
class AdminRouter(object):
def db_for_read(self, model, **hints):
if model._meta.app_label == 'admin_data':
return 'admin_db'
return None
def db_for_write(self, model, **hints):
if model._meta.app_label == 'admin_data':
return 'admin_db'
return None
def allow_relation(self, obj1, obj2, **hints):
if obj1._meta.app_label == 'admin_data' or \
obj2._meta.app_label == 'admin_data':
return True
return None
def allow_migrate(self, db, model):
if db == 'admin_db':
return model._meta.app_label == 'admin_data'
elif model._meta.app_label == 'admin_data':
return False
return None
GorRouter
class UserRouter(object):
def db_for_read(self, model, **hints):
if model._meta.app_label == 'user_data':
return 'default'
return None
def db_for_write(self, model, **hints):
if model._meta.app_label == 'user_data':
return 'default'
return None
def allow_relation(self, obj1, obj2, **hints):
if obj1._meta.app_label == 'user_data' or \
obj2._meta.app_label == 'user_data':
return True
return None
def allow_migrate(self, db, model):
if db == 'default':
return model._meta.app_label == 'user_data'
elif model._meta.app_label == 'user_data':
return False
return None
设置
DATABASE_ROUTERS = ['../modules/data/admin_db_router.AdminRouter','../modules/data/user_db_router.UserRouter']
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'gor_vms',
'USER': 'root',
'PASSWORD': '',
'HOST': '127.0.0.1',
'PORT': '',
},
'admin_db': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'admin_vms_db',
'USER': 'root',
'PASSWORD': '',
'HOST': '127.0.0.1',
'PORT': '',
}
}
所以,为了同步数据库,我按照以下步骤操作:-
1)python manage.py schemamigration data --initial
2) python manage.py syncdb
它返回了一个追踪信息,提示:
Traceback (most recent call last):
File "manage.py", line 10, in <module>
execute_from_command_line(sys.argv)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/__init__.py", line 399, in execute_from_command_line
utility.execute()
File "/usr/local/lib/python2.7/dist-packages/django/core/management/__init__.py", line 392, in execute
self.fetch_command(subcommand).run_from_argv(self.argv)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/base.py", line 242, in run_from_argv
self.execute(*args, **options.__dict__)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/base.py", line 285, in execute
output = self.handle(*args, **options)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/base.py", line 415, in handle
return self.handle_noargs(**options)
File "/usr/local/lib/python2.7/dist-packages/south/management/commands/syncdb.py", line 92, in handle_noargs
syncdb.Command().execute(**options)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/base.py", line 285, in execute
output = self.handle(*args, **options)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/base.py", line 415, in handle
return self.handle_noargs(**options)
File "/usr/local/lib/python2.7/dist-packages/django/core/management/commands/syncdb.py", line 61, in handle_noargs
seen_models = connection.introspection.installed_models(tables)
File "/usr/local/lib/python2.7/dist-packages/django/db/backends/__init__.py", line 1254, in installed_models
if router.allow_syncdb(self.connection.alias, model):
File "/usr/local/lib/python2.7/dist-packages/django/db/utils.py", line 272, in allow_syncdb
for router in self.routers:
File "/usr/local/lib/python2.7/dist-packages/django/utils/functional.py", line 49, in __get__
res = instance.__dict__[self.func.__name__] = self.func(instance)
File "/usr/local/lib/python2.7/dist-packages/django/db/utils.py", line 230, in routers
router = import_by_path(r)()
File "/usr/local/lib/python2.7/dist-packages/django/utils/module_loading.py", line 21, in import_by_path
module = import_module(module_path)
File "/usr/local/lib/python2.7/dist-packages/django/utils/importlib.py", line 33, in import_module
raise TypeError("relative imports require the 'package' argument")
TypeError: relative imports require the 'package' argument
我该如何在不同的数据库中使用不同的模型呢?请帮帮我。
1 个回答
在你的设置中,DATABASE_ROUTERS
列表应该包含的是 python 路径(比如:'modules.data.admin_db_router.AdminRouter', ...
),而不是文件系统路径。需要注意的是,通常的 PYTHONPATH / sys.path
规则仍然适用,也就是说在上面的例子中,modules
和 data
这两个文件夹必须是 Python 包,并且包含 modules
的那个文件夹必须以某种方式在你的 sys.path
中。
另外,Python 和 Java 不一样,所以你不需要为每个类创建一个不同的模块。我个人建议把 AdminRouter
和 UserRouter
这两个类放在同一个 routers.py
模块里。