Django 入门
安装扩展库
pip3 install django
pip3 install django==1.9.7 # pip 默认会安装该库的最新版本,如果我们知道该库的版本号,也可以指定某个版本号安装
查看当前安装的库
pip3 show django
卸载库
pip3 uninstall django
创建Django工程
django-admin startproject proj # proj为工程名
目录结构:
proj/
├── proj/
│ ├── __init__.py
│ ├── settings.py
│ ├── urls.py
│ └── wsgi.py
└── manage.py
proj/ : 对整个工程进行配置
proj/__init__.py:一个空的文件,用它标识一个目录为 Python 的标准包。
proj/settings.py:Django 项目的配置文件,包括 Django 模块应用配置,数据库配置,模板配置等。
proj/urls.py:Django 项目的 URL 声明(对应关系)
proj/wsgi.py:遵循WSIG规范, 为 WSGI 兼容的 Web 服务器服务项目的切入点(django本省并不创建socket,调用Python内部的wsgi模块)。拓展:uwsgi + nginx
manage.py:一个命令行工具,管理Django程序
python manage.py # 查看 manage 所提供的命令(许多命令与 django-admin 相同)
运行项目
python manage.py runserver
python manage.py runserver 127.0.0.1:8001 # Django 默认会通过本机的 8000 端口来启动项目,如果你的当前环境该端口号被占用了,也可以在启动时指定IP 地址和端口号
打开浏览器访问:http://127.0.0.1:8001 , Django 默认页面显示:It worked!
创建APP
python manage.py startapp cmdb
创建完后会多一个以app名称命名的目录, 结构如下:
proj/
├── proj/
├── cmdb/
│ ├── migrations/
│ ├── __init__.py
│ ├── admin.py
│ ├── apps.py
│ ├── models.py
│ ├── tests.py
│ └── view.py
└── manage.py
proj/: 所有app的公共配置
migrations/:用于记录 models 中数据的变更。
admin.py:映射 models 中的数据到 Django 自带的 admin 后台。
apps.py:在新的 Django 版本中新增,用于当前app的配置。
models.py:创建应用程序数据表模型(对应数据库的相关操作,通过命令可以创建数据库结构, ORM)。
tests.py:功能测试。
views.py:业务代码, 控制向前端显示哪些数据。
基本配置
模板的路径 配置
在应用目录下创建 templates目录,用以存放html页面
编辑settings.py :
'DIRS': [os.path.join(BASE_DIR, 'templates')],
静态目录 配置 # 对于所有的静态文件,一般不通过urls路由
编辑settings.py,末尾添加 :
STATICFILES_DIRS = (
os.path.join(BASE_DIR, 'static'), #注意以逗号结尾,否则报错
)
在html中引用 <link rel="stylesheet" href="/static/commons.css" />
定义路由规则
from sign import views #导入cmdb 应用 views 文件
urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^index/', views.index), #添加 index/路径配置, index为views.py中的函数名
]
应用python中的正则表达式
r: 字符串前面加“ r ”是为了防止字符串中出现类似“\t”字符时被转义。
^: 匹配字符串开头;在多行模式中匹配每一行的开头。
$: 匹配字符串末尾;在多行模式中匹配每一行末尾。
views 视图
views视图是连接页面与数据的中间纽带
def func(request): #定义视图函数,至少要有一个形参接收用户的请求,
# request.method # GET / POST
# request.GET.get('',None) # 获取get请求发来的而数据
# request.POST.get('',None) # 获取post请求发来的而数据
# return HttpResponse("字符串")
# return render(request, "HTML模板的路径")
# return redirect('/只能填URL')
当客户机通过 HTTP 协议向服务器提交请求时,最常用到的方法是 GET 和 POST。
GET - 从指定的资源请求数据。
GET 方法会将用户提交的数据添加到 URL 地址中,路径后面跟问号“?”,如:http://127.0.0.1:8000/index/?username=admin&password=admin123
username 和 password 为HTML 代码中<input>标签的 name 属性值,username=admin 表示用户名输入框得到的输入数据为“admin”。password=admin123 密码输入框得到的输入数据为“admin123”。多个参数之间用“&”符号隔开。
POST - 向指定的资源提交要被处理的数据。
“跨站请求伪造”( Cross-Site Request Forgery, CSRF)漏洞,Django 针对 CSRF 的保护措施是在生成的每个表单中放置一个自动生成的令牌,通过这个令牌判断POST请求是否来自同一个网站。
CSRF verification failed. Request aborted.
临时忽略,注释该行 #'django.middleware.csrf.CsrfViewMiddleware'
Django处理流程

这个处理流程并非 Django 的完整处理过程,其中最主要的就是缺失了数据层(model) 的操作,完整处理流程如下 :

示例:
=== urls.py ===
from cmdb import views
urlpatterns = [ url(r'^admin/', admin.site.urls), url(r'^login', views.login), url(r'^home', views.home), ]
=== view.py ===
# Create your views here. from django.shortcuts import HttpResponse from django.shortcuts import render from django.shortcuts import redirect def login(request): # request, 包含用户提交的所有信息,如用户提交方法 error_msg = "" if request.method == "POST": # 获取用户通过POST提交过来的数据, 为了避免key不存在,设置None为默认值 user = request.POST.get('user',None) pwd = request.POST.get('pwd',None) if user == 'root' and pwd == "123": return redirect('/home') # 跳转, / 表示"域名:端口" else: error_msg = "用户名或密码错误" ''' f = open('templates/login.html', 'r', encoding='utf-8') data = f.read() f.close() return HttpResponse(data) ''' # HttpResponse 只能返回字符串,需每次打开读取和关闭文件后返回数据,Django提供render方法接收页面参数完成所有操作 return render(request,'login.html', {'error_msg': error_msg}) # 通过settings.py中配置的模板路径找到页面 # 实际USER_LIST中的数据保存在数据库中 USER_LIST = [ {'username': 'u1', 'email': 'u1@qq.com', "gender": '男'}, {'username': 'u2', 'email': 'u2@qq.com', "gender": '男'}, {'username': 'u3', 'email': 'u3@qq.com', "gender": '男'}, ] def home(request): print(request.GET.get('nid')) if request.method == "POST": u = request.POST.get('username') e = request.POST.get('email') g = request.POST.get('gender') temp = {'username': u, 'email': e, "gender": g} USER_LIST.append(temp) return render(request, 'home.html', {'user_list': USER_LIST}) # 这里使用了模板语言,'user_list'为html的模板变量
=== login.html ===
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <link rel="stylesheet" href="/static/commons.css" /> <style> label{ width: 80px; text-align: right; display: inline-block; } </style> </head> <body> <form action="/login" method="post"> <!-- 注意action里的url必须和urls中定义的一致,要么都以/结尾,要么都不加 --> <p> <label for="username">用户名:</label> <input id="username" name="user" type="text" /> </p> <p> <label for="password">密码:</label> <input id="password" name="pwd" type="password" /> <input type="submit" value="提交" /> <span style="color: red;">{{ error_msg }}</span> </p> </form> <script src="/static/jquery.min.js"></script> </body> </html>
=== home.html ===
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body style="margin: 0"> <div style="height: 48px;background-color: #dddddd"></div> <div> <form action="/home" method="post"> <input type="text" name="username" placeholder="用户名" /> <input type="text" name="email" placeholder="邮箱"/> <input type="text" name="gender" placeholder="性别"/> <input type="submit" value="添加" /> </form> </div> <div> <table> <!-- django 模板语言的for循环 --> {% for row in user_list %} <tr> <td>{{ row.username }}</td> <td>{{ row.gender }}</td> <td>{{ row.email }}</td> </tr> {% endfor %} </table> </div> </body> </html>
模板渲染
模板的载体就是html页面,Django 自带的有模板语言。它的主要作用是如何展示数据,比如视图层返回的是一个字符串,要如何显示在页面上;返回的对象数组要如何显示等。 当然,为了使页面更漂亮需要借助前端技术,比如 CSS、JavaScript 等。
模板标签: {{ }} {% %}
变量 : {{ var }}
条件语句
{% if age %}
<a> born </a>
{% if age > 18 %}
<a> adult</a>
{% else %}
<a> young </a>
{% endif %}
{% else %}
<a> unborn </a>
{% endif %}
For循环
<ul>
{% for row in user_list %}
{% if row == "u1" %}
<li>{{ row }}</li>
{% endif %}
{% endfor %}
</ul>
索引
def func(request):
return render(request, "index.html", {
'current_user': "u1",
'user_list': ['u1','u2','u3'],
'user_dict': {'k1': 'v1', 'k2': 'v2'}
})
<a> {{ user_list.0 }} </a> // 获取列表第一个元素
<a> {{ user_list.1 }} </a>
<a> {{ user_dict.k1 }} </a> // 获取字典k1的值
<a> {{ user_dict.k2 }} </a>

浙公网安备 33010602011771号