Hi Everyone,
I’m trying to implement a way to dynamically switch databases using URL parameters. The purpose of this is to allow users to switch between a live database and test database by clicking a button which would submit a GET or POST request to the server and allow them to switch between both databases, I also tried setting this during login.
I’ve tried using django’s database routing that’s mentioned in the documentation as well as middleware which is mentioned in several stackoverflow threads.
login view:
User = get_user_model()
THREAD_LOCAL = threading.local()
def login_view(request):
form = LoginForm(request.POST or None)
btn = 'Login'
heading = 'Sign in'
if form.is_valid():
username = form.cleaned_data.get('username')
password = form.cleaned_data.get('password')
user = authenticate(username=username, password=password, backend='django.contrib.auth.backends.ModelBackend')
login(request, user)
THREAD_LOCAL.TEST_DB = 0
messages.success(request, 'Logged in')
return HttpResponseRedirect('/')
Database Router:
THREAD_LOCAL = threading.local()
class DifferentDBRouter:
def db_for_read(self, model, **hints):
if THREAD_LOCAL.TEST_DB == 0:
return "default"
else:
return "test"
def db_for_write(self, model, **hints):
if THREAD_LOCAL.TEST_DB == 0:
return "default"
else:
return "test"
Settings:
DATABASE_ROUTERS = ['django_rest_api_tasks.db_router.DifferentDBRouter']
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': BASE_DIR / 'db.sqlite3',
},
'test': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': BASE_DIR / 'test.sqlite3',
}
}
Middleware:
try:
from django.utils.deprecation import MiddlewareMixin
except ImportError:
MiddlewareMixin = object
THREAD_LOCAL = threading.local()
class DBRouterMiddleware(MiddlewareMixin):
def process_view(self, request, view_func, view_args, view_kwargs):
if request.user:
THREAD_LOCAL.TEST_DB = request.session['TestDB']
I’ve also tried using threading.local() and the django-threadlocals library to pass the request to the database router since the database router doesn’t have access to requests, is it possible to pass requests to the database router and change the database connection from there?