周末整理旧日志发现在 2013 年学习 Django 时写的 《Django:快速搭建简单的 Blog》一文得到不少网友的引用,激励了我的创作热情。所以就把旧文重新写一下,毕竟现在的 Django 已经更新到 3.1.1 版本了。
本文分两部分:
第一部分是 介绍如何在 Ubuntu 20.04 上搭建 Django 开发环境;
第二部分是 介绍快速地使用 Django 构建一个简单的 Blog ,供入门参考。
一,在 Ubuntu 20.04 搭建 Django 开发环境 1.
1. 设置 Python
Ubuntu 20.04 中,默认的 Python 版本为 Python3, 在终端只能通过 python3 命令调用 Python 解释器,不能像以往的 Ubuntu 发行版本那样直接通过 python 命令调用。
检查 python 命令:
所以,为了方便后续工作可以为 Python3 创建符号链接把 python3 配置为直接通过 python 命令调用。
使用以下命令为 Python3 创建一个符号链接:
$ sudo update-alternatives --install /usr/bin/python python /usr/bin/python3 1
复制代码
至此,Python3 的配置已经完成。
2. Pip 包管理程序的安装与配置
使用 apt 命令安装 python3-pip:
$ sudo apt install python3-pip -y
复制代码
python3-pip 安装完毕后,把 pip3 设置为默认的 pip 版本:
$ sudo update-alternatives --install /usr/bin/pip pip /usr/bin/pip3 1
复制代码
检查 pip 的版本:
3. 使用 Virtualenv 安装 Django
安装 Django 框架的方式有多种,本人推荐使用 Virtualenv 虚拟环境安装。因为在以后的开发中,不同的应用可能需要不同的 Python 开发环境,而 Virtualenv 可以用来为应用创建一套“隔离”的 Python 运行环境,而不会干扰到系统中其他的 Python 应用。
安装 Python virtualenv 包:
$ sudo pip install virtualenv
复制代码
注意:如果由于某些不可以描述的原因导致 pip 安装缓慢,可以尝试临时修改源的方法:
在使用 pip 的时候在后面加上-i 参数,指定 pip 源。
例如,对上面的命令指定临时源:
$ sudo pip install virtualenv -i https://pypi.tuna.tsinghua.edu.cn/simple
复制代码
国内的一些源:
根据个人需要,选择合适的目录创建 Python 虚拟环境 my_env。
我这里的选择的目录是: /home/matrix/Workspace/Python/Virtualenv
创建 Python 虚拟环境:
$ cd ~/Workspace/Python/Virtualenv
$ virtualenv myenv
复制代码
激活虚拟环境:
$ cd my_env
$ source bin/active
复制代码
安装 2.2 LTS 版本的 Django 框架:
$ pip install django==2.2
复制代码
检查 Django 版本:
看到以上的版本号输出,说明已经安装成功了。
若想切换为正常的用户环境,可以使用以下的命令:
二,快速构建简单的 Blog
按第一部分的介绍搭建好 Django 的开发环境后,接下来将介绍如何快速地创建一个 Blog。
1. 创建名为 my_site 的工程项目
使用 django-admin.py 工具创建工程项目:
$ django-admin.py startproject mysite
复制代码
项目的文件结构如下:
manage.py : Django 项目里面的工具,通过它可以调用 Django Shell 和数据库等。
settings.py : 包含了项目的默认设置,包括数据库信息,调试标志以及其他一些工作的变量。
urls.py : 项目的 URL 声明,就像你网站的 “目录” ,负责把 URL 模式映射到应用程序。
init.py : 一个空文件,告知 Python 当前目录应被认为是一个 Python 包。
wsgi.py : 作为你的项目的运行在 WSGI 兼容的 Web 服务器上的入口。
2. 运行开发服务器
切换到工程项目里,执行以下指令运行开发服务器:
$ python manage.py runserver
复制代码
然后打开浏览器,在地址栏输入 127.0.0.1:8000
访问站点。
3. 创建 Blog 应用
在 mysite 目录下,使用 manage.py 创建 blog 应用:
$ python manage.py startapp blog
复制代码
blog 应用的文件结构如下:
4. 设计 Blog 应用的 Model
在 blog 目录下的 models.py 是 blog 应用的核心文件之一,是定义 blog 数据结构的地方。
用编辑器打开 models.py ,新添加 BlogPost 类,代码如下:
from django.db import models
from django.contrib.auth.models import User
STATUS = (
(0,"Draft"),
(1,"Publish")
)
class Post(models.Model):
title = models.CharField(max_length=200, unique=True)
slug = models.SlugField(max_length=200, unique=True)
author = models.ForeignKey(User, on_delete= models.CASCADE,related_name='blog_posts')
updated_on = models.DateTimeField(auto_now= True)
content = models.TextField()
created_on = models.DateTimeField(auto_now_add=True)
status = models.IntegerField(choices=STATUS, default=0)
class Meta:
ordering = ['-created_on']
def __str__(self):
return self.title
复制代码
5.设置数据库
Dajango 支持主流的数据库服务器(MySQL,PostgreSQL,Oracle 和 MSSQL),但本项目使用 SQLite,这里之需要通过一条简单的命令可以创建 SQLite 数据库。
在终端 切换到工程主目录 mysite/下,执行如下命令:
$ python manage.py makemigrations
$ python manage.py migrate
复制代码
运行上述的数据迁移指令后,会生成框架自带的相关数据表和 我们自己创建的 Post 数据表。
创建后台管理员账号:
$ python manage.py createsuperuser
复制代码
在浏览器地址栏输入:127.0.0.1:8000/admin
成功登录有就会见到后台管理界面:
6. 把 Post 模型添加到管理员后台
打开 blog/admin.py 文件,注册 BlogPost 模型:
from django.contrib import admin
from .models import Post
# Register your models here.
admin.site.register(Post)
复制代码
保存文件,刷新管理员后台页面:
7. 添加文章
点击 Posts 右侧的 Add 按钮,添加文章。
修改 blog/admin.py 文件,为它添加一个 admin.ModelAdmin 的子类 BlogPostAdmin.以列表形式显示 BlogPost 的标题和时间,可以让 admin 的 BlogPost 界面更加美观。
原来的代码:
from django.contrib import admin
from .models import Post
# Register your models here.
admin.site.register(Post)
复制代码
修改后的代码:
from django.contrib import admin
from .models import Post
class PostAdmin(admin.ModelAdmin):
list_display = ('title', 'slug', 'status','created_on')
list_filter = ("status",)
search_fields = ['title', 'content']
prepopulated_fields = {'slug': ('title',)}
admin.site.register(Post, PostAdmin)
复制代码
刷新页面后,可看到效果:
8. 创建 Blog 的视图
从 Django 的角度看,一个页面具有三个典型的组件:
一个模板(template):模板负责把传递进来的信息显示出来。
一个视图(viw):视图负责从数据库获取需要显示的信息。
一个 URL 模式:它负责把收到的请求和你的试图函数匹配,有时候也会向视图传递一些参数。
编辑视图:
打开 blog/views.y ,并编辑:
from django.views import generic
from .models import Post
class PostList(generic.ListView):
queryset = Post.objects.filter(status=1).order_by('-created_on')
template_name = 'index.html'
class PostDetail(generic.DetailView):
model = Post
template_name = 'post_detail.html'
复制代码
在 blog 应用目录创建 urls.py 文件,然后编辑它。
为视图添加 URL 模式:
blog/urls.py
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path('admin/', admin.site.urls),
path('', include('blog.urls')),
]
复制代码
9. 为视图创建模版
在工程目录创建 templates 文件夹:
然后打开 mysite /settings.py 文件,在 BASE_DIR 底下 添加模版路径:
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
# Add 'TEMPLATE_DIRS' here
'DIRS': [TEMPLATES_DIR],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
复制代码
在 templates 文件夹里面,创建 base.html 文件:
<!DOCTYPE html>
<html>
<head>
<title>Matrix Tech</title>
<link
href="https://fonts.googleapis.com/css?family=Roboto:400,700"
rel="stylesheet">
<meta name="google" content="notranslate" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<link
rel="stylesheet"
href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css"
integrity="sha384-Gn5384xqQ1aoWXA+058RXPxPg6fy4IWvTNh0E263XmFcJlSAwiGgFAW/dAiS6JXm"
crossorigin="anonymous"
/>
</head>
<body>
<style>
body {
font-family: "Roboto", sans-serif;
font-size: 17px;
background-color: #fdfdfd;
}
.shadow{
box-shadow: 0 4px 2px -2px rgba(0,0,0,0.1);
}
.btn-danger {
color: #fff;
background-color: #f00000;
border-color: #dc281e;
}
.masthead {
background:#3398E1;
height: auto;
padding-bottom: 15px;
box-shadow: 0 16px 48px #E3E7EB;
padding-top: 10px;
}
</style>
<!-- Navigation -->
<nav class="navbar navbar-expand-lg navbar-light bg-light shadow" id="mainNav">
<div class="container-fluid">
<a class="navbar-brand" href="{% url 'home' %}" >Matrix Tech</a>
<button
class="navbar-toggler navbar-toggler-right"
type="button"
data-toggle="collapse"
data-target="#navbarResponsive"
aria-controls="navbarResponsive"
aria-expanded="false"
aria-label="Toggle navigation"
>
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="navbarResponsive">
<ul class="navbar-nav ml-auto">
<li class="nav-item text-black">
<a
class="nav-link text-black font-weight-bold"
href="#"
>About</a
>
</li>
<li class="nav-item text-black">
<a
class="nav-link text-black font-weight-bold"
href="#"
>Policy</a
>
</li>
<li class="nav-item text-black">
<a
class="nav-link text-black font-weight-bold"
href="#"
>Contact</a
>
</li>
</ul>
</div>
</div>
</div>
</nav>
{% block content %}
<!-- Content Goes here -->
{% endblock content %}
<!-- Footer -->
<footer class="py-3 bg-grey">
<p class="m-0 text-dark text-center ">Copyright © Matrix Tech</p>
</footer>
</body>
</html>
复制代码
在 templates 文件夹里面,创建 index.html 文件:
{% extends "base.html" %}
{% block content %}
<style>
body {
font-family: "Roboto", sans-serif;
font-size: 18px;
background-color: #fdfdfd;
}
.head_text{
color: white;
}
.card{
box-shadow: 0 16px 48px #E3E7EB;
}
</style>
<header class="masthead" >
<div class="overlay"></div>
<div class="container">
<div class="row">
<div class=" col-md-8 col-md-10 mx-auto">
<div class="site-heading">
<h3 class=" site-heading my-4 mt-3 text-white"> 欢迎访问我的博客 </h3>
<p class="text-light">Write the Code. Change the World.  
</p>
</div>
</div>
</div>
</div>
</div>
</header>
<div class="container">
<div class="row">
<!-- Blog Entries Column -->
<div class="col-md-8 mt-3 left">
{% for post in post_list %}
<div class="card mb-4" >
<div class="card-body">
<h2 class="card-title">{{ post.title }}</h2>
<p class="card-text text-muted h6">{{ post.author }} | {{ post.created_on}} </p>
<p class="card-text">{{post.content|slice:":200" }}</p>
<a href="{% url 'post_detail' post.slug %}" class="btn btn-primary">Read More →</a>
</div>
</div>
{% endfor %}
</div>
{% block sidebar %}
{% include 'sidebar.html' %}
{% endblock sidebar %}
</div>
</div>
{%endblock%}
复制代码
在 templates 文件夹里面,创建 sidebar.html 文件:
{% block sidebar %}
<style>
.card{
box-shadow: 0 16px 48px #E3E7EB;
}
</style>
<!-- Sidebar Widgets Column -->
<div class="col-md-4 float-right ">
<div class="card my-4">
<h5 class="card-header">About Us</h5>
<div class="card-body">
<p class="card-text"> Hi, 我是 Matrix, 一名全栈工程师, 熟悉前后端开发和运维各个环节.</p>
<a href=""
class="btn btn-danger">Know more!</a>
</div>
</div>
</div>
{% endblock sidebar %}
复制代码
在浏览器访问 http://127.0.0.1:8000/
创建 post_detail.html 文件
mysite/templates/post_detail.html
{% extends 'base.html' %} {% block content %}
<div class="container">
<div class="row">
<div class="col-md-8 card mb-4 mt-3 left top">
<div class="card-body">
<h1>{% block title %} {{ object.title }} {% endblock title %}</h1>
<p class=" text-muted">{{ post.author }} | {{ post.created_on }}</p>
<p class="card-text ">{{ object.content | safe }}</p>
</div>
</div>
{% block sidebar %} {% include 'sidebar.html' %} {% endblock sidebar %}
</div>
</div>
{% endblock content %}
复制代码
点击页面文章摘要下的 Read More 可以访问 Post 的详细内容:
后记
此教程可以作为 Django 入门练习,通过教程可以学会在 Ubuntu 上搭建 Django 开发环境,以及如何使用 Django 框架。教程是采用『线索性』书写方式,跟着教程一步步练习最终就会搭建出如封面图的简易博客。由于此教程只是展示如何简单入门,所以很多开发细节被忽略,如果希望进一步了解 Django 的使用可以参阅 Django 官方手册。
源代码地址: https://github.com/matrixtechxyz/Django_Mysite
评论