Django Architecture
MVC vs MCT
Architecture- Both MVC and MVT are one of the famous
design patterns
- They are used for many web application frameworks.
- It is an
architectural pattern
thatseparates
an application into three mainlogical components
2.1 Model View Controller(MVC)
- Model
- This is responsible for
maintaining data
. Handles database basically. - Manages data,
Business Logic
- This is responsible for
- View
- This is responsible for
displaying data
(data representation)
- This is responsible for
- Controller
- This is
responsible for the interactions
between the Model and View. - It controls the data flow into Model and updates View when data is changed.
- This is
2.2 Model View Template (MVT)
- Django follows
MVT Architecture
- Model
models.py
- This is responsible for maintaining data.
Handles database
basically.
- Views
views.py
- It is the
business logic layer
- View interact with both models and templates
- Templates
templates(.html)
- It is a presentation layer, the component with which user interacts
- Controller
- There is
no separate controller
and complete application is based on Model View and Template. - But the three components(M-V-T) communicate with each other via an inner
controller
- And that controller is actually
Django framework
, It does thecontrolling part itself
- There is
2.3 Why is Django called loosely coupled framework?
- The various layers of the framework should not know about each other unless absolutely necessary.
- Django is called a loosely coupled framework
because of its MVT architecture
, which is a variant of the MVC architecture. - It helps in
separating the server code from the client-related code
. - Server code –> models and views take care of the server code
- Client code –> templates are mostly HTML and CSS that just need data from models passed in by the views to render them.
- Since these components are
independent of each other
, Django is called a loosely coupled framework.
2.4 django-admin and manage.py
django-admin
- A command-line utility of Django for administrative tasks.
manage.py
- It is automatically created in each Django project
- It does the same thing as django-admin but also sets the DJANGO_SETTINGS_MODULE environment variable.
Create a django project
# Create a Django project
django-admin startproject mysite
# File Structure --> of Django Project
mysite/
manage.py
mysite/
__init__.py
settings.py
urls.py
asgi.py
wsgi.py
Run Django project
# Ways to run django server
python manage.py runserver
python manage.py runserver 8080
python manage.py runserver 0:8000
#OR
export DJANGO_SETTINGS_MODULE=mysite.settings
django-admin runserver
#Reset
export DJANGO_SETTINGS_MODULE=django.conf.global_settings
Create Django App
# Create a app
python manage.py startapp polls
# File Structure
mysite/
manage.py
mysite/
polls/
__init__.py
admin.py
apps.py
migrations/
__init__.py
models.py
tests.py
views.py
2.5 Write custom django-admin commands?
- Also called as
management commands
- Create below files and folders inside app dir
# Management command file structure
polls/
management/
__init__.py
commands/
__init__.py
my_custom_command.py
Positional Arguments
# my_custom_command.py
from django.core.management.base import BaseCommand
class Command(BaseCommand):
help = 'Positional Arguments'
def add_arguments(self, parser):
parser.add_argument('num', type=int, help='Enter a number')
parser.add_argument('name', type=str, help='Enter a name')
def handle(self, *args, **kwargs):
print(kwargs.get('num'), kwargs.get('name'))
# python manage.py my_custom_command 30 amrit
# 30 amrit
Optional Arguments
-name
or--name
is used for optional arguments
# my_custom_command.py
from django.core.management.base import BaseCommand
class Command(BaseCommand):
help = 'Optional Arguments'
def add_arguments(self, parser):
parser.add_argument('-n', type=int, help='Enter a number')
parser.add_argument('--name', type=str, help='Enter a name')
parser.add_argument('-c', '--count', type=int, help='NA')
def handle(self, *args, **kwargs):
print(kwargs.get('n'), kwargs.get('name'), kwargs.get('count'))
# python manage.py my_custom_command -n 1 --name amrit -c 111
# python manage.py my_custom_command -n 1 --name amrit --count 111
# 1 amrit 111
Flag Arguments
action='store_true'
is used to indicate Flag argument
# my_custom_command.py
from django.core.management.base import BaseCommand
class Command(BaseCommand):
help = 'Flag Arguments'
def add_arguments(self, parser):
parser.add_argument('total', type=int, help='NA')
parser.add_argument('-p', '--prefix', type=str, help='NA')
parser.add_argument('-a', '--admin', action='store_true')
def handle(self, *args, **kwargs):
print(kwargs.get('total'), kwargs.get('prefix'), kwargs['admin'])
# python manage.py my_custom_command 1 -p amrit -a
# python manage.py my_custom_command 1 -p amrit --admin
# 1 amrit True
# python manage.py my_custom_command 1 -p amrit
# 1 amrit False
Arbitrary List of Arguments
- Can pass a single or any number of inputs(separated by spaces) as list
# my_custom_command.py
from django.core.management.base import BaseCommand
class Command(BaseCommand):
help = 'Arbitrary List of Arguments'
def add_arguments(self, parser):
parser.add_argument('user_id', nargs='+', type=int, help='NA')
def handle(self, *args, **kwargs):
print(kwargs.get('user_id'))
# python manage.py my_custom_command 1
# 1
# python manage.py my_custom_command 1 2 3
# 1 2 3
Styling
# my_custom_command.py
from django.core.management.base import BaseCommand
class Command(BaseCommand):
help = 'Styling'
def handle(self, *args, **kwargs):
self.stdout.write(self.style.ERROR('error - A major error.'))
self.stdout.write(self.style.NOTICE('notice - A minor error.'))
self.stdout.write(self.style.SUCCESS('success - A success.'))
self.stdout.write(self.style.WARNING('warning - A warning.'))
self.stdout.write(self.style.SQL_FIELD('sql_field - The name of a model field in SQL.'))
self.stdout.write(self.style.SQL_COLTYPE('sql_coltype - The type of a model field in SQL.'))
self.stdout.write(self.style.SQL_KEYWORD('sql_keyword - An SQL keyword.'))
self.stdout.write(self.style.SQL_TABLE('sql_table - The name of a model in SQL.'))
self.stdout.write(self.style.HTTP_INFO('http_info - A 1XX HTTP Informational server response.'))
self.stdout.write(self.style.HTTP_SUCCESS('http_success - A 2XX HTTP Success server response.'))
self.stdout.write(self.style.HTTP_NOT_MODIFIED('http_not_modified - A 304 HTTP Not Modified server response.'))
self.stdout.write(self.style.HTTP_REDIRECT('http_redirect - A 3XX HTTP Redirect server response other than 304.'))
self.stdout.write(self.style.HTTP_NOT_FOUND('http_not_found - A 404 HTTP Not Found server response.'))
self.stdout.write(self.style.HTTP_BAD_REQUEST('http_bad_request - A 4XX HTTP Bad Request server response other than 404.'))
self.stdout.write(self.style.HTTP_SERVER_ERROR('http_server_error - A 5XX HTTP Server Error response.'))
self.stdout.write(self.style.MIGRATE_HEADING('migrate_heading - A heading in a migrations management command.'))
self.stdout.write(self.style.MIGRATE_LABEL('migrate_label - A migration name.'))