Monday, November 19, 2018

Working with Multiple Databases in Django.

Working with Multiple Databases in Django.

As usual django-doc is great to start with any topics. I was just giving a try to use multiple database in single application.

1. Database Settings

First step is to tell your django application that you want to use more than one database. So look for the DATABASES in your project's settings.py file.
project/settings.py

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.sqlite3',
        'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
    },
    'blogs': {
        'ENGINE': 'django.db.backends.sqlite3',
        'NAME': os.path.join(BASE_DIR, 'blogs_db.sqlite3')
    }
}
Here I'm going to store all the blog entries into "blogs" ( blogs_db.sqlite3 ) and rest data will be stored in into "default" database ( db.sqlite3 ).

2. Define Model

blogs/models.py

from django.db import models

class Blog(models.Model):
    title = models.CharField(max_length=200)

3. Setup Database Router

You can define a database router that implements a policy constraining the availability of particular models.
project/settings.py
DATABASE_ROUTERS = ['blogs.router.BlogRouter']
blogs/router.py

class BlogRouter:
    """
    A router to control all database operations on models in the
    auth application.
    """
    def db_for_read(self, model, **hints):
        """
        Attempts to read auth models go to auth_db.
        """
        if model._meta.app_label == 'blogs':
            return 'blogs'
        return None

    def db_for_write(self, model, **hints):
        """
        Attempts to write auth models go to auth_db.
        """
        if model._meta.app_label == 'blogs':
            return 'blogs'
        return None

    def allow_relation(self, obj1, obj2, **hints):
        """
        Allow relations if a model in the auth app is involved.
        """
        if obj1._meta.app_label == 'blogs' or \
           obj2._meta.app_label == 'blogs':
           return True
        return None

    def allow_migrate(self, db, app_label, model_name=None, **hints):
        """
        Make sure the auth app only appears in the 'auth_db'
        database.
        """
        if app_label == 'blogs':
            return db == 'blogs'
        return None
That's it. Now test whether the settings are working fine or not?
./manage.py makemigrations --database=default
./manage.py makemigrations --database=blogs

4. Create Blog

There are multiple ways to create blog entry in blogs_db,

4.1. By using "using()" to create entry in perticular db.
example,
from blogs.models import Blog
Blog.objects.using('blogs').create(title='python goes here')

4.2. Create a blog through admin interface.

blogs/admin.py

from django.contrib import admin
from .models import Blog

admin.site.register(Blog)

5. Test Your Config Using Shell

Create a blog entry using the admin site and will check which database has stored the blog info.
./manage.py shell

from blogs.models import Blog

 # This will run on the DEFAULT-DATABASE/BLOG-DATABASE
Blog.objects.all() 
QuerySet [Blog: Blog object (1)]

 # This will run on the BLOGS-DATABASE
Blog.objects.using('blogs').all()
QuerySet [Blog: Blog object (1)]
# returns blogs

 #This will run on the DEFAULT-DATABASE
Blog.objects.using('default').all()

    301             return Database.Cursor.execute(self, query)
    302         query = self.convert_query(query)
--> 303         return Database.Cursor.execute(self, query, params)
    304
    305     def executemany(self, query, param_list):
OperationalError: no such table: blogs_blog
returns error.
For more detail please visit, https://docs.djangoproject.com/en/2.1/topics/db/multi-db/
Share:
Location: Mumbai, Maharashtra, India

0 comments:

Post a Comment