Django中的choice字段

  应用的场景:

    用户信息举列:如用户性别、婚否、学历、工作状态等可以列举出来供选择的信息

书写models创建表模型:

数据的获取和查询:

总结:

"""
1 存choice里面罗列的数字与中文对应关系
print(user_obj.get_gender_display())
只要是choices字段 在获取数字对应的数据 固定语法
get_choices字段名_display() 2 存没有罗列出来的数字
不会报错 还是展示数字
"""

MTV和MVC框架 (了解概念)

MVC(Model View Controller 模型-视图-控制器)

MTV(Model Templates View 模型-模板-视图):

区别:

MVC中的View的目的是「呈现哪一个数据」,而MTV的View的目的是「数据如何呈现」。

   MTV:是Django框架,自己自称的

    M:models模型

    T:templates模板

    V:views视图

   MVC:目前大部分web框架的本质

    M:models

    V:views

    C:controller  控制器(urls)

本质:MTV其实也是MVC

Django与AJAX

  关键理解:异步提交,局部刷新

例如github官网的注册界面:

  注册用户名时,时刻监测用户名是否存在,向后端发送请求,进行动态的校验.

目前所接触到的向后端发送请求方式:

  GET/POST请求

"""
前端中的<a> </a>标签 >>>>>GET请求
浏览器中输入的url搜索>>>>>GET请求  
from表单 >>>>>>>>>>>>>>>GET/POST请求
AJAX》>>>>>>>>>>>>>>>>>GET/POST请求 """

AJAX简介

  AJAX(Asynchronous Javascript And XML)翻译成中文就是“异步的Javascript和XML”。即使用Javascript语言与服务器进行异步交互,传输的数据为XML(当然,传输的数据不只是XML)。

AJAX 不是新的编程语言,而是一种使用现有标准的新方法。

AJAX 最大的优点是在不重新加载整个页面的情况下,可以与服务器交换数据并更新部分网页内容。(这一特点给用户的感受是在不知不觉中完成请求和响应过程)

AJAX 不需要任何浏览器插件,但需要用户允许JavaScript在浏览器上执行。

  • 同步交互:客户端发出一个请求后,需要等待服务器响应结束后,才能发出第二个请求;
  • 异步交互:客户端发出一个请求后,无需等待服务器响应结束,就可以发出第二个请求。

AJAX:有点是在不重新加载整个页面的情况下,可以与服务器交换数据并更新部分网页内容。

例子:

  页面上有三个input框,在前两个input框中输入数字,点击按钮 发送ajax请求,不刷新页面的情况下,第三个框中自动算出两数之和。

前端向后端发送请求需注意:改成让Django知道走POST请求

views.py

from django.shortcuts import render,reverse,HttpResponse,redirect

# Create your views here.

def index(request):
print(request.is_ajax()) # 用来判断当前请求方式是否是ajax请求
if request.is_ajax():
if request.method == 'POST':
# print(request.POST)
i1 = request.POST.get('i1')
i2 = request.POST.get('i2') # 后端获取的前端数据 都是字符串格式
res = int(i1) + int(i2)
return HttpResponse(res)
return reverse(request,'index.html')

url,py

from django.conf.urls import url
from django.contrib import admin
from app01 import views urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^index/',views.index),
]

index.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<script src="https://cdn.bootcss.com/jquery/3.4.0/jquery.slim.js"></script>
</head>
<body>
<input type="text" id="l1">+<input type="text" id="l2">=<input type="text" id="l3">
<button id="l3">求和</button>
<script> // 绑定点击事件
$('#l3').on('click',function () {
{#alert(123)#}
// 点击按钮 朝后端发送post请求
$.ajax({
url:'', // 控制发送给谁 不写就是朝当前地址提交
type:'post', // 发送方式是post请求
data:{'i1':$('#l1').val(),'l2':$('#l2').val()}, // 发送的数据
success:function (data) { // data形参用来接收异步提交的结果
// 将后端计算好的结果 通过DOM操作 渲染到第三个input框中
$('#l3').val(data)
}
})
})
</script>
</body>
</html>

前端书写AJAX部分

运行的结果是:点击求和后向后端发送POST请求,取到结果并展示

contentType前后端传输数据编码格式

常用的数据编码格式有三类:

1.urlencoded  >>>>>  数据格式:name=jack&pwd=123&boby=running
2.formdata >>>>>>>>> 传文件也支持传普通的键值对:name=jack&pwd=123&boby=running
3.json >>>>>>>> josn格式数据(from表单是无法发送Json格式的数据的)

  form 表单:默认使用的编码格式是urlencoded,数据格式是:name=jason&pwd=123;发送到后端,

django后端针对urlencoded编码格式的数据会自动解析并放到request.POST中供用户获取。

可以修改为formdata 传文件
      django后端针对只要是符合urlencoded编码格式的数据(name=jason&pwd=123)都会自动解析并放到request.POST中供用户获取

如果是文件 只要你指定的编码是formdata 就会自动解析并放到request.FILES中

ajax提交数据:提交的方式默认也是urlencoded

django后端针对不同的编码格式是如何处理的?

1、只要是符合urlencoded编码格式  都会被后端自动获取并解析放到request.POST中
2、如果是符合formdata那么文件会自动被解析放到request.FILES中
3、如果是json格式 后端默认不解析 以二进制的形式就放在request.body你可以自己手动处理即可

ajax发送json格式数据

<script>
$('#b1').on('click',function () {
alert(123)
// 点击按钮 朝后端发送post请求
$.ajax({
url:'', // 控制发送给谁 不写就是朝当前地址提交
type:'post', // 发送方式是post请求
data:JSON.stringify({'username':'jason','password':123}), // 发送的数据
contentType:'application/json', // 告诉后端你这次的数据是json格式 success:function (data) { // data形参用来接收异步提交的结果
alert(data)
// 将后端计算好的结果 通过DOM操作 渲染到第三个input矿中
$('#i3').val(data)
} })
// {)
</script>

要指定传输的数据格式统一

后端验证数据格式:

def index(request):

#验证前后端传输数据的编码格式
    if request.method =='POST':
print('request.POST',request.POST)
print('request.FILES',request.FILES)
jason_str = request.body
import json
# 后端 需要手动去request.body中获取json格式数据 自己处理
res = jason_str.decode('utf-8')
ral_d = json.loads(res)
print(ral_d)
return HttpResponse('OK')
return render(request,'index.html')

总结:前后端在传输数据的时候,一定要保证数据格式和你的编码保持一致性的.

通常情况下,后端针对ajax交互,都是采取字典的形式

基于AJAX传文件:

  关键字formData

传文件:如何获取文件标签存储的问文件对象?固定的语法

  1、先用jQuery查找到存储文件的input标签

  2、将jQuery对象转成原生Javascript对象

  3、利用原生Javascript对象的方法.files[0]获取到标签内部存储的文件对象

{#// ajax传输文件#}
$('#b1').on('click',function () {
// ajax传输文件 建议使用内置对象formdata
var formData = new FormData(); // 既可以传普通的键值对 也可以传文件
// 添加普通键值
formData.append('username','jason');
formData.append('password','123');
//固定的格式
formData.append('my_file',$('#d1')[0].files[0]);
$.ajax({
url:'', // 控制发送给谁 不写就是朝当前地址提交
type:'post', // 发送方式是post请求
data:formData, // 发送的数据
// ajax发送文件需要指定两个额外的参数 processData:false, // 告诉前端不要处理数据
contentType:false, // 不适用任何编码,因为formdata对象自身自带编码 django后端也能够识别formdata对象
success:function (data) { // data形参用来接收异步提交的结果
alert(data)
// 将后端计算好的结果 通过DOM操作 渲染到第三个input矿中
$('#i3').val(data)
} })

注意固定的格式及一些参数的使用

序列化组件

  Django内置的serializers

  简单的解释就是前端想拿到由ORM得到数据库中里面得一个个用户对象,为了简便操作,

后端直接将实例化出来的数据对象直接发送给客户端,这时候就需要用到序列化模块。

主要是考虑Json序列化字典的数据格式,传输的数据类型比较多,也可以以K:V键值对的形式取值。

from django.core import serializers  # django自带的一个小型的序列化工具
def reg(request):
user_list = models.User.objects.all()
  原来的数据传输:
# 将所有的数据都组织成一个符合json的一个个的字典
# user_l = []
# for user_obj in user_list:
# user_l.append(
# json.dumps({'username':user_obj.username,
# 'age':user_obj.age,
# 'gender':user_obj.get_gender_display()
# })
# )
res = serializers.serialize('json',user_list) #
return render(request,'index.html',locals())

利用在这json在线格式转换工具:

AJAX结合sweetalert插件的应用(动态弹框)

  实现以下的动态弹框提示,点击下载Bootstrap-sweetalert项目。需要导入的插件,统一放入static文件中配置到settings.py文件下.

views.py

from django.http import JsonResponse
import time
def userlist(request):
if request.is_ajax():
time.sleep(3)
"""
一般情况下 针对ajax请求 后端通常都是返回一个字典
"""
back_dic = {'code':100,'msg':''}
# 直接获取用户想删除的数据的id值
delete_id = request.POST.get('delete_id')
# 直接利用queryset方法 批量删除
models.User.objects.filter(pk=delete_id).delete()
# 要给前端ajax返回一个消息(字典)
back_dic['msg'] = '真的删除了!'
return JsonResponse(back_dic) user_list = models.User.objects.all()
return render(request,'userlist.html',locals())

userlist.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script src="https://cdn.bootcss.com/jquery/3.4.1/jquery.min.js"></script>
{% load static %}
<link rel="stylesheet" href="{% static 'bootstrap-3.3.7-dist/css/bootstrap.min.css' %}">
<link rel="stylesheet" href="{% static 'dist/sweetalert.css' %}">
<script src="{% static 'bootstrap-3.3.7-dist/js/bootstrap.min.js' %}"></script>
<script src="{% static 'dist/sweetalert.min.js' %}"></script> <style>
div.sweet-alert h2{
padding-top: 10px;
}
</style>
</head>
<body>
<div class="container">
<div class="row">
<div class="col-md-8 col-md-offset-2">
<h2 class="text-center">数据展示</h2>
<table class="table-striped table table-hover table-bordered">
<thead>
<tr>
<th>序号</th>
<th>主键</th>
<th>用户名</th>
<th>年龄</th>
<th>性别</th>
<th>操作</th>
</tr>
</thead>
<tbody>
{% for user in user_list %}
<tr>
<td>{{ forloop.counter }}</td>
<td>{{ user.pk }}</td>
<td>{{ user.username }}</td>
<td>{{ user.age }}</td>
<td>{{ user.get_gender_display }}</td>
<td>
<button class="btn btn-primary btn-sm">编辑</button>
<button class="btn btn-danger btn-sm del" user_id="{{ user.pk }}">删除</button>
</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
</div>
</div>
<script>
$('.del').click(function () {
// 获取当前标签对象
var $btnEle = $(this); swal({
title: "你确定要删吗?",
text: "你要是删了,你就准备跑路吧!",
type: "warning",
showCancelButton: true,
confirmButtonClass: "btn-danger",
confirmButtonText: "是的,老子就要删!",
cancelButtonText: "算了,算了!",
closeOnConfirm: false,
showLoaderOnConfirm: true
},
function(){
// 朝后端发送ajax请求
$.ajax({
url:'',
type:'post',
data:{'delete_id':$btnEle.attr('user_id')},
success:function (data) { // 后端发字典过来 前端不需要你手动转 会自动帮你转换成js自定义对象
if (data.code == 100){
{#window.location.href = ''; // 不写就是条到当前页面#}
// 通过DOM操作 实时改变页面
// 将被点击的删除按钮所在的那一行直接从DOM树中删掉
$btnEle.parent().parent().remove();
swal("删掉了!", "赶紧回去收拾行李吧,准备跑路!", "success");
}else{
swal('发生了未知的错误','估计是有bug了','info')
}
}
}); });
})
</script> </body>
</html>

效果如下:

自定义分页器

直接拷贝代码然后导入使用即可:

class Pagination(object):
def __init__(self, current_page, all_count, per_page_num=2, pager_count=11):
"""
封装分页相关数据
:param current_page: 当前页
:param all_count: 数据库中的数据总条数
:param per_page_num: 每页显示的数据条数
:param pager_count: 最多显示的页码个数 用法:
queryset = model.objects.all()
page_obj = Pagination(current_page,all_count)
page_data = queryset[page_obj.start:page_obj.end]
获取数据用page_data而不再使用原始的queryset
获取前端分页样式用page_obj.page_html
"""
try:
current_page = int(current_page)
except Exception as e:
current_page = 1 if current_page < 1:
current_page = 1 self.current_page = current_page self.all_count = all_count
self.per_page_num = per_page_num # 总页码
all_pager, tmp = divmod(all_count, per_page_num)
if tmp:
all_pager += 1
self.all_pager = all_pager self.pager_count = pager_count
self.pager_count_half = int((pager_count - 1) / 2) @property
def start(self):
return (self.current_page - 1) * self.per_page_num @property
def end(self):
return self.current_page * self.per_page_num def page_html(self):
# 如果总页码 < 11个:
if self.all_pager <= self.pager_count:
pager_start = 1
pager_end = self.all_pager + 1
# 总页码 > 11
else:
# 当前页如果<=页面上最多显示11/2个页码
if self.current_page <= self.pager_count_half:
pager_start = 1
pager_end = self.pager_count + 1 # 当前页大于5
else:
# 页码翻到最后
if (self.current_page + self.pager_count_half) > self.all_pager:
pager_end = self.all_pager + 1
pager_start = self.all_pager - self.pager_count + 1
else:
pager_start = self.current_page - self.pager_count_half
pager_end = self.current_page + self.pager_count_half + 1 page_html_list = []
# 添加前面的nav和ul标签
page_html_list.append('''
<nav aria-label='Page navigation>'
<ul class='pagination'>
''')
first_page = '<li><a href="?page=%s">首页</a></li>' % (1)
page_html_list.append(first_page) if self.current_page <= 1:
prev_page = '<li class="disabled"><a href="#">上一页</a></li>'
else:
prev_page = '<li><a href="?page=%s">上一页</a></li>' % (self.current_page - 1,) page_html_list.append(prev_page) for i in range(pager_start, pager_end):
if i == self.current_page:
temp = '<li class="active"><a href="?page=%s">%s</a></li>' % (i, i,)
else:
temp = '<li><a href="?page=%s">%s</a></li>' % (i, i,)
page_html_list.append(temp) if self.current_page >= self.all_pager:
next_page = '<li class="disabled"><a href="#">下一页</a></li>'
else:
next_page = '<li><a href="?page=%s">下一页</a></li>' % (self.current_page + 1,)
page_html_list.append(next_page) last_page = '<li><a href="?page=%s">尾页</a></li>' % (self.all_pager,)
page_html_list.append(last_page)
# 尾部添加标签
page_html_list.append('''
</nav>
</ul>
''')
return ''.join(page_html_list)

导入使用

from app01.utils.mypage import Pagination
def book(request):
# 使用封装好的自定义分页器
book_list = models.Book.objects.all()
current_page = request.GET.get("page",1)
all_count = book_list.count()
page_obj = Pagination(current_page=current_page,all_count=all_count,per_page_num=10)
page_queryset = book_list[page_obj.start:page_obj.end] return render(request,'booklist.html',locals())

booklist.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script src="https://cdn.bootcss.com/jquery/3.4.1/jquery.min.js"></script>
{% load static %}
<link rel="stylesheet" href="{% static 'bootstrap-3.3.7-dist/css/bootstrap.min.css' %}">
<link rel="stylesheet" href="{% static 'dist/sweetalert.css' %}">
<script src="{% static 'bootstrap-3.3.7-dist/js/bootstrap.min.js' %}"></script>
<script src="{% static 'dist/sweetalert.min.js' %}"></script>
</head>
<body>
<div class="container">
<div class="row">
<div class="col-md-8 col-md-offset-2">
{% for book in page_queryset %}
<p>{{ book.title }}</p>
{% endfor %}
{{ page_obj.page_html|safe }}
</div>
</div>
</div>
</body>
</html>

  

  

Django与AJAX-choice字段-MTV和MVC模型-sweetalert搭建页面的更多相关文章

  1. django----orm查询优化 MTV与MVC模型 choice参数 ajax serializers

    目录 orm查询优化 only defer select_related 与 prefetch_related MTV 与 MVC 模型 choice参数 Ajax 前端代码 后端代码 前后端传输数据 ...

  2. orm查询优化 MTV和MVC模型 字段的chioces参数 Ajax

    目录 一.ORM查询优化 1. all()查询 2. only()/defer()方法 (1)only()方法 (2)defer()方法 3. select_related()/prefetch_re ...

  3. ORM中choices参数(重要)、MTV于MVC模型、多对多关系三种创建方式

    choices参数(重要) **使用方式

  4. django admin 根据choice字段选择的不同来显示不同的页面

    一.举例 tip/tip.js var react = function () { if (django.jQuery('#id_tiptype').val() == 'content') { dja ...

  5. Django-choices字段值对应关系(性别)-MTV与MVC科普-Ajax发json格式与文件格式数据-contentType格式-Ajax搭配sweetalert实现删除确认弹窗-自定义分页器-批量插入-07

    目录 models 字段补充 choices 参数/字段(用的很多) MTV与MVC模型 科普 Ajax 发送 GET.POST 请求的几种常见方式 用 Ajax 做一个小案例 准备工作 动手用 Aj ...

  6. Django --- 查询优化,ajax

    目录 ORM查询优化 MTV与MVC模型 choices参数 ajax简介 前后端传输数据编码格式 ajax如何传输json格式数据 ajax如何传入文件数据 序列化 ORM查询优化 在使用数据库数据 ...

  7. Django之Ajax传输数据

    MTV与MVC模型 MTV与MVC都是模型,只不过MTV是django自己定义的,具体看一下他们的意思 MTV模型(django) M:模型层(models.py) T:templates文件夹 V: ...

  8. django ajax MTV与MVC 多对多创建方式

    MTV与MVC MTV模型(django): M:模型层(models.py) T:templates V:views MVC模型: M:模型层(models.py) V:视图层(views.py) ...

  9. 2019年6月14日 Web框架之Django_07 进阶操作(MTV与MVC、多对多表三种创建方式、前后端传输数据编码格式contentType、ajax、自定义分页器)

    摘要 MTV与MVC 多对多表三种创建方式 ajax ,前后端传输数据编码格式contentType 批量插入数据和自定义分页器 一.MVC与MTV MVC(Model View Controller ...

随机推荐

  1. Discuz中常用的编辑器代码

    .[ b]文字:在文字的位置可以任意加入您需要的字符,显示为粗体效果. .[ i]文字:在文字的位置可以任意加入您需要的字符,显示为斜体效果. .[ u]文字:在文字的位置可以任意加入您需要的字符,显 ...

  2. Vmware 部分所学到的功能简写

    VMware  vSphere  Hypervisor 免费版esxi VMware vSphere Update Manager (6.5之后集成到了VCSA中) 在 vSphere 6.5 及更高 ...

  3. 一天一个设计模式——Prototype 原型模式

    一.模式说明 看了比较多的资料,对原型模式写的比较复杂,个人的理解就是模型复制,根据现有的类来直接创建新的类,而不是调用类的构造函数. 那为什么不直接调用new方法来创建类的实例呢,主要一个原因是如果 ...

  4. POJ 3126:Prime Path

    Prime Path Time Limit: 1000MS   Memory Limit: 65536KB   64bit IO Format: %I64d & %I64u Submit St ...

  5. Idea 中的快捷键(mac)

    Mac键盘符号和修饰键说明 ⌘ Command ⇧ Shift ⌥ Option ⌃ Control ↩︎ Return/Enter ⌫ Delete ⌦ 向前删除键(Fn+Delete) ↑ 上箭头 ...

  6. 微信小程序下载图片到本地

    downloadImg: function(e){ //触发函数 console.log(e.currentTarget.dataset.url) wx.downloadFile({ url: e.c ...

  7. Codeforces 405D 数学问题

    真是脑残...擦 具体题解在这里 http://www.cnblogs.com/windysai/p/3619222.html 原本我为了防止两个数冲突,设置了好多判断,结果发现,如果两个数冲突,另外 ...

  8. P(Y=y|x;θ)表示什么意思

    https://blog.csdn.net/jh1137921986/article/details/88999539 在机器学习中,特别是学习到关于概率/似然估计方面的内容,经常看到类似P(Y=y| ...

  9. rsync搭建

    服务器: 查看是否安装:rpm -qa rsync 未安装则:yum install -y rsync 添加rsync用户 useradd -s /sbin/nologin -M rsync 编辑/e ...

  10. CSS3 box-shadow 效果大全(内阴影,外阴影,三边阴影,双边阴影,单边阴影,细线描边…)

    /* offset-x | offset-y | color */ box-shadow: 60px -16px teal; /* offset-x | offset-y | blur-radius ...