用 Django搭建博客项目

转载自:http://blog.****.net/SKI_12/article/details/78505235

Django是基于Python的高级Web开发框架。本篇文章进行的是简单的功能的实现,后续会进行安全工具相应的开发。

下面只大致说下过程,具体的实现看源代码即可。


安装:

pip install Django==1.11.4

或直接到Github下载源代码安装

确认是否安装:python –m Django –version


创建新项目:

django-admin startproject djangotest

cd djangotest/

ls

用 Django搭建博客项目


项目目录结构如图:

用 Django搭建博客项目

manage.py:与项目进行交互的命令行工具集的入口,即项目管理器,可执行python manage.py来查看所有命令

启动服务:python manage.py runserver 8080

Django shell:python manage.py shell,自动引入项目环境,可以通过其与项目交互进行测试


djangotest目录为一个容器,包含项目的一些基本配置。


wsgi.py:Python Web Server Gateway Interface(Python服务器网关接口),即Python应用与Web服务器之间的接口。


urls.py:URL配置文件


settings.py:

BASE_DIR指定项目根目录。

SECRET_KEY即**,项目启动时需要用到。

DEBUG即调试,在测试时用。

ALLOWED_HOSTS即允许访问的主机名,当列表中包含localhost值时即只允许通过localhost的主机名进行访问。

INSTALLED_APPS即已安装的应用,若自己创建了新的应用则添加进去。

MIDDLEWARE即中间件,是Django自带的工具集。

ROOT_URLCONF即URL配置文件,指向urls.py文件。

TEMPLATES即模板,即关于模板的配置,模板简单地说即HTML文件。

WSGI_APPLICATION

DATABASES,数据库配置。

AUTH_PASSWORD_VALIDATORS和密码认证相关。

LANGUAGE_CODE语言编码,默认为en-us。

TIME_ZONE时区,默认为UTC。

USE_I18N

USE_L10N

USE_TZ

STATIC_URL


__init__.py:Python中声明模块的文件,默认内容为空。


创建应用:

新建blog应用:python manage.py startapp blog

接着将新建的应用添加到settings.py的INSTALLED_APPS中:

用 Django搭建博客项目


应用目录:
用 Django搭建博客项目

migrations:数据移植模块,内容自动生成

admin.py:应用的后台管理系统配置

apps.py:当前应用的配置,在Django-1.9后才自动生成

models.py:数据模块,使用ORM框架

tests.py:自动化测试模块,可再次编写测试脚本

views.py:执行响应的代码所在模块,是代码进行逻辑处理的地方,项目中大部分代码在此编写


编写views.py:

每个响应对应一个函数,因而每个函数必须返回一个响应。

函数必须有一个参数,一般约定为request。

每一个响应或函数对应一个URL。

用 Django搭建博客项目



添加内容到urls.py文件:

用 Django搭建博客项目


启动服务:python manage.py runserver 1234

访问相应的目录:

用 Django搭建博客项目


第二种配置url的方法,如注释所说:

用 Django搭建博客项目


直接修改相应的部分:

用 Django搭建博客项目


然后在blog目录下新建urls.py文件:

用 Django搭建博客项目

注意:url函数中的目录名后要添加/,否则容易出错。

再度访问:

用 Django搭建博客项目


Templates模板:

HTML文件,使用Django模板语言(Django Template Language,DTL),也可以使用第三方模板

开发模板的步骤:

1、在根目录下创建Templates目录

用 Django搭建博客项目

2、在该目录下创建HTML文件

用 Django搭建博客项目

3、在views.py中返回render()

用 Django搭建博客项目

访问:

用 Django搭建博客项目

注意点:Django会按照INSTALLED_APPS中的添加顺序来查找Templates。

解决Templates冲突的方法:在Templates目录下创建以APP名为名称的目录并将HTML文件放入新创建的目录中。


另一种创建templates目录是创建在项目的根目录中而不是在应用的目录中,然后再在该目录下创建和应用名一样的目录,再在其中创建html文件即可,注意一点的是,此时因为是创建在项目根目录中,需要在settings.py文件中设置:

用 Django搭建博客项目


Models:

通常一个Model对应数据库的一张表,是以类的形式表现出来的。

示例的models.py文件:

用 Django搭建博客项目


创建步骤:

1、在根目录下创建models.py,并引入models模块

2、创建类,继承models.Model,该类即是一张数据表

3、在类中创建字段

生成数据表:

python manage.py makemigrations app名(可选)

python manage.py migrate

用 Django搭建博客项目


查看:

在根目录的migrations目录中生成移植文件:

用 Django搭建博客项目

用 Django搭建博客项目

可以看到id字段是自动生成的主键,因为在初始创建字段时并没有指定主键。


查看SQL语句:python manage.py sqlmigrate 应用名 文件id

用 Django搭建博客项目


这里使用的是默认的sqlite3数据库,其在根目录中保存为db.sqlite3,查看其需要特定的软件,这里就不下载安装了:

用 Django搭建博客项目


页面呈现数据:

后台修改views.py,添加数据保存到数据库并从数据库读取数据返回到前端:

用 Django搭建博客项目

注意,这里添加id=10的参数是为了每次调用都是进行相同的内容进行替换保存,以避免每调用一次就新增一项数据。


前端修改index.html:

模板直接使用对象以及对象的“.”操作,如{{ article.title }}

用 Django搭建博客项目


最后访问页面即可:

用 Django搭建博客项目


Admin:

Django自带的自动化数据管理界面,被授权的用户可直接在admin中管理数据库。

配置admin:

创建超级用户:python manage.py createsuperuser


访问添加输入admin/目录即可:

用 Django搭建博客项目



可以将页面的英文修改为中文,到settings.py的LANGUAGE_CODE默认的‘en-us’改为‘zh-hans’即可:

用 Django搭建博客项目


配置应用:

在admin.py中引入自身的models模块

编辑admin.py:

用 Django搭建博客项目


刷新页面:

用 Django搭建博客项目


修改数据:

用 Django搭建博客项目

再访问:

用 Django搭建博客项目


修改数据默认名称:

用 Django搭建博客项目

接着在Article类下添加一个方法,根据Python版本,若为3以上版本则使用__str__(self)方法,若为2系列版本则使用__unicode__(self)方法,添加这个方法是为了在查询时实现相应的内容,这里是实现将显示的内容从对象改为文章标题:

用 Django搭建博客项目

再次查看:

用 Django搭建博客项目


改进:

在admin.py中添加ArticleAdmin类并通过list_display来设置文章列表显示页面中显示的列的内容:

用 Django搭建博客项目

用 Django搭建博客项目


完善Blog开发:

namespace与name参数的注意点:

1、写在include()的第二个参数位置,namespace=’blog’

先在djangotest/djangotest/urls.py的include()函数中添加namespace参数:

用 Django搭建博客项目


2、应用下则写在url()的第三个参数位置,name=’article_page’

然后到djangotest/blog/urls.py中的url()函数中添加name参数:

用 Django搭建博客项目

主要取决于是否使用include引用另一个url配置文件。


最后在HTML文件中:

template中超链接href可以用“{% url ‘app_name:url_name’ param %}”

app_name和url_name都在urls.py中配置

用 Django搭建博客项目


Blog编写页面:添加了编辑、删除、返回主页、登出等链接,具体看代码。


认证登录:

contrib模块:django.contrib.auth,默认的认证框架。

创建users:

1、示例代码如下:

[python] view plain copy
  1. from django.contrib.auth.models import User  
  2. user = User.objects.create_user(‘admin’, ‘[email protected]123.com’, ‘password’)  

2、python manage.py createsuperuser


修改密码:

1、python manage.py changepassword username

2、示例代码如下:

[python] view plain copy
  1. from django.contrib.auth.models import User  
  2. u = User.objects.get(username=’admin’)  
  3. u.set_password(‘newpassword’)  
  4. u.save()  


认证Users:authenticate(username=’admin’, password=’password’),成功则返回User对象,否则返回None。

Web请求中的认证:request.user.is_authenticated()

登录用户:login(request, user),需要先进行认证

登出用户:logout(request)

只允许用户登录访问:

1、检查request.user.is_authenticated()

2、login_required装饰器


先创建一个member应用,在settings.py中添加应用名,然后创建forms.py:

用 Django搭建博客项目

主要是创建用户名和密码的表单类,其中Django用widget来定义数据项的格式,这里为密码格式的文本字段。

然后创建urls.py文件:

用 Django搭建博客项目

在views.py中编写用户登录的方法user_login()。

接着对之前blog应用的views.py中的方法调用login_required()方法进行装饰:

用 Django搭建博客项目

然后再在urls.py中配置一下url即可完成登录相关的功能。


代码实现:

这里重新新建项目来实现博客系统完整的搭建。

整个项目目录架构如下:

用 Django搭建博客项目


blog目录:

admin.py:

[python] view plain copy
  1. from django.contrib import admin  
  2.   
  3. from models import Article  
  4.   
  5. # Register your models here.  
  6. class ArticleAdmin(admin.ModelAdmin):  
  7.     """docstring for ArticleAdmin"""  
  8.     list_display = ('title''content''pub_time')  
  9.     list_filter = ('pub_time',)  
  10.           
  11. admin.site.register(Article, ArticleAdmin)  


models.py:

[python] view plain copy
  1. from __future__ import unicode_literals  
  2.   
  3. from django.db import models  
  4.   
  5. # Create your models here.  
  6. class Article(models.Model):  
  7.     title = models.CharField(max_length=32, default='title')  
  8.     content = models.TextField(null=True)  
  9.     pub_time = models.DateTimeField(null=True)  
  10.   
  11.     def __unicode__(self):  
  12.         return self.title  


urls.py:

[python] view plain copy
  1. from django.conf.urls import url  
  2.   
  3. from . import views  
  4.   
  5. urlpatterns = [  
  6.     url(r'^index/$', views.index, name='index'),  
  7.     url(r'^article/(?P<article_id>[0-9]+)$', views.article_page, name='article_page'),  
  8.     url(r'^edit/(?P<article_id>[0-9]+)$', views.edit_page, name='edit_page'),  
  9.     url(r'^change/$', views.change, name='change'),  
  10.     url(r'^delete/(?P<article_id>[0-9]+)$', views.delete_page, name='delete_page'),  
  11. ]  


views.py:

[python] view plain copy
  1. from django.shortcuts import render  
  2. from django.http import HttpResponse  
  3. from django.contrib.auth.decorators import login_required  
  4.   
  5. from . import models  
  6.   
  7. # Create your views here.  
  8. @login_required  
  9. def index(request):  
  10.     articles = models.Article.objects.all()  
  11.     return render(request, 'blog/index.html', {'articles':articles})  
  12.  
  13. @login_required  
  14. def article_page(request, article_id):  
  15.     article = models.Article.objects.get(pk=article_id)  
  16.     return render(request, 'blog/article_page.html', {'article':article})  
  17.  
  18. @login_required  
  19. def edit_page(request, article_id):  
  20.     if str(article_id) == '0':  
  21.         return render(request, 'blog/edit_page.html')  
  22.     article = models.Article.objects.get(pk=article_id)  
  23.     return render(request, 'blog/edit_page.html', {'article':article})  
  24.  
  25. @login_required  
  26. def change(request):  
  27.     title = request.POST.get('title''TITLE')  
  28.     content = request.POST.get('content''CONTENT')  
  29.     article_id = request.POST.get('article_id''0')  
  30.     if article_id == '0':  
  31.         models.Article.objects.create(title=title, content=content)  
  32.         articles = models.Article.objects.all()  
  33.         return render(request, 'blog/index.html', {'articles':articles})  
  34.   
  35.     article = models.Article.objects.get(pk=article_id)  
  36.     article.title = title  
  37.     article.content = content  
  38.     article.save()  
  39.     return render(request, 'blog/article_page.html',  {'article':article})  
  40.  
  41. @login_required  
  42. def delete_page(request, article_id):  
  43.     models.Article.objects.filter(pk=article_id).delete()  
  44.     articles = models.Article.objects.all()  
  45.     return render(request, 'blog/index.html', {'articles':articles})  


member目录:

forms.py:

[python] view plain copy
  1. from django import forms  
  2.   
  3. class LoginForm(forms.Form):  
  4.     username = forms.CharField()  
  5.     password = forms.CharField(widget=forms.PasswordInput)  
  6.           


urls.py:

[python] view plain copy
  1. from django.conf.urls import url  
  2. from django.contrib.auth import views as auth_views  
  3.   
  4. from . import views  
  5.   
  6. urlpatterns = [  
  7.     url(r'^$', views.user_login, name='login'),  
  8.     url(r'^logout-then-login/$', auth_views.logout_then_login, name='logout_then_login'),  
  9. ]  


views.py:

[python] view plain copy
  1. from __future__ import unicode_literals  
  2.   
  3. from django.shortcuts import render  
  4. from django.http import HttpResponseRedirect  
  5. from django.contrib.auth import authenticate, login  
  6. from django.contrib import messages  
  7.   
  8. from .forms import LoginForm  
  9.   
  10. # Create your views here.  
  11. def user_login(request):  
  12.     login_form = LoginForm()  
  13.     if request.method == 'POST':  
  14.         form = LoginForm(request.POST)  
  15.         if form.is_valid():  
  16.             cd = form.cleaned_data  
  17.             user = authenticate(username=cd['username'], password=cd['password'])  
  18.             if user is not None:  
  19.                 if user.is_active:  
  20.                     login(request, user)  
  21.                     return HttpResponseRedirect('/blog/index')  
  22.                 else:  
  23.                     messages.error(request, "Your username and password didn't match.")  
  24.                     return HttpResponseRedirect('/')  
  25.             else:  
  26.                 messages.error(request, "Your username and password didn't match.")  
  27.                 return HttpResponseRedirect('/')  
  28.     else:  
  29.         return render(request, 'login/user_login.html', {'login_form':login_form})  


myBlog目录:

urls.py:

[python] view plain copy
  1. from django.conf.urls import url, include  
  2. from django.contrib import admin  
  3.   
  4. urlpatterns = [  
  5.     url(r'^admin/', admin.site.urls),  
  6.     url(r'^blog/', include('blog.urls', namespace='blog')),  
  7.     url(r'^', include('member.urls', namespace='member')),  
  8.     url(r'^accounts/login/', include('member.urls')),  
  9. ]  


settings.py中修改几个地方即可:

用 Django搭建博客项目

用 Django搭建博客项目

用 Django搭建博客项目


templates目录:

login目录:

user_login.html:

[html] view plain copy
  1. <!DOCTYPE html>  
  2. <head>  
  3. <meta charset="utf-8"/>  
  4. <title>MyBlog</title>  
  5. </head>  
  6. <body class="login">  
  7. <h2>MyBlog——简单的博客系统</h2>  
  8. <div>  
  9.     <form action="{% url 'member:login' %}" method="post">  
  10.         <h3>Login to your account</h3>  
  11.         {% if messages %}  
  12.         <h5>  
  13.             {% for message in messages %}  
  14.                 {{ message }}  
  15.             {% endfor %}  
  16.         </h5>  
  17.         {% endif %}  
  18.         <div>  
  19.             <label>Username</label>  
  20.             <div>  
  21.                 <input type="text" autocomplete="off" placeholder="Username" name="username"/>  
  22.             </div>  
  23.         </div>  
  24.         <br/>  
  25.         <div >  
  26.             <label>Password</label>  
  27.             <div>  
  28.                 <input type="password" autocomplete="off" placeholder="Password" name="password"/>  
  29.             </div>  
  30.         </div>  
  31.         <br/>  
  32.         {% csrf_token %}  
  33.         <div>  
  34.             <button type="submit">  
  35.             Login  
  36.             </button>  
  37.         </div>  
  38.     </form>  
  39. </div>  
  40. <br>  
  41. <div class="copyright">  
  42.      2017 &copy; SKI12  
  43. </div>  
  44. </body>  
  45. </html>  


blog目录:

index.html:

[html] view plain copy
  1. <!DOCTYPE html>  
  2. <html>  
  3. <head>  
  4.     <title>MyBlog</title>  
  5. </head>  
  6. <body>  
  7. <h1>MyBlog</h1>  
  8. <a href="{% url 'blog:edit_page' 0 %}">编写博客</a>  
  9. <p>博客列表</p>  
  10. {% for article in articles %}  
  11.     <a href="{% url 'blog:article_page' article.id %}">{{ article.title }}</a>  
  12.     <br/>  
  13. {% endfor %}  
  14. <br>  
  15. <a href="{% url 'member:logout_then_login' %}">Logout</a>  
  16. </body>  
  17. </html>  


article_page.html:

[html] view plain copy
  1. <!DOCTYPE html>  
  2. <html>  
  3. <head>  
  4.     <title>Article Page</title>  
  5. </head>  
  6. <body>  
  7. <h1>{{ article.title }}</h1>  
  8. <br/>  
  9. <h3>{{ article.content }}</h3>  
  10. <br/>  
  11. <br/>  
  12. <a href="{% url 'blog:edit_page' article.id %}">Edit</a>  
  13. <a href="{% url 'blog:delete_page' article.id %}">Delete</a>  
  14. <a href="{% url 'blog:index'%}">Home</a>  
  15. <a href="{% url 'member:logout_then_login' %}">Logout</a>  
  16. </body>  
  17. </html>  


edit_page.html:

[html] view plain copy
  1. <!DOCTYPE html>  
  2. <html>  
  3. <head>  
  4.     <title>Edit Page</title>  
  5. </head>  
  6. <body>  
  7. <form action="{% url 'blog:change' %}" method="post">  
  8.     {% csrf_token %}  
  9.     <input type="hidden" name="article_id" value="{{ article.id | default:'0' }}">  
  10.     <label>文章标题  
  11.         <input type="text" name="title" value="{{ article.title }}" />  
  12.     </label>  
  13.     <br/>  
  14.     <label>文章内容  
  15.         <input type="text" name="content" value="{{ article.content }}">  
  16.     </label>  
  17.     <br/>  
  18.     <input type="submit" value="提交">  
  19. </form>  
  20. <br/>  
  21. <div>  
  22.     <a href="{% url 'blog:index'%}">Home</a>  
  23.     <a href="{% url 'member:logout_then_login' %}">Logout</a>  
  24. </div>  
  25. </body>  
  26. </html>  


最终的超简版博客系统效果如图:

首先访问的时候需要登录:

用 Django搭建博客项目

登录成功后转到blog主页:

用 Django搭建博客项目

点击编写博客进入编辑页面:

用 Django搭建博客项目

点击博客文章查看博客:

用 Django搭建博客项目

简易的功能完成了,后面就进一步进行安全开发。