我的建议是为此保持一个代码库和一个服务器运行(或同一 Django 应用程序的多个服务器,无需任何基于客户端的自定义)。主要原因是维护更容易。您不希望多次进行更改以向多个客户端提供功能。
由于您已经有一个 Django 应用程序,我认为最好利用该代码来适应上面给出的方法,而代码更改最少。这意味着,您需要某种方法来处理连接到多个数据库的多个客户端。我建议使用中间件和database router。像这样:(代码基于snippet)。
import threading
request_cfg = threading.local()
class RouterMiddleware (object):
def process_view( self, request, view_func, args, kwargs ):
if 'client' in kwargs:
request_cfg.client = kwargs['client']
request.client = client
# Here, we are adding client info with request object.
# It will make the implementation bit easier because
# then you can access client information anywhere in the view/template.
def process_response( self, request, response ):
if hasattr( request_cfg, 'client' ):
del request_cfg.client
return response
class DatabaseRouter (object):
def _default_db( self ):
from django.conf import settings
if hasattr( request_cfg, 'client' ) and request_cfg.client in settings.DATABASES:
return request_cfg.client
else:
return None
def db_for_read( self, model, **hints ):
return self._default_db()
def db_for_write( self, model, **hints ):
return self._default_db()
然后将它们添加到settings.py:
DATABASES = {
'default': {
'NAME': 'user',
'ENGINE': 'django.db.backends.postgresql',
'USER': 'postgres_user',
'PASSWORD': 's3krit'
},
'client1': {
'NAME': 'client1',
'ENGINE': 'django.db.backends.postgresql',
'USER': 'postgres_user',
'PASSWORD': 's3krit'
},
'client2': {
'NAME': 'client2',
'ENGINE': 'django.db.backends.postgresql',
'USER': '_user',
'PASSWORD': 'priv4te'
}
}
DATABASE_ROUTERS = [
'path.to.DatabaseRouter',
]
MIDDLEWARE = [
# middlewares
'path.to.RouterMiddleware'
]
终于更新urls.py:
urlpatterns = [
path('<str:client>/admin/', admin.site.urls),
path('<str:client>/', include('client_app.urls')),
# and so on
]
这种方法的优点是您不必为新客户端配置任何内容,您只需在设置中添加一个新数据库并按照@987654323 中的说明运行迁移@。无需配置反向代理服务器或其他任何东西。
现在,当涉及到在 celery 中处理任务时,您可以提供您将使用哪个数据库来运行查询(参考 docs)。这是一个例子:
@app.task
def some_task():
logger.info("-"*25)
for db_name in settings.DATABASES.keys():
Model.objects.using(db_name).filter(some_condition=True)
logger.info("-"*25)