用vscode+django搭建自己的博客

1. 写在前面

自己是一只工科狗,正在自学python,想找些项目去做做,就心血来潮的想搭个自己的博客,一路摸爬滚打终于搞出个最基本的版本,把这些心得分享出来,对于自己也是一个很好的回顾与总结的过程。
这个教程的前提环境是python3+vscode,两者的下载与配置搜索网上其他教程即可。
十分感谢以下三篇参考博客给我的莫大帮助:
最主要:python+django搭建博客
vscode配置django环境;
mysql安装教程

2. 基本环境配置

2.1 MySQL安装与配置

●官网下载最新版本
推荐MySQL community server 8版本。建议配合上述的MySQL安装教程一起使用。

●配置my.ini文件
采用解压的方式安装的MySQL是没有自动配置相关文件的,需要手动配置。在安装的根目录新建一个空白的my.ini文件,在其中写入如下代码,其中basedir和datadir是你安装的目录:

[mysqld]
port=3306
basedir=D:\mysql8
datadir=D:\mysql8\Data
max_connections=200
max_connect_errors=10
character-set-server=utf8mb4
default-storage-engine=INNODB
default_authentication_plugin=mysql_native_password
[mysql]
default-character-set=utf8mb4
[client]
port=3306
default-character-set=utf8mb4

●初始化MySQL
以管理员身份运行cmd(在C:\Windows\System 32中右键cmd),并打开MySQL安装的根目录,输入命令:mysqld --initialize --console。系统会生成一段临时密码,注意保存这段临时密码(不包含首位空格),之后需要用到。

●安装+启动MySQL服务
安装:mysqld --install
启动:net start mysql
关闭:net stop mysql

●连接MySQL与修改密码
连接使用Navicat(中文破解版),新建一个连接,配置如下:

配置项内容
连接名随便写
主机名localhost
端口3306
用户名root
密码刚才的那段临时密码

注意:在配置时可能会出现此报错:your password has expired.To log in you must change itusing a client that supports expired passwords。出现此问题的原因是MySQL的密码默认是有时限的,过了时间密码就会过期。解决方法如下:
打开cmd,进入MySQL的安装目录,输入mysql -uroot -p,系统会让你输入密码,输入临时密码后即进入MySQL中。
修改密码:ALTER USER 'root'@'localhost' IDENTIFIED BY ' ';
密码不过期:alter user 'root'@'localhost'password expire never;
退出:exit();
再用Navicat连接即可成功。

2.2 django安装与配置

●建立虚拟环境
新建myBlog文件夹,在cmd中打开该文件,输入:D:\python37\Scripts\virtualenv.exe django_env
前面的目录是你python的目录
●安装django
cd django_env\Scripts 打开环境激活目录
activate激活
pip install django 安装django
●vscode配置
在myBlog文件下建立blog文件夹,在vscode中打开blog文件夹,点击配置项目,会生成两个配置文件:
launch.json 添加一个端口:Alt
setting.json 添加python的启动地址:
Alt
注:上图中的地址并不是该项目的地址,按照自己的设置进行配置,且注意是双斜杠而不是单斜杠。

●测试
点击运行,成功后在网页中输入127.0.0.1:8080,可以看到网页已经成功显示了出来。

3. 建立博客应用

在完成了准备工作后,现在开始正式的用django进行博客的搭建了。
首先在blog文件夹中(在cmd中打开)建立项目与应用:
python manage.py startproject blog 建立项目
python manage.py startapp blogapp 建立应用
myBlog文件夹的目录结构如下:

Alt在blog\setting.py中,找到INSTALLED_APPS,将新建的应用加入:

INSTALLED_APPS = [    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',    
    'django.contrib.sessions',    
    'django.contrib.messages',    
    'django.contrib.staticfiles',    
    'blogapp',
    ]

4. 建立数据库模型

4.1 设计数据库表结构

博客的文章包含了各种基本信息:标题、正文、作者、发布时间,它还应该有对应的分类和一些标签,初级版本就只囊括这些基本要素。其对应关系为:一篇文章只对应一个分类,但是可以有多个标签。接下来就要创建文章、分类、标签这三个大类。

4.2 编写对应代码

创建不同数据库表的操作都在blogapp/models.py中。以分类为例:

from django.db import models

class Category(models.Model):
	name = models.CharField(max_length=100)

Category就是分类的数据库表,它继承了models.Model类,CharField是django定义的一种数据类型,是字符型的一种,一般用来储存较短的字符串,max_length参数规定了允许存储的最大数量。
完整的建立如下:

from django.db import models
from django.contrib.auth.models import User

class Category(models.Model):
	name = models.CharField(max_length=100)

class Tag(models.Model):
	name = models.CharField(max_length=100)

class Post(models.Model):
	title = models.CharField(max_length=70)
	body = models.TextField()
	created_time = models.DateTimeField()
	modified_time = models.DateTimeField()
	excerpt = models.CharField(max_length=200,blank=True)
	category = models.ForeignKey(Category,on_delete=models.CASCADE)
	tags = models.ManyToManyField(Tag,blank=True)
	author = models.ForeignKey(User,on_delete=models.CASCADE)			

简单解释一下Post类中的代码:
Post类定义了(从上到下):标题、正文、创建时间、修改时间、摘要、分类、标签、作者;TextField相比于CharField可存储更多的文本,DateTimeField为存储时间的数据类型;
blank=True允许空值的出现;
ForeignKey为一对多或多对一的关联关系,一篇文章只有一个作者和一个分类,但是一个作者或一个分类可以对应很多文章,一般在’多’的类中定义’一’,on_delete参数代表在删除一模型对象时会对相关联的多对象执行什么操作,默认为级联删除models.CASCADE,表示当删除一时,对应的多都会被删除。ManyToManyField表示多对多的级联关系;
django.contrib.auth为django内置应用,用于处理网站用户注册登录等,User是已经写好的用户模块。

4.3 迁移数据库

先将数据库设置为MySQL,即更改blog/settings.py的配置:

DATABASES = { 
	'default': {  
	'ENGINE': 'django.db.backends.mysql',  
	'NAME': 'django',  #数据库名字  
	'USER': 'root',   #账号  
	'PASSWORD': '123456',  #密码  
	'HOST': '127.0.0.1', #IP  
	'PORT': '3306', #端口 
	}
}

同时在blogapp/init.py中更改:

import pymysql
pymysql.install_as_MySALdb()

执行迁移数据库命令,在cmd中打开myBlog/blog文件夹,分别运行:

python manage.py makemigrations
python manage.py migrate

第一个命令的作用会在blogapp/migrations文件夹下生成0001_initial.py文件,是django用来记录对模型做了哪些修改的文件。
第二个命令通过检验migrations文件夹下的内容来得知我们对数据库的操作,并转化为数据库语言作用于MySQL。在该命令中,我们可以发现它除了对我们自己写的应用进行了操作,还对其他内置应用进行了操作,具体地可以在之前地INSTALLED_APPS里找到。

4.4 对数据进行读取等操作

接下来,实际上已经可以在其中读写数据了,此处不多赘述,有想做一些基本了解的,可以参考python+django搭建博客的4.3-4.4部分。

5. 制作博客的首页视图

5.1 django处理HTTP请求

这一节大家只需要看看就好,因为之后会使用模板,写这一节的目的是让大家了解django的HTTP处理机理。
这一步主要包括:django如何接收HTTP请求;如何处理HTTP请求;如何生成HTTP响应。
1.绑定url和视图函数
django通过blogapp/urls.py(需要自己新建,注意不要和blog/urls.py混淆,这个是整个工程的配置文件)来接收并处理用户的HTTP请求,该文件中记录了不同网址及其所对应的处理函数。当用户访问某个网址时,django就会在这个文件中找对应的网址,如果找到了就会调用对应的处理函数(又被叫做视图函数)。具体做法如下:

from django.conf.urls import url
from . import views

urlpatterns = [
	url(r'^$',views.index,name='index'),
]

urlpatterns中记录了各种网址及其对应的视图函数,url函数则将两者绑定在一起,第一个参数为正则表达式,对于我们的本地开服务器域名,如:http://127.0.0.1:8080,当输入后,django会将协议、域名和端口号都去掉,此时只剩一个空字符串,而该正则正是匹配空字符串的意思(以空字符串开头和结尾),二者匹配后就会调用views.index中的视图函数,name为视图函数定义了一个名字。
2. 编写视图函数
接下来就要编写上面说的views.index视图函数了,视图函数在blogapp/views.py中:

from django.shortcuts import HttpResponse

def index(request):
	return HttpResponse('Welcome!')

这就是视图函数的基本机理:request参数是django为我们封装的HttpRequest类的一个实例,是HTTP请求;HttpResponse是HTTP响应的封装类,我们只需要传入想表达的文字就好。
3. 配置URL
之前我们创建了urls.py文件,也绑定了URL与index,接下来要让django知道我们执行了这些操作,在之前说的blog/urls.py中写下如下代码:

from django.contrib import admin
from django.conf.urls import url,include

urlpatterns = [
	url('admin/',admin.site.urls),
	url('',include('blogapp.urls')),
]

url函数的若干参数拼合起来就是完整的路径,因此就在系统urls中配置了blogapp下的urls。
4. 运行
两种方法都可以运行服务器:
运行python manage.py runserver
在vscode中打开myBlog/blog文件夹,按F5编译

5.2 使用django模板系统

我们现在已经完成了对博客的基本搭建,但是这样构建的太过简单,为了实现一些华丽的视觉效果,我们需要用到django的模板系统。我们可以把大段的文本写到一个文件里,然后django自行读取并把内容传给HttpResponse。下一章我们将结合模板来做出我们的页面。

6. 基于模板制作首页视图

再次回忆如何基于django制作首页视图:配置url–>绑定url和视图函数–>在系统urls文件中引入–>基于模板编写视图函数–>返回HTTP响应。接下来我们基于这个思路去实现我们的首页视图。

6.1 首页的视图函数

首页的视图函数如下:

from django.shortcuts import render
from .models import Post

def index(request):
	post_list = Post.objects.all().order_by('-created_time')
	return render(request,'blog/index.html',{'post_list':post_list})

objects是django内自定义的模型类的对象,数据类型是QuerySet,即查询集,这种数据类型能够提高查询效率。
第一行代码的意思就是通过all()从数据库获取了所有文章,再通过order_by进行排序,排序字段是created_time,同时负号代表逆序排列(一般来说博客文章列表是按照发布时间倒序排列的)。
第二行代码中,render()的作用是给定一个模板和上下文字典,返回一个模板渲染后的HttpResponse对象。

6.2 处理静态文件

博客模板采用网上的一套:点击下载。下载后把它放在blogapp/static/blog下(需要新建),我们要对它进行一系列的设置。
首先需要告诉django在哪里找模板,在settings.py中的TEMPLATES里,将’DIRS’补全:

...
'DIRS':[os.path.join(BASE_DIR,'blogapp','static')],
...

我们可以看到,把DIRS中的路径和上面render函数第二个参数的路径连起来就是我们模板实际的绝对路径了,这样django就可以找到模板在哪里了。
接下来我们需要更改静态文件的加载路径,否则浏览器中显示的样式会非常混乱。打开模板文件中的index.html文件,找到head标签包裹的内容(对这部分代码看不懂的同学可以看一下css的基本语法,最基本的不是很难),改为:

{% load staticfiles %} 
<!DOCTYPE html>
<html>
<head>
	<title>Black & White</title>
	
	<!-- meta --> 
	<meta charset="UTF-8"> 
	<meta name="viewport" content="width=device-width, initial-scale=1">
	
	<!-- css -->
	<link rel="stylesheet" href="{% static 'blog/css/bootstrap.min.css' %}" rel="external nofollow" rel="external nofollow" >
	<link rel="stylesheet" href="http://code.ionicframework.com/ionicons/2.0.1/css/ionicons.min.css" rel="external nofollow" rel="external nofollow" rel="external nofollow" >
	<link rel="stylesheet" href="{% static 'blog/css/pace.css' %}" rel="external nofollow" rel="external nofollow" >
	<link rel="stylesheet" href="{% static 'blog/css/custom.css' %}" rel="external nofollow" >
	
	<!-- js -->
	<script src="{% static 'blog/js/jquery-2.1.3.min.js' %}"></script> 
	<script src="{% static 'blog/js/bootstrap.min.js' %}"></script> 
	<script src="{% static 'blog/js/pace.min.js' %}"></script> 
	<script src="{% static 'blog/js/modernizr.custom.js' %}"></script>
</head> 
<body> 
<!-- 其它内容 --> 
<script src="{% static 'blog/js/script.js' %}"></script> 
</body>
</html>

顶部的{% load staticfiles%}就是加载静态文件的代码,此外,我们可以看到href标签中被{%%}包裹起来的部分,这样改才可以正确引入路径。

6.3 修改模板

接下来我们需要在首页显示我们写的文章,具体做法就是使用之前传入的post_list变量,找到index.html的article标签,只留一个article标签,使用for循环把每篇文章都调用出来:

...
{% for post in post_list %}
	<article class="post post-{{ post.pk }}">
	... 
	</article>
{% empty %} 
	<div class="no-post">暂时还没有发布的文章</div>
{% endfor %}
	...

pk是primary key的缩写,即每篇post所对应的索引值,我们无需显式定义,django会自动为我们添加。
对于标题,我们这样修改:

<h1 class="entry-title"> 
	<a href="single.html" rel="external nofollow" >{{ post.title }}</a>
</h1>

对于其他span标签,即分类、发布时间、作者、评论和阅读量5个,做如下修改,评论和阅读不动,暂时无法更换:

<div class="entry-meta">
<span class="post-category"><a href="#">{{ post.category.name }}</a></span>
<span class="post-date"><a href="#"><time class="entry-date"
datetime="{{ post.created_time }}">{{ post.created_time }}</time></a></span> 
<span class="post-author"><a href="#">{{ post.author }}</a></span>
<span class="comments-link"><a href="#">4 评论</a></span>
<span class="views-count"><a href="#">588 阅读</a></span>
</div>                                                                   

摘要做如下修改:

<div class="entry-content clearfix"> 
<p>{{ post.excerpt }}</p> 
<div class="read-more cl-effect-14"> 
<a href="#" class="more-link">继续阅读 <span class="meta-nav">→</span></a> 
</div>
</div>

7. 在django Admin后台发布文章

我们可以在django自带的Admin后台来发布我们自己的博客文章,只需要做一些设置即可。

7.1 注册模型

首先在cmd中输入python manage.py createsuperuser,创建超级用户(具体操作可参照网上)。
之后需要在后台注册好我们创建的模型,即在blogapp/admin.py中输入:

from django.contrib import admin
from .models import Post,Category,Tag

admin.site.register(Post)
admin.site.register(Category)
admin.site.register(Tag)

之后就可以运行开发服务器了,输入127.0.0.1:8080/admin/,就进入到后台页面,可以增加分类、标签和文章,自行尝试一下就好。

7.2 定制Admin后台

当然,我们可以对admin有自定义的设置,比如希望它可以显示文章的详细信息,那么在admin.py添加如下代码:

from django.contrib import admin
from .models import Post,Category,Tag

class PostAdmin(admin.ModelAdmin):
	list_display = ['title','created_time','modified_time','category','author']
	
admin.site.register(Post,PostAdmin)
admin.site.register(Category)
admin.site.register(Tag)

这样可以看到它能够显示文章的详细信息。

8. 博客文章详情页

做完首页后,我们可以继续制作详情页了,开发流程是一样的。

8.1 设置详情页url

对于详情页来说,每篇文章都对应了一个URL。即网站域名/post/1就是第一篇文章内容,以此类推,以这个规则在blogapp/urls.py中绑定URL和视图函数(这些操作是固定搭配,一般直接拿来用就好):

from django.conf.urls import url
from . import views
app_name = 'blogapp'

urlpatterns = [
	url(r'^$',views.index,name='index'),
	url(r'^post/(?P<pk>[0-9]+)/$',views.detail,name='detail'),
	]

第二个url函数中的正则表达式,表示以post/开头,后面至少跟一个一位的数字,并且以/符号结尾。同时括号内表示命名捕获组,作用是把url中的指定字符串捕获并传给detail函数。
app_name则是视图函数命名空间,用来区分不同的视图函数。
为了能够按照规则生成每篇文章的url,我们可以在models.py中对Post类增加一个方法,具体为:

from django.urls import reverse

class Post(models.Model):
	...
	def get_absolute_url(self):
		return reverse('blogapp:detail',kwargs={'pk':self.pk})

reverse函数的作用是解析视图函数的URL,第一个参数指定了视图函数,由于我们在detail函数中指定了替换准则,因此每篇文章的id会被pk所替换,从而生成自己的URL。

8.2 编写detail视图函数

detail视图函数在blogapp/views.py中编写:

from django.shortcuts import get_object_or_404
...
def detail(request,pk):
	post = get_object_or_404(Post,pk=pk)
	return render(request,'blog/detail.html',{'post':post})

detail视图函数和index函数类似,很容易理解。也就是说,详情页的流程是这样的:当用户输入一个网址时,url函数将pk值捕获,传入视图函数,查找数据库中是否存在这样的pk值所对应的网页,如果有则显示页面,没有则返回404页面。同时,在Post类中定义一个获得全路径的方法get_absolute_url,便于静态文件的编写。

8.3 编写详情页模板

把模板中的single.html改为detail.html,与index页面一样,需要进行一些改写。可以发现,如果我们有很多这样的页面,那么每次都修改一遍,会非常麻烦,但是我们可以采用模板继承的方法来消除重复操作。

8.4 模板继承

我们发现,index.html和detail.html文件除了main标签包裹的部分不同外,其他地方都是相同的,那么我们就可以把相同部分都放在base.html中,这样就可以省略很多重复操作。我们在同级目录下新建base.html文件,并将index.html的内容都拷进来,然后删除main标签内的内容,替换为:

...
<main class="col-md-8"> 
{% block main %} 
{% endblock main %}
</main>
<aside class="col-md-4"> 
{% block toc %} 
{% endblock toc %} 
...
</aside>
...

block的作用就是占位,想不明白的话把它想象成类的继承与重写就可以。这样,当子类(之后说到的index.html和detail.html)块内写了东西,就会按子类来,如果没有东西,就不会显示这两行。
接下来,在index.html顶部写上{% extends 'base.html' %},这个意思就是继承了base,我们就只需要填block内部的东西就可以了:

{% extends 'blog/base.html' %} 
{% block main %} 
{% for post in post_list %}  
<article class="post post-1">   
...  
</article> 
{% empty %}  
<div class="no-post">暂时没有发布文章!</div> 
{% endfor %} 
<!-- 简单分页效果 <div class="pagination-simple">  <a href="#">上一页</a>  
<span class="current">第 6 页 / 共 11 页</span>  
<a href="#">下一页</a> 
</div> 
--> 
<div class="pagination">  
... 
</div>
{% endblock main %}

detail.html同理,我们需要填写main部分和目录toc部分,不过目前目录只是占位,之后再实现从文章中自动摘取目录:

{% extends 'blog/base.html' %} 
{% block main %} 
<article class="post post-1">  
... 
</article> 
<section class="comment-area">
... 
</section>
{% endblock main %}
{% block toc %} 
<div class="widget widget-content">  
<h3 class="widget-title">文章目录</h3>  
<ul>   
<li>    
<a href="#" >教程特点</a>   
</li>   
<li>    
<a href="#">谁适合这个教程</a>   
</li>   
<li>    
<a href="#">在线预览</a>   
</li>   
<li>    
<a href="#">资源列表</a>   
</li>   
<li>    
<a href="#">获取帮助</a>   
</li>  
</ul> 
</div>
{% endblock toc %}

同时,修改article标签下的内容,让其显示文章的实际数据:

<article class="post post-{{ post.pk }}"> 
<header class="entry-header"> 
<h1 class="entry-title">{{ post.title }}</h1> 
<div class="entry-meta">  
<span class="post-category"><a href="#">{{ post.category.name }}</a></span>  
<span class="post-date"><a href="#"><time class="entry-date"            datetime="{{ post.created_time }}">{{ post.created_time }}</time></a></span>  
<span class="post-author"><a href="#">{{ post.author }}</a></span>  <span class="comments-link"><a href="#">4 评论</a></span>  
<span class="views-count"><a href="#">588 阅读</a></span> 
</div> 
</header> 
<div class="entry-content clearfix"> 
{{ post.body }} 
</div>
</article>

这样,我们就完成了一个博客的基本创建。

9. 总结

到目前为止,我们已经实现了博客的基本搭建,但是还有很多功能没有完成,比如:1.阅读数和评论量;2.目录部分等。这些功能我以后会继续探索研究,最近太忙,也没有时间继续做下去了。
写完以后发现写一遍比做一遍要花更久的时间,不过在写的过程我又学习了一遍,感觉收获很大,也基本上理清楚那些教程所说的东西了。共勉!

  • 4
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
智慧校园整体解决方案是响应国家教育信息化政策,结合教育改革和技术创新的产物。该方案以物联网、大数据、人工智能和移动互联技术为基础,旨在打造一个安全、高效、互动且环保的教育环境。方案强调从数字化校园向智慧校园的转变,通过自动数据采集、智能分析和按需服务,实现校园业务的智能化管理。 方案的总体设计原则包括应用至上、分层设计和互联互通,确保系统能够满足不同用户角色的需求,并实现数据和资源的整合与共享。框架设计涵盖了校园安全、管理、教学、环境等多个方面,构建了一个全面的校园应用生态系统。这包括智慧安全系统、校园身份识别、智能排课及选课系统、智慧学习系统、精品录播教室方案等,以支持个性化学习和教学评估。 建设内容突出了智慧安全和智慧管理的重要性。智慧安全管理通过分布式录播系统和紧急预案一键启动功能,增强校园安全预警和事件响应能力。智慧管理系统则利用物联网技术,实现人员和设备的智能管理,提高校园运营效率。 智慧教学部分,方案提供了智慧学习系统和精品录播教室方案,支持专业级学习硬件和智能化网络管理,促进个性化学习和教学资源的高效利用。同时,教学质量评估中心和资源应用平台的建设,旨在提升教学评估的科学性和教育资源的共享性。 智慧环境建设则侧重于基于物联网的设备管理,通过智慧教室管理系统实现教室环境的智能控制和能效管理,打造绿色、节能的校园环境。电子班牌和校园信息发布系统的建设,将作为智慧校园的核心和入口,提供教务、一卡通、图书馆等系统的集成信息。 总体而言,智慧校园整体解决方案通过集成先进技术,不仅提升了校园的信息化水平,而且优化了教学和管理流程,为学生、教师和家长提供了更加便捷、个性化的教育体验。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值