文章目录
django 实现 ajax
AJAX简介
AJAX(Asynchronous Javascript And XML)翻译成中文就是“异步的Javascript和XML”。即使用Javascript语言与服务器进行异步交互,传输的数据为XML(当然,传输的数据不只是XML)。
AJAX 不是新的编程语言,而是一种使用现有标准的新方法。
AJAX 最大的优点是在不重新加载整个页面的情况下,可以与服务器交换数据并更新部分网页内容。(这一特点给用户的感受是在不知不觉中完成请求和响应过程)
AJAX 不需要任何浏览器插件,但需要用户允许JavaScript在浏览器上执行。
- 同步交互:客户端发出一个请求后,需要等待服务器响应结束后,才能发出第二个请求;
- 异步交互:客户端发出一个请求后,无需等待服务器响应结束,就可以发出第二个请求。
补充: 这里只介绍jQuery封装之后的Ajax版本(原生的复杂且在实际项目中一般不用),因此在前端页面中使用Ajax的时候需要确保导入jQuery
Ajax优点
- AJAX使用JavaScript技术向服务器发送异步请求;
- AJAX请求无须刷新整个页面;
- 因为服务器响应内容不再是整个页面,而是页面中的部分内容,所以AJAX性能高;
- 两个关键点:1.局部刷新,2.异步请求
朝后端发送请求的四种方式:
- 浏览器地址栏直接输入url回车 GET请求
- a标签的href属性 GET请求
- from表单 GET请求/POST请求
- ajax GET请求/POST请求
jQuery实现Ajax
- 做一个简单的基于ajax动态请求的加法运算器
实现效果:
- 前端核心代码:
<p><input type="text" id="d1">+
<input type="text" id="d2">=
<input type="text" id="d3"></p>
<p> <button id="btn">提交</button> </p>
<script>
$('#btn').on('click',function () {
{#朝后端发送ajax请求#}
$.ajax({
{#1. 指定朝那个后端发送ajax请求#}
url:'', // 不写就是朝当前地址提交
{#2. 请求方式#}
type:'post', // 指定提交类型,默认是get请求
{#3. 数据#}
data:{'v1':$('#d1').val(),'v2':$('#d2').val()}, // 动态获取值
{#4. 回调函数#}
success:function (args) { // args 是后端返回的的,就是个形参
$('#d3').val(args) // 将后端放回的值添加到结果框中
}
})
})
</script>
- 后端核心代码
def sum(request):
if request.method == 'POST':
# print(request.POST) <QueryDict: {'v1': ['12'], 'v2': ['12']}>
v1 = request.POST.get('v1')
v2 = request.POST.get('v2')
v3 = int(v1)+int(v2)
return HttpResponse(v3)
return render(request,'sum.html')
- 补充
HttpResponse返回的对象只能是字符串或数字类型,要是其他类型数据,
列如字典,方式如下:
后端:
d = {'code':1000,'msg':v3}
1. 手动序列化
import json
return HttpResponse(json.dumps(d)) # 返回给前端是一个json格式数据,需要前端反序列化
前端反序列化:
1. 手动反序列化
JSON.prase(arg)
2. 自动反序列化
dataType:'JSON' # ajax中自动反序列化参数
2. 使用JsonResponse对象
return JsonResponse(d) # 推荐使用,返回给前端是一个对象
总结:
针对后端如果是HttpResponse返回的数据 回调函数不会自动反序列化
如果后端直接用的是JsonResponse返回的数据 回调函数会自动帮你反序列化
前后端传输数据的编码格式(contentType)
主要研究post请求数据的编码格式
get请求数据就是直接放在url后面的数据 url?username=xxx&password=123
- 可以朝后端发送post请求的方式
- form表单
- ajax请求
- 前后端传输数据的编码格式
- urlencoded
- formdata
- json
- 研究from表单结论
- form表单的编码格式是urlencoded
数据格式: username=xxx&password=123 - django后端针对urlencoded编码格式的数据都会自动解析封装到request.POST中
- 如果把编码格式改成formdata,那么针对普通的键值对还是解析到reques.POST中,将文件解析到request.FILES中
- form表单没有办法发送json格式的数据
- form表单的编码格式是urlencoded
补充:
1. form表单修改编码格式修改参数:
enctype="multipart/form-data" // formdata编码格式,传输文件必须要改
-
研究ajax结论
-
默认编码格式是urlencoded
数据格式: username=xxx&password=123
-
django后端针对符合rulencoded编码格式的数据都会自动解析封装到request.POST中
-
Ajax发送json格式数据
注意:
-
前后端传输数据的时候一定要确保编码格式跟数据真正的格式是一致的(不一致)
-
django针对json格式的数据 不会做任何的处理
-
reuqest对象方法补充
request.is_ajax() # 判断当前请求是否是ajax请求 返回布尔值
前端ajax发送json格式数据核心代码
$.ajax({
url:'',
type:'post',
data:JSON.stringify({'username':'xxx','age':18})
contentType:'application/json',
success:function (args) {
}
})
后端接收json格式数据核心代码
由于django针对json格式的数据不会做任何处理,需要自己解码处理
def ab_json(request):
if request.is_ajax():
json_str = request.body # b'{"username":"xxx","age":18}'
# json.loads括号内如果传入了一个二进制格式的数据那么内部会自动解码再反序列化
# 注意: 字符编码会默认选用系统默认字符编码,最好使用encoding指定字符编码
json.loads(json_str,encoding='utf8')
return render(request,'ab_file.html')
前端ajax发送文件数据核心代码
<script>
// 点击按钮朝后端发送普通键值对和文件数据
$('#d4').on('click',function () {
// 1 需要先利用FormData内置对象
let formDateObj = new FormData();
// 2 添加普通的键值对
formDateObj.append('username',$('#d1').val());
formDateObj.append('password',$('#d2').val());
// 3 添加文件对象
formDateObj.append('myfile',$('#d3')[0].files[0])
// 4 将对象基于ajax发送给后端
$.ajax({
url:'',
type:'post',
data:formDateObj, // 直接将对象放在data后面即可
// ajax发送文件必须要指定的两个参数
contentType:false, // 不需使用任何编码 django后端能够自动识别formdata对象
processData:false, // 告诉你的浏览器不要对你的数据进行任何处理
success:function (args) {
}
})
})
</script>
后端接收json格式数据核心代码
def ab_file(request):
if request.is_ajax():
if request.method == 'POST':
print(request.POST)
print(request.FILES)
return render(request,'ab_file.html')
总结:
1. 前端需要利用内置对象FormData
2. 添加普通键值对方法
formDateObj.append('username',$('#d1').val());
formDateObj.append('password',$('#d2').val());
3. 添加文件对象
formDateObj.append('myfile',$('#d3')[0].files[0])
1. 需要指定两个关键性的参数
contentType:false,
processData:fasle
4. django后端能够直接识别到formdata对象并且能够将内部的普通键值对自动解析并封装到request.POST中 文件数据自动解析并封装到request.FILES中
django自带的序列化组件
from django.core import serializers
def ab_ser(request):
user_queryset = models.User.objects.all()
# 序列化
res = serializers.serialize('json',user_queryset)
'''serializers组件会自动将数据变成json格式的字符串 并且内部非常全面'''
return HttpResponse(res)
'''
序列化后数据格式
[
{ "model": "app01.user",
"pk": 1,
"fields": {"username": "xxx", "age": 15, "gender": 1}}, ]
'''
ajax结合sweetalert实现删除二次确认
-
前端核心代码
<script> $('.del').on('click',function () { // 先将当前标签对象存储起来 let currentBtn = $(this); // 二次确认弹框 swal({ title: "你确定要删吗?", text: "你可要考虑清除哦,可能需要拎包跑路哦!", type: "warning", showCancelButton: true, confirmButtonClass: "btn-danger", confirmButtonText: "是的,老子就要删!", cancelButtonText: "算了,算了!", closeOnConfirm: false, closeOnCancel: false, showLoaderOnConfirm: true // 等待动态效果 }, function(isConfirm) { if (isConfirm) { // 朝后端发送ajax请求删除数据之后 再弹下面的提示框 $.ajax({ {#url:'/delete/user/' + currentBtn.attr('delete_id'), // 1 传递主键值方式1#} url:'/delete/user/', // 2 放在请求体里面 type:'post', data:{'delete_id':currentBtn.attr('delete_id')}, success:function (args) { // args = {'code':'','msg':''} // 判断响应状态码 然后做不同的处理 if(args.code === 1000){ swal("删了!", args.msg, "success"); // 1.lowb版本 直接刷新当前页面 {#window.location.reload()#} // 2.利用DOM操作 动态刷新 currentBtn.parent().parent().remove() }else{ swal('完了','出现了位置的错误','info') } } }) } else { swal("怂逼", "不要说我认识你", "error"); } }); }) </script>
-
后端核心代码
def book_del2(request): if request.is_ajax(): if request.method == 'POST': del_id = request.POST.get('del_id') back_dic = {"code": 1000, 'msg': del_id} models.Book.objects.filter(pk=del_id).delete() return JsonResponse(back_dic)