0% found this document useful (0 votes)
28 views

django_notes (3)

detail django notes

Uploaded by

Yash Kadam
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
28 views

django_notes (3)

detail django notes

Uploaded by

Yash Kadam
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 134

What is Django

A web framework is a server-side application framework which is designed to support the


development of dynamic websites.

With the help of a framework, you don’t have to handle the hassles of web development and
its various components.

Therefore, it makes the life of a web application developer much easier as they don’t have to
code from scratch.

It follows the principle of “Don’t Repeat Yourself”.


As the name says, this principal is all about keeping the code simple and non repeating.
Why Django
• It takes care of user authentication, content administration, site maps and many more.
• Django is highly secure. It helps the developers to avoid many common security mistakes,
such as SQL injection, cross-site scripting, csrf/ xsrf (cross-site request forgery) and click-
jacking.
• It’s pretty scalable. (Example: Instagram, Disqus).
• The framework cleanly separates components such as its database layer and application
layer.
• It has various other advantages as it has an automatic administration interface, Object-
relational mapper (ORM), RSS feeds and many more.
• Django is also a high level, MVT architecture based.
• Dynamically builds web applications.
• Grands ease to build multi-protocol networks.
• Provides quick processing.
• Extremely fast & SEO Optimized.
Why Django
Django Architecture

Source : medium.com
MVC vs MVT
MVC architecture

Source : medium.com
MVC vs MVT
MVT architecture

MVT stands for Model View Template. In MVT, there is a predefined template for user
interface.

Now you might be wondering where is the controller?


In the case of MVT, Django itself takes care of the controller part, it’s inbuilt.
That is, it’s probably the framework itself: the machinery that sends a request to the
appropriate view, according to the Django URL configuration.
MVC vs MVT
MVT architecture
C:\Users\kunalpag\AppData\Local\Programs\Python\Python37-32>pip freeze
certifi==2020.6.20
click==7.1.1
cx-Oracle==8.0.0
cycler==0.10.0
Django==2.2.2
Flask==1.1.2
itsdangerous==1.1.0
Jinja2==2.11.1
kiwisolver==1.2.0
MarkupSafe==1.1.1
matplotlib==3.3.1
numpy==1.17.0
opencv-python==4.1.0.25
Pillow==7.2.0
pyparsing==2.4.7
python-dateutil==2.8.1
pytz==2019.1
six==1.15.0
sqlparse==0.3.0
Create a project
$django-admin help

$django-admin startproject helloworld

Open the project in sublime text/visual studio

$python manage.py runserver


Django project structure
$ django-admin startproject helloworld_project .
├── Pipfile
├── Pipfile.lock
├── helloworld_project
│ ├── __init__.py
│ ├── settings.py
│ ├── urls.py
│ └── wsgi.py
└── manage.py
settings.py file controls our project’s settings. E.g: DB setting, debugging info.
urls.py tells Django which pages to build in response to a browser or url request
wsgi.py which stands for web server gateway interface, helps Django serve our eventual web
pages.
manage.py is used to execute various Django commands such as running the local web server
or creating a new app.
11
Project structure
__pycache__
Generate when server gets started/runs. No need to update anything here. Just use to run
server/programs faster. Delete will reappear the folder again when server gets run.

Seeting.py
Key value pair
DEBUG=true (In production keep it false)
Installed_apps : Django has concept called as apps. These are default apps.
Create an app with name “pages”
Django uses the concept of projects and apps to keep code clean and readable.
A single Django project contains one or more apps within it that all work together to power a web
application.
Project Dir-FB

Project Dir-FB Dashboard Posts Messenger Menu

This is why the command for a new Django project is startproject!

For example, a real-world Django e-commerce site might have one app for user authentication,
another app for payments, and a third app to show the item listing details.
create our first app which we’ll call pages

$ python manage.py startapp pages

13
Create apps inside project
$ python manage.py startapp pages
It will create pages app(folder) with few files
Things to remember
$django-admin startapp appName

1) Register newly created application with rootapp


2) Define URL for the application (urls.py)
3) Define view(views.py) of the application(http://localhost:8080/login)
4) Include application URL into main URL(present in "root App" folder)
Open seetings.py Update settings.py
Add entry of newly created app inside settings.py

Note : PagesConfig is a config class present in apps.py of pages app.


Create urls.py inside pages
Create URL inside pages app

# pages/urls.py
from django.urls import path

#from .views import index


# OR
from . import views

urlpatterns = [
path('', views.home, name='home'),
]

In next step write index and homePageView function


Write index function
from django.shortcuts import render

# Create your views here.

from django.shortcuts import render


from django.http import HttpResponse

def home(request):
return HttpResponse(‘<h1>Hello, I am learning Django!</h1>')
Register the links of pages app into main urls.py
from django.contrib import admin
from django.urls import path,include

urlpatterns = [
path('', include('pages.urls')),
path('admin/', admin.site.urls),
]

Run the server


$python manange.py runserver
def home(request):
return HttpResponse(‘<h1>Hello, I am learning Django!</h1>')

We shouldn't be keep writing response like this when response is big.

More correct way is to handle the request and send the response is through Django
Template view.
Template view
Template view intro
Build, and deploy a Pages app that has a homepage and an about page. Using class-based
views and templates which are the building blocks of Django’s

Templates, Views, and URLs.


The URLs control the initial route, the entry point into a page, such as /about.
The views contain the business logic. For web pages that rely on a database model, it is the
view that does much of the work to decide what data is available to the template.
The template has the HTML

21
Create template at project level
Create template at project level and subfolder for the applications.

Next we need to update settings.py to tell Django to look at the project-level for templates
TEMPLATES = [
{
...
'DIRS': [os.path.join(BASE_DIR, 'templates')],
...
},
]
Update views.py function
Update functions to return html page in response.
# pages/views.py
from django.shortcuts import render

# Create your views here.

from django.shortcuts import render


from django.http import HttpResponse # pages/urls.py
from django.urls import path
#def index(request):
# return HttpResponse('Hello, World using index!') #from .views import homePageView
# OR
def index(request): from . import views
return render(request,'pages/index.html')
urlpatterns = [
def about(request): path('', views.index, name='home'),
return HttpResponse('Hello, I am in About!') path('about/', views.about, name='about')
]

Note: change definition of about method also


Run.
base html page
We don’t want to repeat html, head, title etc in each page.
Create a common page and extend it in different pages.

Create base.html under templates folder

<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Django session</title>
</head>
<body>
{% block content %} {% endblock %}
</body>
</html>
Update html pages
<!– index.html --> <!– about.html -->

{% extends 'base.html' %} {% extends 'base.html' %}

{% block content %} {% block content %}


<H1>Home Page </H1> <H1>About Page </H1>
{% endblock %} {% endblock %}

Run and check the page source~


Static files and Path

All images, css, js files needed to refer into project can be treated as static
files.
Static files configuration
Create static folder inside project -> project app directory

Copy css, js, images folder into static


Update settings.py with static dir location
Open settings.py and go at the end
Create below variables. Collectstatic command looks for static dir location and once it find
then Django configure it as static location.
STATIC_URL = '/static/'
STATIC_ROOT = os.path.join(BASE_DIR,'static')
STATICFILES_DIRS = [
os.path.join(BASE_DIR,'helloworld/static')
]

$python manage.py help


Command to get list of staticfiles.
Collect Static
Ask Django to collect static files
$python manage.py collectstatic

You should see below output


139 static files copied to 'C:\Users\kunalpag\Documents\My_data\python-
proj\django\helloworld\static'.
Copy script and CSS Add CSS and script path in base html
Few of the path is invalid and thus we have to use the static to
find the files in static path.
{% load static %}
<!doctype html> <!doctype html>
<html lang="en"> <html lang="en">
<head> <title>Django session</title> <head> <title>Django session</title>

<!-- Font Awesome -->


<!-- Font Awesome -->
<link rel="stylesheet" href="{% static 'css/all.css' %}">
<link rel="stylesheet" href="assets/css/all.css">
<!-- Bootstrap -->
<!-- Bootstrap --> <link rel="stylesheet" href="{% static 'css/bootstrap.css' %}">
<link rel="stylesheet" href="assets/css/bootstrap.css"> <!-- Custom -->
<!-- Custom --> <link rel="stylesheet" href="{% static 'css/style.css' %}">
<link rel="stylesheet" href="assets/css/style.css"> <!-- Custom -->
</head> <link rel="stylesheet" href="{% static 'css/lightbox.min.css' %}">
<body> </head>
<body>
{% block content %} {% endblock %}
{% block content %} {% endblock %}
<script src="assets/js/jquery-3.3.1.min.js "></script>
<script src="{% static 'js/jquery-3.3.1.min.js' %}"></script>
<script src="assets/js/bootstrap.bundle.min.js "></script> <script src="{% static 'js/bootstrap.bundle.min.js' %}"></script>
<script src="assets/js/main.js "></script> <script src="{% static 'js/lightbox.min.js' %}"></script>
</body> <script src="{% static 'js/main.js' %}"></script></body>
</html> </html>
Add Navbar, header, footer
Update base.html code with Navbar, header and footer.
<section id="top-bar" class="p-3"> Top Bar
<div class="container">

<div class="row">

<div class="col-md-4">

<i class="fas fa-phone"></i> 94-555-55552

</div>

<div class="col-md-4">

<i class="fas fa-envelope-open"></i> [email protected]

</div>

<div class="col-md-4">

<div class="social text-right">

<a href="#">

<i class="fab fa-twitter"></i>

</a>

<a href="#">

<i class="fab fa-facebook"></i>

</a>

<a href="#">

<i class="fab fa-linkedin"></i>

</a>

<a href="#">

<i class="fab fa-instagram"></i>

</a>

</div>

</div>

</div>

</div>

</section>
<nav class="navbar navbar-expand-lg navbar-dark bg-primary sticky-top">

<div class="container">

<a class="navbar-brand" href="index.html"> navbar


<img src="assets/img/logo.png" class="logo" alt="">

</a>

<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarNavAltMarkup">

<span class="navbar-toggler-icon"></span>

</button>

<div class="collapse navbar-collapse" id="navbarNavAltMarkup">

<ul class="navbar-nav">

<li class="nav-item active mr-3">

<a class="nav-link" href="index.html">Home</a>

</li>

<li class="nav-item mr-3">

<a class="nav-link" href="about.html">About</a>

</li>

<li class="nav-item mr-3">

<a class="nav-link" href="listings.html">Featured Listings</a>

</li>

</ul>

<ul class="navbar-nav ml-auto">

<li class="nav-item mr-3">

<a class="nav-link" href="register.html">

<i class="fas fa-user-plus"></i> Register</a>

</li>

<li class="nav-item mr-3">

<a class="nav-link" href="login.html">

<i class="fas fa-sign-in-alt"></i>

Login</a>

</li>

</ul>

</div>

</div>

</nav>
URL linking
To link the page developer uses href with page name inside html.

To make it more dynamic and easy Django uses url

<a href="{% url 'index' %}">


<i class="fas fa-home"></i> Home</a>
Highlight the link in navbar
When we click on about link, still HOME link is active state.

The active link is depend on css class


<li class="nav-item active mr-3">
<a class="nav-link" href="{% url 'index' %}">Home</a>
</li>
<li class="nav-item mr-3">
<a class="nav-link" href="{% url 'about' %}">About</a>
</li>

To make a link active/inactive dynamically, we need to add if-else logic with Django code
Highlight the link in navbar cont..
<li
{% if '/' == request.path %}
class="nav-item active mr-3"
{% else %}
class="nav-item mr-3"
{% endif %}
>
<a class="nav-link" href="{% url 'index' %}">Home</a>
</li>
<li
{% if 'about' in request.path %}
class="nav-item active mr-3"
{% else %}
class="nav-item mr-3"
{% endif %}
>
New App – listing

As we have to list the homes or search with specific criteria. Better to have separate app.
Listing app
$python manage.py startapp listings

Create folder called listings inside template + create listing.html, listings.html


Create urls.py inside listings app
# pages/urls.py
from django.urls import path
from . import views
# /listings will be base URL i.e default
# /listings/20 listing with ID
urlpatterns = [
path('', views.index, name='listings'),
path('<int:listing_id>', views.listing, name='listing'),
path('search/', views.listing, name='search')
]
Add entry to main urls.py

Add new app entry in seetings.py


Django with mysql connection
Download mysql server
https://dev.mysql.com/downloads/mysql/
C:\Program Files\MySQL\MySQL Server 8.0

Start the service


Note : if you don’t know the root password facing error like (Cant find data directory) then, to create
data dir
C:\Program Files\MySQL\MySQL Server 8.0\bin>mysqld -u root --initialize-insecure
C:\Program Files\MySQL\MySQL Server 8.0\bin>mysqld.exe -u root --console
(it get the error then run as admin)
And then
Start the mysql client from another prompt
C:\Program Files\MySQL\MySQL Server 8.0\bin>mysql –u root
mysql> CREATE DATABASE restful_db;

mysql>use restful_db

mysql> CREATE TABLE product(


product_id INT(11) PRIMARY KEY AUTO_INCREMENT,
product_name VARCHAR(200),
product_price INT(11)
)ENGINE=INNODB;
Connect to mysql from django
If you face below error
Error: ER_NOT_SUPPORTED_AUTH_MODE: Client does not support authentication protocol
requested by server; consider upgrading MySQL client
Solution : ALTER USER 'root'@'localhost' IDENTIFIED WITH mysql_native_password BY 'password'

Where root as your user, localhost as your URL, and password as your password

Then run this query to refresh privileges:

flush privileges;

Try connecting using node/django after you do so.

If that doesn't work, try it without @'localhost' part.


Create DB, table and insert data
CREATE DATABASE restful_db;

CREATE TABLE product(


product_id INT(11) PRIMARY KEY AUTO_INCREMENT,
product_name VARCHAR(200),
product_price INT(11)
)ENGINE=INNODB;

INSERT INTO product(product_name,product_price) VALUES


('Product 1','2000'),
('Product 2','5000'),
('Product 3','4000'),
('Product 4','6000'),
('Product 5','7000');
pip install mysqlclient DB client installation

• If you face the below issue then download whl file


Issue : fatal error C1083: Cannot open include file: 'mysql.h': No such file or directory

Solution : download file from https://www.lfd.uci.edu/~gohlke/pythonlibs/#mysqlclient

File: mysqlclient-1.4.6-cp37-cp37m-win32.whl
Then
$pip install C:\\Users\\kunalpag\\downloads\\mysqlclient-1.4.6-cp37-cp37m-win32.whl

• If you face below error on linux


mysql_config not found pip linux
Then solution :sudo apt-get install libmysqlclient-dev
Create mysql database
C:\Program Files\MySQL\MySQL Server 8.0\bin>mysql -u root –p

mysql> create database djangodb


-> ;
Query OK, 1 row affected (0.01 sec)

mysql> show tables;


ERROR 1046 (3D000): No database selected
mysql> use djangodb;
Migrate and create super user
Access the database through mysql client
C:\Program Files\MySQL\MySQL Server 8.0\bin>mysql -u root –p

mysql> show tables;


+----------------------------+
| Tables_in_djangodb |
+----------------------------+
| auth_group |
| auth_group_permissions |
| auth_permission |
| auth_user |
| auth_user_groups |
| auth_user_user_permissions |
| django_admin_log |
| django_content_type |
| django_migrations |
| django_session |
+----------------------------+
10 rows in set (0.00 sec)

mysql> select * from auth_user;


Decide the DB table and attribute
As per the requirement Decide the DB table-Models and attribute-field
1) Listing
• Id, Title, address, price, bedroom, bathroom,sqfeet, listingdate, description, photo_main,
• foreign key from realtor-realtor ID
• Is_published (false by default)

2) Realtor
• Id, name, photo, description, email, phone, isBestSeller,

3) Contact
• Id, user_id, name, email, phone, isBestSeller, message, contact_date
• listing_id
Create listing model
• We can map DB table to models in python.
• Goto listing app-> models.py to write the model code
• Use documentation for the reference
https://docs.djangoproject.com/en/2.0/ref/models/fields/
from django.db import models
Create a model- Listing
from datetime import datetime
from realtors.models import Realtor sqft=models.Integer()
photo_main=models.ImageField(upload_to='photos
# Create your models here. /%Y/%m/%d/')

class Listing(models.Model): photo_1=models.ImageField(upload_to='photos/%Y


realtor=models.ForeignKey(Realtor, /%m/%d/',blank=True)
on_delete=models.DO_NOTHING)
photo_2=models.ImageField(upload_to='photos/%Y
title=models.CharField(max_length=100) /%m/%d/',blank=True)
address=models.CharField(max_length=100)
city=models.CharField(max_length=100) photo_3=models.ImageField(upload_to='photos/%Y
/%m/%d/',blank=True)
state=models.CharField(max_length=100)
zipcode=models.CharField(max_length=10) is_published = models.BooleanField(default=True)
description=models.TextField(blank=True) #optional list_date=models.DateTimeField(default=datetime.now
, blank=True)
prize=models.IntegerField()
bedrooms=models.IntegerField() def __str__(self):
bathrooms=models.DecimalField(max_digits=2, return self.title
decimal_places=1)
Create a model- Realtors
from django.db import models
from datetime import datetime
# Create your models here.
class Realtor(models.Model):
name = models.CharField(max_length=200)
photo = models.ImageField(upload_to='photos/%Y/%m/%d/')
description = models.TextField(blank=True)
phone = models.CharField(max_length=20)
email = models.CharField(max_length=20)
is_mvp = models.BooleanField(default=False)
hire_date=models.DateTimeField(default=datetime.now,blank=True)

def __str__(self):
return self.name
Models migration
These tables are just models in python.
They are not in DB yet- like we don’t have any table which represent the listing,relators.

To migirate the newly created models inside DB


1) Make migration
This will create a new migrations files inside app/ migrations folder

2) Migrate
This will connect to DB and write the content present in migrations folder
1) python manage.py makemigrations Migration commands
Migrations for 'realtors':
realtors\migrations\0001_initial.py
- Create model Realtor
Migrations for 'listings':
listings\migrations\0001_initial.py
- Create model Listing

2) python manage.py migrate


Apply all migrations: admin, auth, contenttypes, listings, realtors, sessions
Running migrations:
Applying realtors.0001_initial... OK
Applying listings.0001_initial... OK
Admin app
localhost:8000/admin

We don’t see any tables related to listing, relators models. Need to register the models in
admin.
# Open listings->admin.py Register the models

from django.contrib import admin


from .models import Listing

admin.site.register(Listing)

Save and refresh the admin page


Register realtors
from django.contrib import admin
from .models import Realtor

admin.site.register(Realtor)
Setting the media folder
Open setting files and define media folder path.

Go at the end.

#Media folder settings


MEDIA_ROOT = os.path.join(BASE_DIR,'media')
MEDIA_URL = '/media/' # just Like we did for static URL
To put the images into media folder we need to add configuration in urls.py
Update main urls.py

from django.contrib import admin


from django.urls import path,include
from django.conf import settings
from django.conf.urls.static import static

urlpatterns = [
# http://localhost:8000/
# http://localhost:8080/about
path('', include('pages.urls')),

# http://localhost:8000/listings/
# http://localhost:8000/listings/10
# http://localhost:8000/listings/search
# http://localhost:8000//search invalid
path('listings/', include('listings.urls')),

path('admin/', admin.site.urls),
] + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
Customize the Admin Area
Lets customize the admin page

Create admin folder inside templates


Create base_site.html

{% extends 'admin/base.html' %}
{% load static %}

{% block branding%}
<h1 id="head">
<img src="{% static 'img/logo.png' %}" alt="Real estate-admin page" class="brand_img" height="50"
width="80">
Real estate-admin page </h1>
{% endblock %}
Customize the Admin Area
Before After
Convert the pages from static to dynamic
Dynamic listings of properties
Convert listings of properties from static content to dynamic.

Steps needed to implement


1) Retrive data from backend
2) Pass data to view i.e html page
3) Print the data in html page
Dynamic listing cont.
How to pass the data from py file to html Print data received from py file
For test purpose display the data anywhere.

Open listings ->views.py Open listings ->listings.html

from django.shortcuts import render div class="col-md-12">


<h1 class="display-4">Browse Our Properties
def index(request): {{name}} </h1>
return render(request,'listings/listings.html', {'name':'Kunal'} ) <p class="lead"></p>
</div>
def listing(request):
return render(request,'listings/listing.html')
Dynamic listings of properties
Retrieve data from backend-DB

Listings-> view.py

from django.shortcuts import render


from .models import Listing

def index(request):
listings = Listing.objects.all()
context = {
'propListings' : listings
}
return render(request,'listings/listings.html',context)
Display the data i.e json array using loops. Dynamic listings of properties
<!-- Listings -->
<section id="listings" class="py-4">
Logic <div class="container">
<div class="row">
{% if propListings %}
<div class="row"> {% for listing in propListings %}
{% if propListings %} <div class="col-md-6 col-lg-4 mb-4">
<div class="card listing-preview">
{% for listing in propListings %} <img class="card-img-top"
<!-- Html code goes here --> src="assets/img/homes/home-1.jpg" alt="">
{% endfor %} <div class="card-img-overlay">
<h2>
{% else %} <span class="badge badge-secondary text-
<div class="col-md-12"> white">{{listing.prize}}</span>
<p>No listings available</p> </h2>
</div>
</div>
<div class="card-body">
{% endif %} <div class="listing-heading text-center">
</div> <h4 class="text-
primary">{{listing.address}}</h4>
<p>
Update few properties Dynamic listings of properties
<div class="row">
{% if propListings %}
{% for listing in propListings %}
<div class="col-md-6 col-lg-4 mb-4">
<div class="card listing-preview">
<img class="card-img-top" src="{{ listing.photo_main.url}}" alt="">
<div class="card-img-overlay">
<h2>
<span class="badge badge-secondary text-white"> {{ listing.prize}}
</span>
</h2>
</div>
<div class="card-body">
<div class="listing-heading text-center">
<h4 class="text-primary">{{ listing.title}}</h4>
<p>
<i class="fas fa-map-marker text-secondary"></i> {{ listing.address}}</p>
Lets put prize in correct format Dynamic listings of properties

Add humanize in settings ->installed App In listings.html code


INSTALLED_APPS = [
{% extends 'base.html' %}
'listings.apps.ListingsConfig', {% load humanize %}
'realtors.apps.RealtorsConfig', ……….
'pages.apps.PagesConfig', <div class="card-img-overlay">
'django.contrib.admin', <h2>
'django.contrib.humanize', <span class="badge badge-secondary text-white">{{ listing.prize |
intcomma}}</span> </h2>
] </div>
Dynamic listings of properties
Print time and realtor name

<div class="row py-2 text-secondary">


<div class="col-12">
<i class="fas fa-user"></i> {{listing.realtor}}</div>
</div>
<div class="row text-secondary pb-2">
<div class="col-6">
<i class="fas fa-clock"></i> {{ listing.list_date | timesince}} </div>
</div>
Single listing configuration
URL to single listing.html

<a href="listing.html" class="btn btn-primary btn-block">

Convert to
<a href="{% url 'listing' listing.id %}" class="btn btn-primary btn-block">More Info</a>
Home and About Dynamic part

Uptil now we had display home and about page with static content. Now lets move to
dynamic
Home.html (index.html) static code
{% extends 'base.html' %}

{% load static %}

{% block content %}

<!-- Showcase -->

<section id="showcase">

<div class="container text-center">

<div class="home-search p-5">

<div class="overlay p-5">

<h1 class="display-4 mb-4">

Property Searching Just Got So Easy

</h1>

<p class="lead">This is the home page of real estate. You can search the properties based on your requirement like search with aminities, number of bedroom, state wise search etc</p>

<div class="search">

<form action="search.html">

<!-- Form Row 1 -->

<div class="form-row">

<div class="col-md-4 mb-3">

<label class="sr-only">Keywords</label>

<input type="text" name="keywords" class="form-control" placeholder="Keyword (Pool, Garage, etc)">

</div>

<div class="col-md-4 mb-3">

<label class="sr-only">City</label>

<input type="text" name="city" class="form-control" placeholder="City">

</div>

<div class="col-md-4 mb-3">

<label class="sr-only">State</label>

<select name="state" class="form-control">

<option selected="true" disabled="disabled">State (All)</option>


about.html static code
{% extends 'base.html' %}

{% load static %}

{% block content %}

<section id="showcase-inner" class="py-5 text-white">

<div class="container">

<div class="row text-center">

<div class="col-md-12">

<h1 class="display-4">About Real Estate</h1>

<p class="lead">Welcome to Django real estate app</p>

</div>

</div>

</div>

</section>

<!-- Breadcrumb -->

<section id="bc" class="mt-3">

<div class="container">

<nav aria-label="breadcrumb">

<ol class="breadcrumb">

<li class="breadcrumb-item">

<a href="{% url 'index' %}">

<i class="fas fa-home"></i> Home</a>

</li>

<li class="breadcrumb-item active"> About</li>

</ol>

</nav>

</div>

</section>

<section id="about" class="py-4">


Index.html dynamic
pages/views.py
Up till now we have below code in pages/views.py
Task: We should use listings model to retrieve top 3 published listing and display it in home page.
Yes its possible to use models created in different application to another application.

from django.shortcuts import render

from django.shortcuts import render


from django.http import HttpResponse

def index(request):
return render(request,'pages/index.html')

def about(request):
#return HttpResponse('Hello, I am in About!')
return render(request,'pages/about.html')
Index page dynamic
pages/views.py

from django.shortcuts import render


from django.http import HttpResponse

from listings.models import Listing


def index(request):
listings = Listing.objects.order_by('-list_date').filter(is_published=True)[:3]
context = {
'homePropListings' : listings
}
return render(request,'pages/index.html',context)
Index listing dynamic html page
section id="listings" class="py-2">

<div class="container">

<h3 class="text-center mb-3">Latest Listings</h3>

<div class="row">

{% if homePropListings %}

{% for singleProp in homePropListings %}

<div class="col-md-6 col-lg-4 mb-4">

<div class="card listing-preview">

<img class="card-img-top" src="{{ singleProp.photo_main.url }}" alt="" height="250" width="250">

<div class="card-img-overlay">

<h2>

<span class="badge badge-secondary text-white">{{ singleProp.prize }}</span>

</h2>

</div>

<div class="card-body">

<div class="listing-heading text-center">

<h4 class="text-primary">{{ singleProp.title }}</h4>

<p>

<i class="fas fa-map-marker text-secondary"></i> {{ singleProp.address }} , {{ singleProp.city }}, {{ singleProp.state }}, {{ singleProp.zipcode }}</p>

</div>

<hr>

<div class="row py-2 text-secondary">

<div class="col-6">

<i class="fas fa-th-large"></i> Sqft: {{ singleProp.sqft}}</div>

<div class="col-6">

<i class="fas fa-car"></i> Gallary: {{singleProp.gallary}}</div>

</div>

<div class="row py-2 text-secondary">

<div class="col-6">

<i class="fas fa-bed"></i> Bedrooms: {{ singleProp.bedrooms}}</div>

<div class="col-6">

<i class="fas fa-bath"></i> Bathrooms: {{ singleProp.bathrooms}}</div>

</div>
Output index html
Now we have latest 3 listing order by date in home page
About us page dynamic
Task : Up till now we displayed realter info (Our team) and seller of the month as static
content. Now make it dynamic.
About page views.py dynamic
Retrieve the realtors information and best player of the month from DB and pass it to
about.html page
pages/views.py

def about(request):
#return HttpResponse('Hello, I am in About!')
#Get all realtors
allRealtors = Realtor.objects.order_by('-hire_date')

#Seller of the month (most valuable player)


mvp_realtors = Realtor.objects.all().filter(is_mvp=True)

context = {
'allRealtors' : allRealtors,
'mvp_realtors' : mvp_realtors
}

return render(request,'pages/about.html',context)
templates/pages/about.html About page html dynamic

{% extends 'base.html' %}
{% load static %}
{% block content %}
<section id="showcase-inner" class="py-5 text-white">
<div class="container">
<div class="row text-center">
<div class="col-md-12">
<h1 class="display-4">About Real Estate</h1>
<p class="lead">Welcome to Django real estate app</p>
</div>
</div>
</div>
</section>

<!-- Breadcrumb -->


<section id="bc" class="mt-3">
<div class="container">
<nav aria-label="breadcrumb">
<ol class="breadcrumb">
<li class="breadcrumb-item">
Single Listing Page
Listings/Listing should give complete information about selected property.
Go to listings and click on more info.
Account App – Authentication, register and login
Create new App. Account app
$python manage.py startapp accounts
As we know Django has user table already in placed. Lets use it.
Register and login templates

Create accounts folder and few files


Register and login templates

Create urls.py inside accounts app.

# accounts/urls.py
from django.urls import path
from . import views
urlpatterns = [
path('login', views.login, name='login'),
path('register', views.register, name='register'),
path('logout', views.logout, name='logout'),
path('dashboard', views.dashboard, name='dashboard'),
]
Register and login views
Define methods in views.py

from django.shortcuts import render, redirect

def register(request):
return render(request,'accounts/register.html')

def login(request):
return render(request,'accounts/login.html')

def logout(request):
return redirect('index')

def dashboard(request):
return render(request,'accounts/dashboard.html')
Open settings.py and add entry of the app 'accounts' Accounts app settings
INSTALLED_APPS = [
'listings.apps.ListingsConfig',
'accounts.apps.AccountsConfig',
'realtors.apps.RealtorsConfig',
….
]

Register urls.py of accounts in main urls.py


Main app folder/urls.py

urlpatterns = [
path('', include('pages.urls')),
path('listings/', include('listings.urls')),
path('accounts/', include('accounts.urls')),
path('admin/', admin.site.urls),
]
Now update/verify register and login link
Register and login links
base.html

<ul class="navbar-nav ml-auto">


<li class="nav-item mr-3">
<a class="nav-link" href= "{% url 'register' %}" >
<i class="fas fa-user-plus"></i> Register</a>
</li>
<li class="nav-item mr-3">
<a class="nav-link" href= "{% url 'login' %}" >
<i class="fas fa-sign-in-alt"></i>Login</a>
</li>
</ul> Click on login will redirect to this page
Make login and register links active/inactive
Register and login template
Copy login and registration template code from html/css theme. Register and login template
Add base html entry.
login.html <div class="form-group">
<label for="password2">Password</label>
{% extends 'base.html'%} <input type="password" name="password"
{% block content %} class="form-control" required>
<section id="login" class="bg-light py-5"> </div>
<div class="container">
<input type="submit" value="Login" class="btn btn-
<div class="row">
secondary btn-block">
<div class="col-md-6 mx-auto">
</form>
<div class="card"> </div>
<div class="card-header bg-primary text-white"> </div>
<h4> </div>
<i class="fas fa-sign-in-alt"></i> Login</h4> </div>
</div> </div>
<div class="card-body"> </section>
<form action="index.html">
<div class="form-group">
<label for="username">Username</label>
<input type="text" name="username" class="form-control"
required>
</div>
Copy login and registration template code from html/css theme. Register and login template
Add base html entry. <div class="form-group">
Register.html
<label for="email">Email</label>
{% extends 'base.html'%}
<input type="email" name="email" class="form-
{% block content%}
control" required>
</div>
<section id="register" class="bg-light py-5">
<div class="form-group">
<div class="container">
<label for="password2">Password</label>
<div class="row">
<input type="password" name="password"
<div class="col-md-6 mx-auto">
<div class="card">
class="form-control" required>
<div class="card-header bg-primary text-white">
</div>
<h4>
<div class="form-group">
<i class="fas fa-user-plus"></i> Register</h4> <label for="password">Confirm Password</label>
</div> <input type="password" name="password2"
<div class="card-body"> class="form-control" required>
<form action="index.html"> </div>
<div class="form-group"> <input type="submit" value="Register" class="btn btn-
<label for="username">Username</label> secondary btn-block">
<input type="text" name="username" class="form-control" required> </form>
</div> </div>
<div class="form-group"> </div>
<label for="email">Email</label> </div>
<input type="email" name="email" class="form-control" required> </div>
</div> </div>
</section>
Register form action
Register get request url will display the register page.
When register form gets submitted we need POST request to register page
Also add CSRF token for security precaution

<form action="{% url register' %}" method="POST">


{% csrf_token %}
<div class="form-group">
<label for="username">Username</label>
<input type="text" name="username" class="form-control" required>
</div>
login form action
Register get request url will display the register page.
When register form gets submitted we need POST request to register page
Also add CSRF token for security precaution

<form action="{% url 'login' %}" method="POST">


{% csrf_token %}
<div class="form-group">
<label for="username">Username</label>
<input type="text" name="username" class="form-control" required>
</div>
Check CSRF token
Open inspect element (ctrl+shitft+I on chrome)
Check hidden token
Add get/post login in register login view function
accounts/views.py

def register(request):
if request.method == 'POST':
print("Submitted reg page")
return redirect('register')
else:
return render(request,'accounts/register.html')

#fill register form and sumit it. output of print will be displayed on command line
# Apply same thing for registration
Partials
Base.html code usually gets messy with html,bootstrap,css code. Partials
• Create separate folder called partials and divide the base page into different pages likes navbar, topbar etc.
Partial file convention is _filename,html
• Cut the code the topbar,navbar, footer from base.html to these files.
• Add load static into each partial file
{% load static %}
• Modify base.html – add include statements.
<!-- top bar -->
{% include 'partials/_topbar.html' %}

<!-- nav bar -->


{% include 'partials/_navbar.html' %}

<!-- Main content -->


{% block content %} {% endblock %}

<!-- nav bar -->


{% include 'partials/_footer.html' %}
{% load static %}
<!doctype html> Base.html after partials
<html lang="en">
<head> <meta charset="utf-8"> <title>Django session</title>
<link rel="stylesheet" href="{% static 'css/all.css' %}"> <link rel="stylesheet" href="{% static 'css/bootstrap.css' %}">
<link rel="stylesheet" href="{% static 'css/style.css' %}"> <link rel="stylesheet" href="{% static 'css/lightbox.min.css' %}">
</head>
<body>
<!-- top bar -->
{% include 'partials/_topbar.html' %}
<!-- nav bar -->
{% include 'partials/_navbar.html' %}
<!-- Main content -->
{% block content %} {% endblock %}
<!-- nav bar -->
{% include 'partials/_footer.html' %}

<script src="{% static 'js/jquery-3.3.1.min.js' %}"></script>


<script src="{% static 'js/bootstrap.bundle.min.js' %}"></script>
<script src="{% static 'js/lightbox.min.js' %}"></script>
<script src="{% static 'js/main.js' %}"></script>

</body> </html>
Django Message framework

Django comes with inbuilt message app.

https://docs.djangoproject.com/en/3.1/ref/contrib/messages/

Quite commonly in web applications, you need to display a one-time notification message
(also known as “flash message”) to the user after processing a form or some other types of
user input.

For this, Django provides full support for cookie- and session-based messaging, for both
anonymous and authenticated users. The messages framework allows you to temporarily
store messages in one request and retrieve them for display in a subsequent request (usually
the next one). Every message is tagged with a specific level that determines its priority (e.g.,
info, warning, or error).
Update settings.py with message framework configuration
• Go at the end of file and add below configuration.

from django.contrib.messages import constants as messages


MESSAGE_TAGS = {
messages.ERROR: 'danger'
}

• Message app is default app and you can see entry in Installed_app array
'django.contrib.messages',
# Lets write alert message in separate file
# templates/partial/_alert.html
alert.html file
{% if messages %}
{% for message in messages %}
<div id="message" class="container">
<div class="alert alert={{ message.tags }} alert-dismissible text-center" role="alert">
<button type="button" class="close" data-dismiss="alert"><span aria-
hidden="true">&times;</span></button>
<strong>
{% if message.level == DEFAILT_MESSAGE_LEVELS_ERROR %}
Error
{% else %}
{{ message.tags|title }}
{% endif %}
</strong>
{{ message }}
</div>
</div>
{% endfor %}
{% endif %}
Update views.py
Update view.py code, send dummy message as of now

def register(request):
if request.method == 'POST':
print("Submitted reg page")
messages.error(request,"Testing error message")
return redirect('register')
else:
return render(request,'accounts/register.html')
Update register.html
Display the error message somewhere in register page

<div class="card-body">
<!-- Alerts -->
{% include 'partials/_alert.html' %}
<form action="{% url 'register' %}" method="POST">
{% csrf_token %}
Registration
Write basic code to validate if username exists in DB already, password/confirm pass do not
match etc.
For sample test create one user in DB from admin app
Lets work on registration code – accounts/view.py Registration
function – register
# Password match
if(password1==password2):
from django.shortcuts import render,redirect # Check Username
from django.contrib import messages if User.objects.filter(username=username).exists():
messages.error(request,'The username is not
from django.contrib.auth.models import User
available')
def register(request): return redirect('register')
if request.method == 'POST': else:
# Get form values if User.objects.filter(email=email).exists():
messages.error(request,'The Email
#first_name=request.POST['first_name']
ID is not available')
#last_name=request.POST['last_name'] return redirect('register')
username=request.POST['username'] else:
email=request.POST['email'] #Good to go
return
password1=request.POST['password1']
else:
password2=request.POST['password2'] messages.error(request,'Password do not match')
return redirect("register")
else:
return render(request,'accounts/register.html')
Test the registration code
Save the user registered user into DB
Its time to save the use details into DB and redirect the page to login.

else:
if User.objects.filter(email=email).exists():
messages.error(request,'The Email ID is not available')
return redirect('register')
else:
# Looks good, data entered by user is valid
user = User.objects.create_user(username=username,password=password1,
email=email)
user.save()
messages.success(request,"You are now registered and can login")
return redirect('login')
After user successfully registered

User 'Tejas' got added


Alert in home page.
Go to home page (index.html) and include alert message incase needed to print.

<!-- Alert -->


{% include 'partials/_alert.html' %}
<!-- Listings -->
<section id="listings" class="py-5">
……
Validate username and password with backend Login
accounts/views.py

from django.shortcuts import render,redirect


from django.contrib import messages,auth
from django.contrib.auth.models import User
def login(request):
if request.method == 'POST':
username = request.POST['username']
password = request.POST['password']
user = auth.authenticate(username=username, password=password)

if user is not None:


auth.login(request,user)
messages.success(request, "You are now logged in")
return redirect('dashboard')
else:
messages.error(request,'Invalid username/password')
return redirect('login')
else:
return render(request,'accounts/login.html')
Login with invalid password Login test

Login with valid password


Logout and auth handling
Update the dashboard.html with html content.

{% extends 'base.html'%}

{% block content %}
Update dashboard html code
<section id="showcase-inner" class="py-5 text-white">
<section id="dashboard" class="py-4">
<div class="container">
<div class="container">
<div class="row text-center"> <div class="row">
<div class="col-md-12">
<div class="col-md-12">
<h1 class="display-4">Dashboard- Real Estate</h1>

<p class="lead">This is sample dashboard page of real estate.</p>


<h2>Welcome John</h2>
</div> <p>Here are the property listings that you have
</div> inquired about</p>
</div>

</section>
<table class="table">
<thead>
<!-- Breadcrumb --> <tr>
<section id="bc" class="mt-3">
<th scope="col">#</th>
<div class="container">

<nav aria-label="breadcrumb">
<th scope="col">Property</th>
<ol class="breadcrumb"> <th></th>
<li class="breadcrumb-item">
</tr>
<a href="index.html">

<i class="fas fa-home"></i> Home</a>


</thead>
</li> <tbody>
<li class="breadcrumb-item active"> About</li> <tr>
</ol>
<td>22</td>
</nav>

</div>
<td>45, Hadapsar road</td>
</section> <td>
<a class="btn btn-light" href="#">View
Listing</a>
If user is logged in then we have to show logout link otherwise register and login link should be displayed. Update navbar
<ul class="navbar-nav ml-auto">
{% if user.is_authenticated %}
login authentication check worked.
{% else %}
<li {% if 'register' in request.path %} class="nav-item active mr-3"
{% else %} class="nav-item mr-3"
{% endif %}
>
<a class="nav-link" href="{% url 'register' %}">
<i class="fas fa-user-plus"></i> Register</a>
</li>
<li {% if 'login' in request.path %} class="nav-item active mr-3"
{% else %} class="nav-item mr-3"
{% endif %}
>
<a class="nav-link" href="{% url 'login' %}">
<i class="fas fa-sign-in-alt"></i> Login</a>
</li>
{% endif %}
</ul>
Logout
We cant just add logout link and use it as get request.
We have to submit a form so that we can handle the logout and perform the logout with
POST.
{% if user.is_authenticated %}
# Some message
# Display the dashboard menu like welcome message and logout link
{% else %}
Display welcome message once logged in. Logout continue
<ul class="navbar-nav ml-auto">
{% if user.is_authenticated %}
<li
{% if 'dashboard' in request.path %}
class="nav-item active mr-3"
{% else %}
class="nav-item mr-3"
{% endif %}
>
Welcome {{user.username}}
<a class=nav-link href="{% url 'dashboard' %}"> Dashboard
</a>
</li>

{% else %}
<li
{% if 'register' in request.path %}
<ul class="navbar-nav ml-auto">
{% if user.is_authenticated %}
Logout link
<li
{% if 'dashboard' in request.path %} class="nav-item active mr-3"
{% else %} class="nav-item mr-3"
{% endif %}
>
<a class=nav-link href="{% url 'dashboard' %}"> Welcome {{user.username}} Dashboard </a>
</li>
<li class="nav-item mr-3">
<a href="javascript:{document.getElementById('logout').submit()}"class="nav-link">
<i class="fas fa-sign-out-alt"></i>logout
</a>
<form action="{% url 'logout'%}" method="POST" id="logout">
{% csrf_token %}
<input type="hidden">
</form>
</li>
{% else %}
Logout code
accounts/views.py

def logout(request):
if request.method == 'POST':
auth.logout(request)

return redirect('index')
Contacts
- Create new app Contacts app
$python manage.py startapp contacts

- Write model contacts/model.py


Contacts registration
Create new entry of app contacts into settings.py

Add entry to admin.py


Migrate Contacts
C:\Users\kunalpag\Documents\My_data\python-proj\django\helloworld>python manage.py
makemigrations contacts
Migrations for 'contacts':
contacts\migrations\0001_initial.py
- Create model Contact

C:\Users\kunalpag\Documents\My_data\python-proj\django\helloworld>python manage.py
migrate contacts
Operations to perform:
Apply all migrations: contacts
Running migrations:
Applying contacts.0001_initial... OK
Django errors and resolution
How To Add New Model Field To Exist Django Model
1. Change Django Model Field Steps.
Change model class field in Django application models.py file. Below example add a new field user_desc =
models.CharField(max_length=100, default=”), and remove field emp_onboard_date =
models.DateTimeField(auto_now=True).

class Employee(models.Model): ......


#emp_onboard_date = models.DateTimeField(auto_now=True)
user_desc = models.CharField(max_length=100, default='') ......

2. Better specify a default value for the new field, otherwise you may encounter below error message
when you make migrations.
$ python3 manage.py makemigrations dept_emp
You are trying to add a non-nullable field ' user_desc ' to employee without a default; we can't do that
(the database needs something to populate existing rows).
Please select a fix:
• 1) Provide a one-off default now (will be set on all existing rows with a null value for this column)
• 2) Quit, and let me add a default in models.py
Select an option:
How To Add New Model Field To Exist Django Model

3. Make migration output


$ python3 manage.py makemigrations dept_emp
Migrations for 'dept_emp':
dept_emp/migrations/0004_auto_20190228_0617.py
- Remove field emp_onboard_date from employee
- Add field user_desc to employee
4. Execute migrate command
$ python3 manage.py migrate dept_emp
Operations to perform:
Apply all migrations: dept_emp
Running migrations:
Applying dept_emp.0004_auto_20190228_0617... OK
Drop Table from Admin backend
Remove the table with SQL query first by using mysql prompt.

1. Comment all/Remove the TestModel class definition in dept_emp / models.py file.


- Remove entry from admin.py also
2. Go to the Django project root folder in a terminal and run makemigrations command on
the dept_emp application to check model class changes.
$ python3 manage.py makemigrations dept_emp
Migrations for 'dept_emp':
dept_emp/migrations/0009_delete_testmodel.py
- Delete model TestModel
Note : if you don’t see above message then remove entry of app from admin.py also
3. Run migrate command to apply the model changes.
Drop All Model Tables In One Django Application.

If you want to remove all the model related talbes in the backend. Remove it from backend using mysql.
Run
$ python3 manage.py makemigrations dept_emp
$ python3 manage.py migrate dept_emp zero
But during above process, you may encounter error message like django.db.utils.IntegrityError: NOT NULL
constraint failed: dept_emp_employee.dept_id.
To resolve above error, you need to delete all the past migration generated python files in
the dept_emp / migrations folder, but do not remove the 0001_initial.py file.
Then again run
$ python3 manage.py makemigrations dept_emp
$ python3 manage.py migrate dept_emp zero

Help:https://www.dev2qa.com/how-to-drop-change-tables-from-sqlite3-database-in-django/
Django hosting
Create account on
https://www.pythonanywhere.com/user/kunalkp6/

You might also like