FullStack之Django(1)开发环境配置

author: Once Day date:2022年2月11日/2024年1月27日

漫漫长路,才刚刚开始…

全系列文档请查看专栏:

具体参考文档:

1.概述

详情参考文档:

1.1 简介

Web开发指的是开发基于B/S架构,通过前后端的配合,将后台服务器的数据在浏览器上展现给前台用户的应用。比如将电子购物网站的商品数据在浏览器上展示给客户,在基于浏览器的学校系统管理平台上管理学生的数据,监控机房服务器的状态并将结果以图形化的形式展现出来等等。

而Django是基于Python的Web开发框架。早期没有框架的时候,人们使用python直接编写HTML网页,曾经这一方法很流行。

Django是一个全栈Web框架。所谓全栈框架,是指除了封装网络和线程操作,还提供HTTP请求和响应、数据库读写管理、HTML模板渲染等一系列功能的框架。你可以不太准确地理解为全栈工程师包办了前后端和数据库访问的所有开发工作,整个网站都是一个人搭建的。

Django本身基于MVC架构,即Model(模型)+View(视图)+ Controller(控制器)设计模式,因此天然具有MVC的出色基因:开发快捷、部署方便、可重用性高、维护成本低等优点。

Django的设计模式命名为MTV:

  • 模型(Model):用于封装与应用程序的业务逻辑相关的数据及对数据的处理方法,是Web应用程序中用于处理应用程序的数据逻辑的部分,Model只提供功能性的接口,通过这些接口可以获取Model的所有功能。白话说,这个模块就是业务逻辑和数据库的交互层,定义了数据表。
  • 模板(Template):将模型数据与HTML页面结合起来的引擎
  • 视图(View):负责实际的业务逻辑实现

逻辑图参考如下:

FullStack之Django(1)开发环境配置-LMLPHP

1.2 Django项目历史

Django 是一个开源的高级 Python Web 框架,它鼓励快速开发和清晰、实用的设计。它由 Lawrence Journal-World 的在线新闻操作的 Web 开发人员创建,并于 2005 年 7 月首次公开发布。

Django 的开发始于 2003 年,最初是为了管理多个新闻网站的内容。开发者们希望创建一个框架,既能够快速开发出功能完备的网站,也能够应对高流量的挑战。它的名字来源于著名的吉普赛风格吉他手 Django Reinhardt,寓意着该框架旨在帮助开发者像 Django 演奏音乐那样快速、灵活地开发网站。

随着时间的推移,Django 赢得了大量跟随者,并建立了一个强大的社区。它不断更新和改进,引入了如数据库迁移、ORM (对象关系映射器)、模板引擎等众多功能,并且支持 RESTful API 的开发。

Django的优点如下:

  1. 快速开发:Django 遵循 “Don’t Repeat Yourself” (DRY) 原则,意味着你可以编写更少的代码,并且代码更加高效。
  2. 全能型:Django 是一个全栈框架,提供了开发一个网站所需要的大部分功能,从数据库模型到后端服务,再到模板渲染。
  3. 安全性:Django 提供了许多内置的安全功能,如防止跨站请求伪造(CSRF)、SQL 注入、点击劫持等。
  4. 可扩展性:它能够支持从小型项目到大型企业级应用的开发。
  5. 强大的社区支持:有着庞大且活跃的社区,提供大量的第三方库,插件和中间件。

Django的缺点如下:

  1. 单体架构:对于微服务架构,Django 的单体架构可能不是最理想的选择。
  2. 性能问题:虽然足以应付大多数流量,但在处理超高并发的环境下,Django 的性能可能不如某些竞争对手,比如 Node.js 或 Go 语言编写的框架。
  3. 异步支持:尽管 Django 从 3.1 版本开始增加了对异步编程的支持,但它的异步能力仍然不如专为此设计的框架,如 Node.js。
  4. 学习曲线:由于 Django 框架较为全面,初学者可能需要花费一定的时间来学习其全面的功能和组件。

对于初学者来说,Django 很适合快速了解全栈开发。它有详细的官方文档,以及大量教程和书籍,这些资源可以帮助新手更快地上手。

Flask 是另一个流行的 Python web 框架,与 Django 相比,它更加轻量级和灵活。Flask 适合想要更多控制权和自定义能力的开发者。相比之下,Django 提供了更多 “开箱即用” 的功能。

1.3 Django开发环境和数据库选择

参考文档:

Django 要求先安装 Python。参见下个问题中的表格,它介绍了各个 Django 版本所支持的 Python 版本。某些情况下可能需要一些额外的 Python 库,如果未安装,你会在这些库被用到时获得一个错误提示。

Django 版本	Python 版本
3.2			 3.6, 3.7, 3.8, 3.9, 3.10 (在 3.2.9 中就已经加入了)
4.0			 3.8,3.9,3.10
4.1			 3.8,3.9,3.10,3.11(4.1.3 添加)
4.2			 3.8, 3.9, 3.10, 3.11, 3.12 (4.2.8 添加)
5.0		     3.10、3.11、3.12

对于开发环境,如果你仅仅只是想体验一下Django,你不需要分开安装web服务器和数据库服务器。

Django自带了轻量级开发服务器,对于生产环境, Django 遵循 WSGI 规范PEP 3333,这意味着它可以运行在各种 web 服务平台上。

Django 默认使用 SQLite , 它随着 Python 一起安装。在生产环境中,推荐使用 PostgreSQL,此外也同样支持 MariaDBMySQL,、SQLiteOracle

如果你打算使用 Django 的数据库 API 功能,你需要确保一个数据库服务器正在运行。Django 支持许多不同的数据库服务器,官方支持 PostgreSQLMariaDBMySQLOracleSQLite

如果你正在开发一个小项目或不打算在生产环境中部署的东西,SQLite 通常是最好的选择,因为它不需要运行一个单独的服务器。然而,SQLite 与其他数据库有许多不同之处,所以如果你正在开发一些实质性的东西,建议使用你计划在生产中使用的同一数据库进行开发。

除了官方支持的数据库,还有第三方提供的后端允许你在 Django 中使用其他数据库。

除了数据库后端,你还要确保安装了 Python 数据库绑定。

  • 如果您使用 PostgreSQL,您将需要 psycopgpsycopg2 包。有关更多详细信息,请参阅 PostgreSQL notes
  • 如果你正在使用 MySQL 或 MariaDB,则需要一个像 mysqlclient 一样的 DB API 驱动。 详细信息参见 MySQL 后端注意事项
  • 如果你正在使用 SQLite,则可能需要阅读 SQLite 后端笔记
  • 如果你使用的是 Oracle,你需要安装 oracledb,但请阅读 Oracle 后端的说明 以了解有关支持的 Oracle 版本和 oracledb 的详细信息。
  • 如果你使用的是非官方的第三方后端,请参阅提供的文档以了解任何其他要求。

如果你打算使用 Django 的 manage.py migrate 命令为你的模型自动创建数据库表(首先安装 Django 并创建项目后),你需要确保 Django 有权限在你使用的数据库中创建和修改表;如果你打算手动创建表,你可以授予 Django SELECTINSERTUPDATEDELETE 权限。创建具有这些权限的数据库用户后,你将在项目的配置文件中指定详细信息,详细信息参见 DATABASES

如果你正在使用 Django 的 测试框架 来测试数据库查询,Django 将需要创建测试数据库的权限。

2.开发环境搭建
2.1 安装Django开发环境

具体安装可参考:

Python虚拟环境允许你在一个隔离的环境中安装Python软件包,而不会影响到系统的Python环境。

可以使用python3 -m venv path/to/venv命令创建一个虚拟环境,然后使用source path/to/venv/bin/activate命令激活这个环境。在这个环境中,可以自由地使用pip来安装软件包。

(1) 首先创建一个工作目录,这个并不是真实的开发生产环境,而是用于测试的本地环境。

onceday->forwhat:# pwd	# 创建一个工作目录, 名字为forwhat
/root/forwhat
onceday->forwhat:# mkdir temp-test	# 用于django开发测试的目录
/root/forwhat/temp-test

(2) 然后创建python虚拟环境,也许后续也能直接放在docker里面隔离运行。

# 如果命令执行失败,可以先安转pip-evnv包,需要root权限
onceday->temp-test:# apt-get update
onceday->temp-test:# apt install python3.11-venv
onceday->temp-test:# python3 -m venv ./venv
onceday->temp-test:# ll
drwxr-xr-x 5 root root 4096 Jan 27 16:49 venv/
onceday->temp-test:# ll venv/
total 24
drwxr-xr-x 5 root root 4096 Jan 27 16:49 ./
drwxr-xr-x 3 root root 4096 Jan 27 16:49 ../
drwxr-xr-x 2 root root 4096 Jan 27 16:49 bin/
drwxr-xr-x 3 root root 4096 Jan 27 16:49 include/
drwxr-xr-x 3 root root 4096 Jan 27 16:49 lib/
lrwxrwxrwx 1 root root    3 Jan 27 16:49 lib64 -> lib/
-rw-r--r-- 1 root root  167 Jan 27 16:49 pyvenv.cfg

可以看到,venv大概构建了一个虚拟的root目录,从而隔离Python的执行环境

(3) Django本质上是Python语言的一个类库,因此可以通过pip工具安装。这也是最简便、最好的安装方式。

# 先激活python虚拟环境
onceday->temp-test:# source venv/bin/activate 
(venv) onceday->temp-test:# echo ${PATH}
/root/forwhat/temp-test/venv/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:

如上所示,通过导入venv/bin/activate 可以更改一系列的环境变量。然后就可以安装django库了,在此之前,一般需要对Python进行换源操作,如下:

# windows在user目录下创建一个pip.ini文件, 如C:\Users\用户名\pip\
# Linux在~/.pip/pip.conf文件中增加配置.
# 目录不存在则先使用mkdir进行创建, 然后使用nano/vi/vim创建配置文件, 内容如下:
[global]
index-url = https://pypi.tuna.tsinghua.edu.cn/simple

然后执行django安装命令,此时下载速度就会非常快了,如下:

(venv) onceday->temp-test:# python -m pip install Django
Looking in indexes: https://pypi.tuna.tsinghua.edu.cn/simple
Collecting Django
  Downloading https://pypi.tuna.tsinghua.edu.cn/packages/97/67/6804ff6fc4fa6df188924412601cc418ddc2d0a500963b0801a97b7ec08a/Django-5.0.1-py3-none-any.whl (8.1 MB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 8.1/8.1 MB 23.4 MB/s eta 0:00:00                                  
Collecting asgiref<4,>=3.7.0
  Downloading https://pypi.tuna.tsinghua.edu.cn/packages/9b/80/b9051a4a07ad231558fcd8ffc89232711b4e618c15cb7a392a17384bbeef/asgiref-3.7.2-py3-none-any.whl (24 kB)
Collecting sqlparse>=0.3.1
  Downloading https://pypi.tuna.tsinghua.edu.cn/packages/98/5a/66d7c9305baa9f11857f247d4ba761402cea75db6058ff850ed7128957b7/sqlparse-0.4.4-py3-none-any.whl (41 kB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 41.2/41.2 kB 9.2 MB/s eta 0:00:00                                 
Installing collected packages: sqlparse, asgiref, Django
Successfully installed Django-5.0.1 asgiref-3.7.2 sqlparse-0.4.4

在Windows环境下,需要注意系统环境变量的设置。

使用 pip list 命令可以检查所有安装模块,这样可以确定是否已安装Django模块。

(venv) onceday->temp-test:# pip list
Package    Version
---------- -------
asgiref    3.7.2
Django     5.0.1
pip        23.0.1
setuptools 66.1.1
sqlparse   0.4.4

(4) 可以在命令行使用下面的命令确认是否安装好了:

(venv) onceday->temp-test:# django-admin help

Type 'django-admin help <subcommand>' for help on a specific subcommand.

Available subcommands:

[django]
    check
    compilemessages
    createcachetable
    dbshell
    diffsettings
    dumpdata
    flush
    inspectdb
    loaddata
    makemessages
    makemigrations
    migrate
    optimizemigration
    runserver
    sendtestemail
    shell
    showmigrations
    sqlflush
    sqlmigrate
    sqlsequencereset
    squashmigrations
    startapp
    startproject
    test
    testserver
Note that only Django core commands are listed as settings are not properly configured (error: Requested setting INSTALLED_APPS, but settings are not configured. You must either define the environment variable DJANGO_SETTINGS_MODULE or call settings.configure() before accessing settings.).
2.2 搭建git版本控制仓库

可参考文档:

作为开发流程必不可少的一部分,需要使用版本控制系统来精准控制代码、配置文件、文档的更新和创建,以便后续追踪。

一般而言,可以使用githubgitee这样的代码托管网站来实现代码托管,但是这还不够,下面介绍基于云服务器搭建属于自己的git裸仓库,从而实现额外的代码备份功能。

首先,我们可以在gitee或者github上创建一个代码仓库,详细步骤这里就省略了。然后拿到仓库的ssh路径地址,并且克隆到本地一份:

ubuntu->pull-git:$ git clone git@gitee.com:xxxxxx/forwhat.git
Cloning into 'forwhat'...
remote: Enumerating objects: 9, done.
remote: Counting objects: 100% (9/9), done.
remote: Compressing objects: 100% (9/9), done.
remote: Total 9 (delta 0), reused 0 (delta 0), pack-reused 0
Receiving objects: 100% (9/9), 4.86 KiB | 4.86 MiB/s, done.

然后切换目录到专门存放git仓库的文件夹中,如/var/git:

ubuntu->git:$ pwd
/var/git

从现有的forwhat.git仓库中导出裸仓库:

# pull-git/forwhat/ 是上面clone的forwhat.git的本地目录路径
ubuntu->git:$ git clone --bare pull-git/forwhat/ pri-forwhat.git
Cloning into bare repository 'pri-forwhat.git'...
done.

pri-forwhat.git本质是一个目录名,但是我们按照惯例加上.git的后缀

查看pri-forwhat.git目录文件,信息如下:

ubuntu->git:$ ll pri-forwhat.git/
total 44
drwxrwxr-x 7 ubuntu ubuntu 4096 Jan 27 18:43 ./
drwxrwxr-x 5 ubuntu root   4096 Jan 27 18:43 ../
drwxrwxr-x 2 ubuntu ubuntu 4096 Jan 27 18:43 branches/
-rw-rw-r-- 1 ubuntu ubuntu  118 Jan 27 18:43 config
-rw-rw-r-- 1 ubuntu ubuntu   73 Jan 27 18:43 description
-rw-rw-r-- 1 ubuntu ubuntu   23 Jan 27 18:43 HEAD
drwxrwxr-x 2 ubuntu ubuntu 4096 Jan 27 18:43 hooks/
drwxrwxr-x 2 ubuntu ubuntu 4096 Jan 27 18:43 info/
drwxrwxr-x 4 ubuntu ubuntu 4096 Jan 27 18:43 objects/
-rw-rw-r-- 1 ubuntu ubuntu  105 Jan 27 18:43 packed-refs
drwxrwxr-x 4 ubuntu ubuntu 4096 Jan 27 18:43 refs/

可以看到,裸仓库中只有.git中的文件,而没有当前工作目录的内容,实际上就是正常仓库目录下.git的内容

这种裸仓库,也可以使用整体打包拷贝到其他服务器上,作为远程仓库使用。

使用这种仓库非常简单,使用ssh连接即可,如下:

  • 把使用设备的ssh公钥放在远程服务器对应账户的认证文件中,如下:

    ubuntu->git:$ ll ~/.ssh/authorized_keys 
    -rw------- 1 ubuntu ubuntu 1923 Jan 26 11:53 /home/ubuntu/.ssh/authorized_keys
    

    这里使用的是ubuntu用户,ssh用户需要确保对仓库目录有操作权限,否则更新或者读取操作会失败。

    如果是给其他人使用,建议分别建立专门的账户,而不是混用一个高权限账户,并且指定这些git用户的shell为专门的git-shell

  • 然后在使用设备上,直接克隆clone或者添加remote仓库(如果弹出not known警告, 直接yes即可):

    (venv) onceday->temp-test:# git clone ubuntu@onceday.work:/var/git/pri-forwhat.git
    Cloning into 'pri-forwhat'...
    remote: Enumerating objects: 9, done.
    remote: Counting objects: 100% (9/9), done.
    remote: Compressing objects: 100% (9/9), done.
    remote: Total 9 (delta 0), reused 9 (delta 0), pack-reused 0
    Receiving objects: 100% (9/9), 4.86 KiB | 4.86 MiB/s, done.
    

在克隆远程服务器的Git仓库到本地之后,我们就可以看到一些基础的文件了(Gitee仓库预配置的文件):

(venv) onceday->temp-test:# ll pri-forwhat/
drwxr-xr-x 8 root root 4096 Jan 27 18:55 .git/
drwxr-xr-x 2 root root 4096 Jan 27 18:55 .gitee/
-rw-r--r-- 1 root root 2035 Jan 27 18:55 .gitignore
-rw-r--r-- 1 root root 1506 Jan 27 18:55 LICENSE
-rw-r--r-- 1 root root  904 Jan 27 18:55 README.en.md
-rw-r--r-- 1 root root  993 Jan 27 18:55 README.md

并且仓库的拉取和推送都已经配置好了:

(venv) onceday->pri-forwhat:# git remote -v
origin  ubuntu@onceday.work:/var/git/pri-forwhat.git (fetch)
origin  ubuntu@onceday.work:/var/git/pri-forwhat.git (push)
(venv) onceday->pri-forwhat:# git branch -a
* master                                                                                                        
  remotes/origin/HEAD -> origin/master
  remotes/origin/master 

一般为了规范化管理(越是一个人开发,越是要严格约束自己),我们还会配置提交模板,可参考下面文档:

Git的配置分为多个层级,全局配置、本地配置、用户配置等等,那么对于个人电脑,一般配置全局即可:

git config --global user.name "Your Name"
git config --global user.email "your_email@example.com"

对于提交模板信息,可以按照简介、原因、所属模块、细节描述、署名等信息组成,一种建议信息如下:

# Subject line (best to under 50 chars). 简单


# The reason why do this commit.
Reason:

# The code position in project.
Module:

# Multi-line description of this commit.
Description:

# Something about commit:
Signed-off-by: Once Day <once_day@qq.com>

然后设置全局模板文件的配置路径,如下:

git config --global commit.template /path/to/.gitmessage.txt

正常情况下,提交时会默认使用模板信息,弹出编辑器界面,并且修改完毕后再提交。如果默认提交不想使用模板信息,也可以如下所示,跳过模板的使用:

git commit --no-template

如果希望提交更改时,Git能自动署名(即配置里用户和邮箱信息),那么可以使用下面的提交方式:

git commit --signoff -m "Your commit message"

Git 的commit 命令的 -s--signoff 选项,会在提交消息的末尾添加一行 “Signed-off-by”,其格式为:

Signed-off-by: Your Name <your.email@example.com>

这表示认可代码并且有权提交这段代码,同时也意味着遵守了项目的贡献者许可协议(Contributor License Agreement, CLA)。

3.创建第一个项目
3.1Project项目创建

项目是Django的核心部分,你可以认为你的个人网站即是一个Project,而一个网页会有多个应用或模组,如图片墙,评论区,博客文章等。实际上Project和app完全可以是多对多的样子。

建立Django project只需要下列命令即可:

 django-admin startproject mysite

其中mysite是项目名字,任意取名,除了不能与python模组重名。目录结构如下所示

PS E:\Django\mysite> dir -d 2

    目录: E:\Django\mysite
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
d-----         2022/2/12     11:09                mysite
-a----         2022/2/12     11:09            684 manage.py

    目录: E:\Django\mysite\mysite
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
-a----         2022/2/12     11:09            405 asgi.py
-a----         2022/2/12     11:09           3344 settings.py
-a----         2022/2/12     11:09            769 urls.py
-a----         2022/2/12     11:09            405 wsgi.py
-a----         2022/2/12     11:09              0 __init__.py

各文件和目录解释:

  • 外层的mysite/目录与Django无关,只是你项目的容器,可以任意重命名。
  • manage.py:一个命令行工具,管理Django的交互脚本。
  • 内层的mysite/目录是真正的项目文件包裹目录,它的名字是你引用内部文件的Python包名,例如:mysite.urls
  • mysite/__init__.py:一个定义包的空文件。
  • mysite/settings.py: 项目的配置文件。
  • mysite/urls.py: 路由文件,所有的任务都是从这里开始分配,相当于Django驱动站点的目录。
  • mysite/wsgi.py:一个基于WSGI的web服务器进入点,提供底层的网络通信功能,通常不用关心。
  • mysite/asgi.py:一个基于ASGI的web服务器进入点,提供异步的网络通信功能,通常不用关心。

这些文件里面,settings.py和urls.py是用户自定义最多的文件。其他文件都是无需操心的。

输入以下命令可以查看manage.py支持的交互命令

PS E:\Django\mysite> python manage.py -h

Type 'manage.py help <subcommand>' for help on a specific subcommand.

Available subcommands:

[auth]
    changepassword
    createsuperuser

[contenttypes]
    remove_stale_contenttypes

[django]
    check
    compilemessages
    createcachetable
    dbshell
    diffsettings
    dumpdata
    flush
    inspectdb
    loaddata
    makemessages
    makemigrations
    migrate
    sendtestemail
    shell
    showmigrations
    sqlflush
    sqlmigrate
    sqlsequencereset
    squashmigrations
    startapp
    startproject
    test
    testserver

[sessions]
    clearsessions

[staticfiles]
    collectstatic
    findstatic
    runserver

其中[auth]等表示相应模块支持的命令,比如auth是用户认证工具。

help还可以查看对应命令的详细用法和作用。

PS E:\Django\mysite> python manage.py help runserver
usage: manage.py runserver [-h] [--ipv6] [--nothreading] [--noreload] [--nostatic] [--insecure] [--version]
                           [--settings SETTINGS] [--pythonpath PYTHONPATH] [--no-color] [--force-color]
                           [--skip-checks]
                           [addrport]

Starts a lightweight web server for development and also serves static files.

positional arguments:
  addrport              Optional port number, or ipaddr:port

optional arguments:
  -h, --help            show this help message and exit
  --ipv6, -6            Tells Django to use an IPv6 address.
  --nothreading         Tells Django to NOT use threading.
  --noreload            Tells Django to NOT use the auto-reloader.
  --nostatic            Tells Django to NOT automatically serve static files at STATIC_URL.
  --insecure            Allows serving static files even if DEBUG is False.
  --version             Show program's version number and exit.
  --settings SETTINGS   The Python path to a settings module, e.g. "myproject.settings.main". If this isn't provided,
                        the DJANGO_SETTINGS_MODULE environment variable will be used.
  --pythonpath PYTHONPATH
                        A directory to add to the Python path, e.g. "/home/djangoprojects/myproject".
  --no-color            Don't colorize the command output.
  --force-color         Force colorization of the command output.
  --skip-checks         Skip system checks.

现在project里面还没有任何apps,而runserver可以开启一个用于开发的web服务器,因此无需配置一个类似Ngnix的生产服务器,就能让站点运行起来。这是一个由Python编写的轻量级服务器,简易并且不安全,因此不能用于生产环境。

现在就直接运行runserver命令并访问一下这个测试服务器:

PS E:\Django\mysite> python manage.py runserver
Watching for file changes with StatReloader
Performing system checks...

System check identified no issues (0 silenced).

You have 18 unapplied migration(s). Your project may not work properly until you apply the migrations for app(s): admin, auth, contenttypes, sessions.
Run 'python manage.py migrate' to apply them.
February 12, 2022 - 11:45:33
Django version 4.0.1, using settings 'mysite.settings'
Starting development server at http://127.0.0.1:8000/
Quit the server with CTRL-BREAK.

默认的访问地址是http://127.0.0.1:8000/,复制粘贴到浏览器,就可以看到它的界面了。

FullStack之Django(1)开发环境配置-LMLPHP

用于开发的服务器在需要的情况下会对每一次的访问请求重新载入一遍 Python 代码。所以你不需要为了让修改的代码生效而频繁的重新启动服务器。然而,一些动作,比如添加新文件,将不会触发自动重新加载,这时你得自己手动重启服务器

3.2Apps应用创建

在 Django 中,每一个应用(app)都是一个 Python 包,并且遵循着相同的约定。Django 自带一个工具,可以帮你生成应用的基础目录结构。

app应用与project项目的区别:

  • 一个app实现某个具体功能,比如博客、公共档案数据库或者简单的投票系统;
  • 一个project是配置文件和多个app的集合,这些app组合成整个站点;
  • 一个project可以包含多个app;
  • 一个app可以属于多个project!

app的存放位置可以是任何地点,但是通常都将它们放在与manage.py脚本同级的目录下,这样方便导入文件。

输入以下命令即可创建应用,

 python manage.py startapp login

这里创建了一个登入应用,其目录结构如下:

PS E:\django\mysite> dir ./login -d 2

    目录: E:\django\mysite\login
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
d-----         2022/2/12     21:03                migrations
-a----         2022/2/12     21:03             66 admin.py
-a----         2022/2/12     21:03            148 apps.py
-a----         2022/2/12     21:03             60 models.py
-a----         2022/2/12     21:03             63 tests.py
-a----         2022/2/12     21:03             66 views.py
-a----         2022/2/12     21:03              0 __init__.py

    目录: E:\django\mysite\login\migrations
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
-a----         2022/2/12     21:03              0 __init__.py

各个目录的说明:

  • admin.py,管理后台,用于注册你的模型,以便它们可以在Django的管理后台中使用。在这里,你可以定义你的模型在admin界面中的显示方式,比如列表中显示的列、过滤选项、搜索字段等。
  • apps.py,应用,帮助Django识别这是一个可用的app。在这个文件中,你通常定义一个子类AppConfig,用于存放app的配置信息。这个类包含app的一些属性,比如它的名字。
  • migrations,迁移目录,包含Django迁移文件。迁移是Django的方式来对数据库模式进行版本控制。每当你对模型进行更改(比如添加字段、删除模型等)时,你会创建一个迁移文件,该文件是一个包含更改数据库结构所需操作的Python脚本。
  • model.py,模型,定义了app的数据模型。Django模型是一个Python类,它映射到数据库中的一个表。每个模型都表示数据库表中的一种数据结构,并且Django提供了一个富有表现力的API来查询数据库中的记录。
  • test.py,测试,用于编写单元测试。Django内建了测试框架,允许你测试你的视图、模型和模板等。编写良好的测试是确保你的应用在修改和增加新功能时保持稳定的好方法。
  • view.py,视图,定义了app的视图。在Django中,视图是一个Python函数或类,它接收Web请求并返回Web响应。视图函数通常会读取数据库中的数据,然后将其传递给模板或直接生成响应。

根据Django的MTV框架,其处理 request 的流程如下:

  1. 浏览器送出 HTTP Request
  2. Django 依据 URL Conf 分配至对应的 View
  3. View 进行资料库的操作或其他运算,并回传 Http Response 物件
  4. 浏览器依据 HTTP Response,显示网页画面

这里先在视图view.py里定义一个函数,

#login/view.py
from django.shortcuts import render
from django.http import HttpResponse
# Create your views here.
#定义一个函数,或者说一个网页
def user_login(request):#浏览器送出 HTTP Request
    return HttpResponse("欢迎来到Once Day的个人网站!")

现在有了一个View,但还需要配置URL使得Django能正确分配访问请求。

官方列出了三种View和URL之间的配置,

Function views
    1. Add an import:  from my_app import views
    2. Add a URL to urlpatterns:  path('', views.home, name='home')
Class-based views
    1. Add an import:  from other_app.views import Home
    2. Add a URL to urlpatterns:  path('', Home.as_view(), name='home')
Including another URLconf
    1. Import the include() function: from django.urls import include, path
    2. Add a URL to urlpatterns:  path('blog/', include('blog.urls'))

从模块化编程思想出发,把Apps中的View配置到Project的URL中,通过第三种方式比较好。而在app内部则设置一个urls.py文件,采用第一种或第二种方式导入。这样不同app内部的URL配置相对独立,整体上也便于管理。在login文件夹内新建urls.py文件,并填入下列代码:

#login/urls.py
from django.urls import path
#导入编写的视图函数,注意默认的根目录是项目文件夹所在的目录
from login.views import user_login

urlpatterns = [
    path('', user_login,name="login"),#格式按官方的例子写就行
]

然后在mysite项目的urls.py中导入login的urls.py配置:

from django.contrib import admin
from django.urls import path,include

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

注意导入的格式也是按官方的例子套的!include语法相当于多级路由,它把接收到的url地址去除与此项匹配的部分,将剩下的字符串传递给下一级路由urlconf进行判断。

include的背后是一种即插即用的思想。项目的根路由不关心具体app的路由策略,只管往指定的二级路由转发,实现了应用解耦。app所属的二级路由可以根据自己的需要随意编写,不会和其它的app路由发生冲突。app目录可以放置在任何位置,而不用修改路由。这是软件设计里很常见的一种模式。

建议:除了admin路由外,尽量给每个app设计自己独立的二级路由。

path函数的原型如下:

# path()
@overload
def path(
    route: str, view: Callable[..., HttpResponseBase], kwargs: Dict[str, Any] = ..., name: str = ...
) -> URLPattern: ...
@overload
def path(route: str, view: IncludedURLConf, kwargs: Dict[str, Any] = ..., name: str = ...) -> URLResolver: ...
@overload
def path(
    route: str, view: Sequence[Union[URLResolver, str]], kwargs: Dict[str, Any] = ..., name: str = ...
) -> URLResolver: ...

该函数可以接受四个参数,其中前2个是必须的:routeview,以及2个可选的参数:kwargsname

  • route route 是一个匹配 URL 的准则(类似正则表达式)。当 Django 响应一个请求时,它会从 urlpatterns 的第一项path开始,按顺序依次匹配列表中的项,直到找到匹配的项,然后执行该条目映射的视图函数或下级路由,其后的条目将不再继续匹配。因此,url路由执行的是短路机制,path的编写顺序非常重要!需要注意的是,route不会匹配 GET 和 POST 参数或域名。例如,URLconf 在处理请求 https://www.liujiangblog.com/myapp/时,它会尝试匹配 myapp/。处理请求 https://www.liujiangblog.com/myapp/?page=3 时,也只会尝试匹配 myapp/
  • view view指的是处理当前url请求的视图函数。当Django匹配到某个路由条目时,自动将封装的HttpRequest对象作为第一个参数,被“捕获”的参数以关键字参数的形式,传递给该条目指定的视图view。
  • kwargs 任意数量的关键字参数可以作为一个字典传递给目标视图。
  • name 对URL进行命名,能够在Django的任意处,尤其是模板内显式地引用它。这是一个非常强大的功能,相当于给URL取了个全局变量名,不会将url匹配地址写死。

做完以上工作,运行,

PS E:\django\mysite> python manage.py runserver

浏览器访问127.0.0.1:8000/login/,即可看到编写的网页!

FullStack之Django(1)开发环境配置-LMLPHP

注:本文章内容收集总结于互联网,仅供学习之用!
02-02 19:51