Django 2入门教程:利用GoormIDE和Bootstrap 4开发旅游博客

原版书名:《Django 2.1 Tutorial : Build a Travel Blog with GoormIDE and Bootstrap 4 (Tutorial Project)》

作者:Hojun Lee、 Suwon Choi 

出版时间:2018-08


演示地址:https://tutorialdjango-ircmu.run.goorm.io/

源码地址:https://github.com/wenguonideshou/tutorialdjango


这本书适合谁

这本书的目标读者是想使用django编程的程序员。django是python语言里非常流行的框架。希望这是个提升你的web开发技能的好机会。


关于这本书

这本书将会教你使用django开发简单旅游博客,并不学习django开发的详细细节,而是主要关注于手把手的开发简单web项目。

如果你跟着操作,你将学会开发django web项目,你可以在上面的源码地址下载源码和模板。

本书的前端编程部分使用bootstrap 4。


学完教程后

学完本书后,你将学会排错,并记录解决办法,而且你将能开发实际的web项目。

如果你对python其他方面感兴趣,你可能还想学习数据分析、数据可视化或人工智能。


第一章    在Goorm IDE安装环境


1.1 介绍

django是基于python开发的免费开源的web框架,在Instagram、NASA、Disqus等大公司应用广泛。

框架是利用诸多现成的组件使得开发web应用更快更容易的支持结构。

django在2005年做为免费开源的框架出现,django2.0在2017年12月发布,目前在韩国还没有关于django2.0的书籍。

为了理解网站开发的全部过程,本书中我们将开发简单博客。

如果你想了解django的更多信息,建议参考django官方网站 https://www.djangoproject.com ,官方主页提供django介绍、下载和支持文档。

PDF文档下载地址  https://media.readthedocs.org/pdf/django/2.0.x/django.pdf


1.2 安装django和环境配置

下图描述互联网的工作原理,这是你在浏览器输入google.com后互联网的运行流程。

我们即将开发的网站也会是安装这样的流程运行。

我们将使用不同的编程语言和框架如HTML、CSS、JavaScript、Python、Bootstrap和django。

1.jpg

1)你在浏览器输入google.com

2)浏览器获取到你输入的域名

3)浏览器从DNS服务器获取到域名对应的IP 216.58.221.164

4)浏览器向Google服务器发起首页请求

5)浏览器渲染服务器返回的响应,展现给你


我们将使用GoormIDE的云服务,操作系统是基于Linux的Ubuntu 14。

过去大家大部分使用图形化界面环境比如Windows,因此纯黑界面的Linux命令行环境可能对你来说比较陌生。

Linux系统占有全世界服务器操作系统至少90%的市场。这就是我们推荐使用Linux系统的原因。


对比下3种不同的云服务类型

  1. SaaS(Software as a Service):SaaS是软件的开发、管理、部署都交给第三方,不需要关心技术问题,可以拿来即用,是用户体验最好的

  2. PaaS(Platform as a Service):PaaS提供软件部署平台,抽象掉了硬件和操作系统细节,可以无缝地扩展。开发者只需要关注自己的业务逻辑,不需要关注底层

  3. IaaS(Infrastructure as a Service):IaaS是云服务的最底层,主要提供一些基础资源,主要是专业人士使用




我相信你选择本书是因为被python强大的库、直观、优秀的可扩展性吸引。

现在python已成为世界上最流行的编程语言之一。

关于框架呢?下图是python官方wiki上关于python不同框架的描述。

除django外,还有其他流行的框架比如Flask。django是全栈web框架,而Flask是轻量、可扩展的。

从下面的框架中做出选择,没有绝对的正确和错误,这完全取决于你的项目。

2.png2-2.png


1.2使用IDE配置环境

下面开始设置Goorm IDE环境,注意图片中的红框,官网 https://ide.goorm.io ,点击Sign Up注册账号,免费账号完全够用,可以创建5个容器。

3.png

4.png

注册完成后会自动登录Dashboard,或者在首页点击Dashboard。

5.png

在Dashboard页面有个看起来像设置电脑的容器,点击Create a new container,新版goorm需要填写申请理由然后人工审核通过后才能新建容器,内容就填写学习django web开发。

审核通过后,再次点击Create a new container,Source from选择Template,Name栏输入tutorialdjango,Description栏输入create a travel blog in django,software stack选择Python,点击Create

6.png

你将看到容器很快创建完成,并提示是否运行容器,点击Run进入容器

7_看图王.png

容器加载过程中通常会有代码提示或提到名人

8.png

下图是容器成功加载后的界面

9.png

①处是文件夹结构,在右上角有个刷新按钮,如果你新建或更新某些文件/文件夹但是在①看不见,就点击刷新按钮

②显示.txt .html .py等文件的内容

③协作、聊天窗口,我们不会使用到它

④命令行窗口,大部分命令在这里输入


点击Project - Running URL and Port,下图的红色方框是以后从外部访问的URL地址

提示:如果你没设置域名,在URL处输入域名,然后设置PORT为80

10.png

11.png

首先就是设计网站界面,本书不包括此步骤,如果想了解详情请阅读书籍《Bootstrap Tutorial: Learn how to create Travel Blog using Bootstrap》

我们看下站点结构:

  1. 主页 https://用户域名.run.Goorm.io

    主页,网站介绍,Google地图API,最新发布

    模板:index.html

  2. 博客列表 https://用户域名.run.Goorm.io/blog/

    点击blog会跳转到主页,展现博客列表

    模板:blog.html

  3. 文章详情 https://用户域名.run.Goorm.io/blog/文章ID

    在列表页点击文章后跳转

    模板:contens.html


下面是项目完成后的网站主页预览图,我们任意新建了一些文章

12.png

下面是博客列表页

13.png

下面是文章详情页,我们也任意填充了一些内容

14.png


现在开始开发,在④命令行窗口按步骤输入下面的命令

python --version
# 检查python版本,是3.6.5
mkdir mysite
# 创建名为mysite的文件夹
cd mysite
# 进入mysite目录
apt-get install python-virtualenv
# 安装虚拟环境所需要的包
virtualenv myvenv
# 基于python3.6.5创建虚拟环境
source myvenv/bin/activate
# 激活虚拟环境,注意:每次使用云容器都应该运行此命令激活虚拟环境

15.png

16.png

现在命令行最前面有(myenv)标志,说明已进入虚拟环境

安装django,创建项目

pip3 install django==2.0.6
# 安装django
django-admin startproject tutorialdjango .
# 在当前目录新建项目
python manage.py migrate
# 稍后解释,简而言之,在数据库中新建表结构

18.png

19.png

一定要注意django-admin startproject后面的.

如果你创建的容器名称不是tutorialdjango,命令修改为django-admin startproject xxx,其中xxx是你的容器名称


现在打开左边面板,修改tutorialdjango目录的settings.py,第28改行为ALLOW_HOSTS = ['*'] 允许任意用户访问,如图所示

20.png21.png

修改后按Ctrl+S保存生效,然后在命令行输入下面的命令

python manage.py runserver 0:80

22.png

点击Project - Running URL and Port

23.png

24.png

点击红框中的域名,浏览器会打开如图所示的页面

25.png


第二章    创建主页


使用django可以同时创建和组装多个应用,因为我们开发的是简单项目,现在我们只新建1个叫main的应用,在命令行窗口Ctrl+C停止运行上面的项目,输入命令:

python manage.py startapp main

26.png

在settings.py找到INSTALLED_APPS在最下面添加1行,注册main应用

注意:在'main'后面有个,

27.png

28.png

在项目下的urls.py添加内容视图函数和URL的映射

from main.views import index

意思是导入main目录下的views.py中的index函数,现在在views.py还没定义index函数,所以会报错,添加一行

path('', index)

意思是django会重定向任何访问 http://用户域名/  到index函数,下面将连接index函数和index.html模板

29.png

30.png

文件位于 mysite/tutorialdjango/urls.py


现在打开mysite> main> views.py新建index函数,可以看到 调用此函数时它将会返回render渲染main/index.html模板

31.png

文件位于 mysite/main/urls.py


新建myiste/main/templates/main/index.html目录和文件,然后粘贴以下代码:

32.png

<html>
<head>
    <title>Django!</title>
</head>
<body>
    <h1>Test!</h1>
</body>
</html>

启动web服务,看看网站发生了什么变化

python manage.py runserver 0:80

34.png

35.png

在域名后面添加/admin然后回车即可访问管理后台,可以在后台发布、编辑、删除文章,还可以管理用户。

但是现在还不能登录,因为没有创建管理员账号。为了安全考虑,建议在web应用中不要对外开放管理后台。


接下来将展示如何在主页加载图片,django不支持HTML和CSS中的相对目录。

在mysite目录下新建static文件夹,用来存储静态文件。

36.png

上传图片

37.png

38.png

如果在左边面板没找到图片,点击刷新标志即可

39.png

如图所示 在settings.py定义静态文件目录列表,注意在代码最后有个,

STATICFILES_DIRS = (
    os.path.join(BASE_DIR, 'static'),
)

40.png

打开index.html输入下列代码调用静态文件,{% %}语法意思是调用模板标签

更多django模板语法请访问 https://docs.djangoproject.com/en/2.0/ref/templates/builtins/

<html>
<head>
    <title>Django!</title>
</head>
<body>
    <h1>Test!</h1>
    {% load staticfiles %}
    <img src="{% static 'bluemountain.jpg' %}">
</body>
</html>

如果web服务器没有运行,在命令行输入python manage.py runserver 0:80 ,点击Project - Running URL and Port菜单,点击域名,可以正常访问

41.png

现在项目结构如下图所示,红色方框的文件是刚修改过的文件

42.png

django把MVC模式叫做MTV模式,虽然术语改变,但是本质是相同的。下图演示了django的运行流程。

43.png

CRUD分别代表增、查、改、删

44.png


第三章  创建列表页


新建包括所有文章的列表页,首先编辑tutorialdjango/urls.py和tutorialdjango/views.py

from main.views import index, blog
path('blog/', blog)

45.png

def blog(request):
    return render(request, 'main/blog.html')

46.png

新建mysite/main/templates/main/blog.html文件,输入以下代码

<html>
<head>
    <title>Django!</title>
</head>
<body>
    <h1>Blog Page!</h1>
</body>
</html>

运行web服务器,浏览器打开 https://用户域名/blog/ ,可以正常访问

47.png

现在为每篇文章新建内容,首先需要创建文章模型,包括postname和contens字段,在myiste/main/models.py输入

class Post(models.Model):
    postname = models.CharField(max_length=50)
    contents = models.TextField()

49.png

要在数据库中新建模型对应的表结构,按Ctrl+C停止web服务器,然后输入下面的迁移命令

python manage.py makemigrations main
python manage.py migrate

48.png

现在打开main/admin.py导入模型,修改管理后台界面

50.png

from .models import Post
admin.site.register(Post)

现在创建超级管理员账户,超级管理员能删除、编辑、保存文章,还能管理其他用户。 在命令行窗口输入

python manage.py createsuperuser

51.png

为了安全考虑,在命令行输入密码的时候是不可见的。

再开启web服务器,能看见登录界面了吧。

52.png

输入创建的超级管理员用户名和密码登录,进入后台可以试下新建文章

53.png

54.png

点击SAVE后,刚才输入的标题并没有显示,而是只显示了Post object(1)。这是因为没有定义模型的显示名为postname。

编辑main/models.py输入

    def __str__(self):
        return self.postname

59.png

刷新后台页面,现在可以看到刚才发布的文章标题,现在随便创建一些文章,稍后会删除。

55.png

56.png

这里我创建了3篇文章,现在准备在列表页展现这些文章,修改main/views.py

57.png

from .models import Post
postlist = Post.objects.all()
{'postlist': postlist}

58.png

修改blog.html模板在<h1>下面新增代码

    <table>
        {% for list in postlist %}
        <tr>
            <td>{{list.postname}}</td>
            <td>{{list.contents}}</td>
        </tr>
        {% endfor %}
    </table>

60.png

61.png

这里使用{}模板标签从数据库获取所有数据

更多关于Django文档请访问 https://docs.djangoproject.com/en/2.0/

模板语言文档请访问 https://docs.djangoproject.com/en/2.0/ref/templates/language/


现在使用F12查看网页源代码,是看不到模板语言的,因为是在django内部渲染成HTML再展现给访客

62.png


第四章  新建详情页


任何时候你返回该项目,都需要运行下面的命令确保运行的是虚拟环境的python而不是系统自带的python

在使用虚拟环境的情况下,命令行最前面有(myvenv)标志

root@Goorm:/workspace/container name# cd mysite

root@Goorm:/workspace/container name/mysite# source myvenv/bin/activate

(myvenv)root@Goorm:/workspace/container name/mysite#

如果你在没有进入虚拟环境的情况下运行了以下命令,此时最好的解决办法就是删除容器并重建容器。

最前面是否有(myvenv)标志非常重要,因为他代表的是完全不同的运行环境!


现在创建详情页,展示每一篇文章。修改tutorialdjango/urls.py新增以下代码

from main.views import index, blog, postdetails
path('blog/<int:pk>', postdetails),

63.png

修改main/views.py,新增以下代码

def postdetails(request, pk):
    postlist = Post.objects.get(pk=pk)
    return render(request, 'main/postdetails.html', {'postlist': postlist})

64.png

如下图所示,在templates文件夹有3个模板文件,现在这个是最后的模板(在第七章将会使用bootstrap美化模板)

65.png

新建templates/main/postdetails.html,输入

<html>
<head>
    <title>Django!</title>
</head>
<body>
    <h1>Postdetails Page!</h1>
    <p>{{postlist.postname}}</p>
    <p>{{postlist.contents}}</p>
</body>
</html>

66.png

在URL最后添加文章数字编号,页面如图所示

67.png

使用onclick事件实现 在博客列表页点击文章标题或者内容进入文章详情页,编辑templates/main/blog.html

<tr onclick="location.href='/blog/{{list.pk}}'">

68.png

69.png

点击后

70.png

在详情页新建返回列表页的按钮,在postdetails.html添加带超链接的标签<a>

<a href='/blog/'>List(Go back)</a>

71.png

72.png

编辑main/models.py,新增可以上传图片的ImageField

mainphoto = models.ImageField(blank=True, null=True)

73.png

由于要上传图片,所以需要安装叫Pillow的图片处理库

pip3 install pillow
# 上面修改了模型,所以需要迁移模型到数据库
python manage.py makemigrations
python manage.py migrate
python manage.py runserver 0:80

74.png

75.png

76.png

修改settings.py,设置上传文件的保存目录MEDIA_ROOT和访客访问的URL,如果不设置MEDIA_ROOT,文件将会上传到mysite目录下

77.png

现在在后台新建5篇文章,每篇文章上传1张图片

78.png

79.png

最开始上传名为jeju的图片,点击文章查看文件图片是否上传成功

80.png

点击图片文件名,浏览器弹出新页面 报错提示文件不存在,但是刚刚我们明明已经上传了!

81.png

还差一步,在urls.py设置图片URL

from django.conf.urls.static import static
from django.conf import settings

urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)

82.png

现在可以刷新页面可以看到图片了

83.png84.png

修改postdetails.html添加代码,注意红框内的域名改成你自己的

    {% if postlist.mainphoto %}
        <img src='{{postlist.mainphoto.url}}'>
    {% endif %}

85.png

django官方文档中相关说明

86.png

现在可以在详情页看到图片了

87.png


第五章  增加评论框和标签


现在增加评论功能,我准备使用叫Disqus的插件。

也可以使用pip3 install django-disqus安装该扩展,但我打算使用另一种方式安装。

打开 https://disqus.com/ 点击Get Started

88.png

输入用户名、邮箱等注册

89.png

注册成功后先去邮箱收件箱 查收验证邮件,验证邮箱,然后点击I want to install Disqus on my site

91.png

输入网站名称、网站类型、语言,点击Create Site

90.png

选择套餐,当然是Basic啦。点击Subscribe Now

92.png

现在选择平台,点击最后的I don't see my platform listed, install manually with Universal Code

93.png

复制①里面的代码,点击Configure

94.png

点击Complete Setup

95.png

编辑postdetails.html在</body>标签前粘贴代码

96.png

刷新详情页,可以在页面最下面看到评论框

97.png


修改模型增加发布时间字段、编辑时间字段

    publishDate = models.DateTimeField(blank=True, null=True)
    modifiedDate = models.DateTimeField(blank=True, null=True)

98.png

迁移模型

python manage.py makemigrations
python manage.py migrate

99.png

在后台可以看到新增的字段

100.png

修改所有文章,并修改blog.html模板,增加下面这行

<td>{{list.modifiedDate}}</td>

101.png

添加过编辑时间字段的文章都能在网页上显示编辑时间

102.png

安装django-taggit为文章添加标签,还可以利用标签来查找具有相同标签的文章

pip3 install django-taggit

103.png

修改models.py添加tag字段

from taggit.managers import TaggableManager
tag = TaggableManager(blank=True)

104.png

编辑settings.py,在INSTALLED_APPS添加'taggit',

105.png

迁移模型

python manage.py makemigrations
python manage.py migrate

106.png

在后台确认文章编辑界面底部是否有标签选项,把旅行过的国家作为标签

107.png

输入标签,点击SAVE保存

108.png

修改postdetails.html添加以下代码

<p>{{postlist.tag.names}}</p>

109.png

在详情页可以看到Queryset类型的标签

110.png

使用for循环语句可以展现所有的标签,我暂时只使用1个标签所以用{{post.tag.names.0}}

现在标签是字符串类型了

111.png


第六章  使用bootstrap美化模板以及部署


可以把bootstrap看成花最少的精力快速获得想要的结果的包罗万象的前端web框架。

不管是超大屏幕还是手机端,bootstrap都为用户体验量身定制,也叫响应式设计。

bootstrap自带HTML、CSS、表单、按钮、表格、导航栏。

bootstrap3中能用的标签大部分在bootstrap4也能使用,但是4相较于3变化也不小,所以你需要了解下新版本的bootstrap。

可以在 https://www.w3schools.com/bootstrap4  找到bootstrap4的入门教程。

更多信息请访问官方网站 https://getbootstrap.com/docs/4.1/content/reboot/  

可以在 https://getbootstrap.com/ 下载bootstrap4(在本书中不需要下载)

112.png

bootstrap默认模板使用CDN(内容分发网络),CDN的好处是无需下载文件,在全球访问速度都很不错

113.png

如果想使用最新版本的CDN,在Google搜索"bootstrap cdn"然后访问 https://www.bootstrapcdn.com 获取,最新版本是4

114.png

115.png

在001.html的<body></body>标签内有调用CDN的<script></script>标签,下图中的红框是模板中用来填充内容的代码

116.png

利用bootstrap的网格系统可以快速方便的建立响应式布局,整个页面的一行中可以有最多12列,如果不想使用全部12列 可以把列合并为更宽的列。

117.png

如下图所示,在<body></body>标签之间输入代码后,保存为002.html并用浏览器打开

118.png

红框代表在一行中定义的网格,每4小列分组为1个中型列,所以能看到3列

119.png

003.html把.col-md-4类和.col-md-6类的网格进行对比,效果一目了然

120.png121.png

122.png

在官方网站可以看到,列也可以拆分

123.png

如果想在网格系统中使用所有的12列占满屏幕,使用.container-fluid类。

还可以把.no-gutters类添加到.row类,以消除列之间的外边距和内边距。

下面是官方网站对网格系统的描述,nestable意思是可以分割列。常用的是md类。

124.png

如果使用了偏移列,列的位置将会浮动,有许多方法设置外边距,不过常用的是偏移列和弹性盒子对列排序。下图的003.html只使用了偏移列。

125.png126.png

127.png


现在解压templates.zip后,可以看到index.html,blog.html和blogdetails.html。

用浏览器打开index.html可以看到含有标记的地图。

每篇文章都需要坐标以在地图上做标记。

下图index001.html里的LatLng指的是纬度和精度。

128.png

在模型中添加经纬度字段

    Lat = models.FloatField(null=True)
    Lng = models.FloatField(null=True)

129.png

官方文档提供blank和null的解释和区别:https://docs.djangoproject.com/en/2.0/ref/models/fields/#django.db.models.FloatField

130.png

迁移模型,重新运行web服务器

python manage.py makemigrations
python manage.py migrate
python manage.py runserver 0:80

131.png

可以在后台文章编辑页面看到地理坐标类型的经纬度字段。

如果忘记了后台用户名密码,可以在命令行执行python manage.py changepassword admin修改admin用户的密码。

给每篇文章填充经纬度数据

bluemountain 照片,经纬度(-33.3493206,149.7360613)

jejucityhall 照片,经纬度(33.499597,126.5290653)

perth 照片,经纬度(-32.0388312,115.4010747)

sydney 照片,经纬度(-33.8567844,151.213108)

tasmania 照片,经纬度(-42.200633, 146.643736)

然后从lorem ipsum网站生成虚假内容然后从本地templates/img文件夹上传照片。

lorem ipsum网站:https://lipsum.com/

现在删除其他数据,只留下下面5条。

132.png

编辑views.py在index函数里添加以下代码,才能在首页使用postlist变量

postlist = Post.objects.all()

133.png

从index_002.html复制全部代码,粘贴到index.html。这2个文件唯一不同的地方如下图所示。

134.png

现在刷新首页,可以看到坐标标记,但是照片是裂开的。

135.png

接下来用{% %}和{{}}语法把每篇文章的照片放到红色方框的Infowindow(信息窗口,地图专用术语)中。

点击照片后,跳转到文章详情页。

136.png

把index_003.html的所有代码复制到index.html中,记得把其中的域名改成你自己的域名。

下图显示的是2个文件之间的区别,左边是index.html右边是index_003.html。

137.png

打开本地的templates/blog.html,修改blog.html的第161到180行的代码,找到<a href=""></a>然后把红框位置换成你的自己的域名。

复制全部代码,粘贴到云服务的blog.html。

138.png

现在访问 https://你的域名/blog/  ,点击每张图片都会跳转到文章详情页。

139.png

打开本地的templates/blogdetails.html,修改第147到166行,找到<a href=""></a>标签,把红框的域名换成你自己的域名。

然后复制所有代码,粘贴到云服务里面的postdetails.html。

140.png

现在访问 https://你的域名/blog/文章ID ,可以看到漂亮的带评论框的详情页。

141.png

虽然本书中并没有用到模板继承,但是在实际的django web项目开发中会经常用到模板继承。

一般是新建含有头部、菜单、底部等的母版,然后在其他所有模板中继承此模板。

下图是模板继承的简单例子。year_archive.html继承base.html。

142.png

143.png


在GoormIDE,Always On(永远在线)选项仅供付费用户。

如果是付费用户,当点击Always On,容器的绿色在线状态将会被点亮,访客可以在任意时间访问旅游博客。

负责只能在Dashboard点击Run后容器才能运行,网站才能访问。

点击图片中的红框地方,查看更多详细选项。

144.png


部署


点击Configure进入详细配置页面,点击+Add添加你自己购买的域名和端口,或者使用GoormIDE赠送的域名也可以。

在Setting下面的Init script处点击Set,然后输入容器初始化命令,我经常使用下面2行命令:

source /workspace/容器名称/mysite/myvenv/bin/activate
python3 /workspace/容器名称/mysite/manage.py runserver 0:80

输入完成后,点击下面的Stop停止容器,再点击右上角的Run

145.png

现在访问域名,测试网站完全正常运行。如果正常,说明上面的初始化脚本正常运行。


第七章  总结


django是python语言中快速开发web项目的框架,大部分功能都已经自动化,而且官方文档也很详尽。

阅读官方文档后,不用再考虑其他文档了。

现在我们使用django创建了简单的博客。

但是这仅仅使用了django的一小部分功能,如果想使用更多更强大的功能,推荐阅读官方文档。

下面是django的结构图,我画图简单总结之前我们做的所有步骤。你可以对照检查下是否有步骤遗漏。

注意:我们没有使用到表单功能


Django

146.png


urls.py

下图是我们之前所有操作的流程图。

最开始修改的是urls.py,urls.py根据特定的URL规则调用视图函数 。

147.png

148.png


views.py

在urls.py定义URL规则后,创建与URL相关联的视图函数。视图函数包括页面逻辑。

149.png

150.png


models.py

模型中的类变量代表数据库中的字段。需要执行迁移以保证数据库和模型结构同步。

151.png

152.png


templates

模板就是简单的文本文件,可以是任何基于文本的格式(html,csv等),模板展示的是页面设计界面。

153.png



译者注:全文到此结束。作者的模板做的很粗糙,页面中的很多超链接是死链。毕竟这只是个入门教程。

猜你喜欢

转载自blog.51cto.com/wenguonideshou/2407592