赞
踩
号外号外,基于Pycharm的Django学习,项目实战彩蛋来啦!
我报考的学校,今天下午五点就要出考研成绩了,我好慌,从来没有这么紧张过,我就想着把项目收个尾,这样赶在出成绩之前,也是把Django学完啦。
昨天的后续又完善了一下,在新建任务里面又加了任务列表,提交后就更新:
老规矩,先设计表结构:
class Order(models.Model):
"""订单"""
# 可以根据下单时间加上随机字符串自动生成订单号
oid = models.CharField(verbose_name="订单号", max_length=64)
title = models.CharField(verbose_name="名称", max_length=32)
price = models.IntegerField(verbose_name="价格")
status_choices = (
(1, "待支付"),
(2, "已支付")
)
status = models.SmallIntegerField(verbose_name="订单状态", choices=status_choices, default=1)
# models.CASCADE没有括号 否则会报错
admin = models.ForeignKey(verbose_name="管理员", to="Admin", on_delete=models.CASCADE)
生成后不要忘记这两步:
在数据库查看一下:
这里我们就不自己在数据库生成数据了,和任务管理一样,提交后就存入到数据库。
{% extends 'layout.html' %} {% block content %} <div style="margin-bottom:20px"> <input id="btnAdd" type="button" value="新建订单" class="btn btn-primary"> </div> <!-- Modal --> <div class="modal fade" id="myModal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel"> <div class="modal-dialog" role="document"> <div class="modal-content"> <div class="modal-header"> <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span> </button> <h4 class="modal-title" id="myModalLabel">Modal title</h4> </div> <div class="modal-body"> ... </div> <div class="modal-footer"> <button type="button" class="btn btn-default" data-dismiss="modal">Close</button> <button type="button" class="btn btn-primary">Save changes</button> </div> </div> </div> </div> {% endblock %} {% block js %} <script type="text/javascript"> $(function(){ bindBtnAddEvent(); }) function bindBtnAddEvent(){ $("#btnAdd").click(function(){ $('#myModal').modal('show'); }); } </script> {% endblock %}
这样测试页面就出来了!!
继续完善模态框内容:
class OrderModelForm(BootStrapModelForm, forms.ModelForm):
class Meta:
model = models.Order
exclude = ["oid"]
在modal body中新增如下:
{% for field in form %}
<div class="form-group">
<label>{{field.label}}</label>
{{field}}
<span style="color:red;">{{field.errors.0}}</span>
</div>
{% endfor %}
最后效果:
这里和任务管理一样,采用的ajax请求,使用的是模态框。
{% extends 'layout.html' %} {% block content %} <div style="margin-bottom:20px"> <input id="btnAdd" type="button" value="新建订单" class="btn btn-primary"> </div> <div> <div class="panel panel-default"> <div class="panel-heading"> <span class="glyphicon glyphicon-th-list"></span> 订单列表 </div> <!--可以直接在浏览器中选中元素 copy element--> <table class="table table-bordered"> <thead> <tr> <th>ID</th> <th>订单号</th> <th>标题</th> <th>价格</th> <th>状态</th> <th>管理员</th> </tr> </thead> <tbody> {% for data in data_list %} <tr> <th scope="row">{{data.id}}</th> <td>{{data.oid}}</td> <td>{{data.title}}</td> <td>{{data.price}}</td> <td>{{data.get_status_display}}</td> <td>{{data.admin.username}}</td> <td> <a class="btn btn-success btn-xs" href="#">编辑</a> <a class="btn btn-danger btn-xs" href="#">删除</a> </td> </tr> {% endfor %} </tbody> </table> </div> </div> <!-- Modal --> <div class="modal fade" id="myModal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel"> <div class="modal-dialog" role="document"> <div class="modal-content"> <div class="modal-header"> <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span> </button> <h4 class="modal-title" id="myModalLabel">新建订单</h4> </div> <!--需要展示的内容放在模态对话框里面--> <div class="modal-body"> <form id="formAdd"> {% for field in form %} <div class="form-group"> <label>{{field.label}}</label> {{field}} <span style="color:red;" class="error-msg">{{field.errors.0}}</span> </div> {% endfor %} </form> </div> <div class="modal-footer"> <button type="button" class="btn btn-default" data-dismiss="modal">关闭</button> <button id="btnSave" type="button" class="btn btn-primary">保存</button> </div> </div> </div> </div> {% endblock %} {% block js %} <script type="text/javascript"> $(function(){ bindBtnAddEvent(); bindBtnSaveEvent(); }) function bindBtnAddEvent(){ $("#btnAdd").click(function(){ $('#myModal').modal('show'); }); } function bindBtnSaveEvent(){ $("#btnSave").click(function(){ $(".error-msg").empty(); $.ajax({ url: "/order/add/", type: "post", data: $("#formAdd").serialize(), dataType: "JSON", success: function(res){ if(res.status){ alert("添加任务成功"); $("#formAdd")[0].reset(); $('#myModal').modal('hide'); location.reload(); }else{ $.each(res.error,function(name,data){ $("#id_"+name).next().text(data[0]); }) } } }) }); } </script> {% endblock %}
def order_list(request): form = OrderModelForm() data_list = models.Order.objects.all() content = { "form": form, "data_list": data_list } return render(request, "order_list.html", content) @csrf_exempt def order_add(request): form = OrderModelForm(data=request.POST) if form.is_valid(): # 添加没有提交过来的oid form.instance.oid = datetime.now().strftime("%Y%m%d%H%M%S") + str(random.randint(1000, 9999)) form.save() data_dict = {"status": True} # return HttpResponse(json.dumps(data_dict)) return JsonResponse(data_dict) data_dict = {"status": False, "error": form.errors} return HttpResponse(json.dumps(data_dict))
加一个分页吧!
注意,数据多基本上是一个单独的页面,但是数据少,那就是模态框。
之前我们在写删除的时候,是点击删除按钮,就将该行的id传递给函数,但是这次我们不打算这样处理,我们打算把所有的删除写成一个class,然后使用js来进行处理。
function bindBtnConfirmDeleteEvent(){
$("#btnConfirmDelete").click(function(){
$.ajax({
url: "/order/delete/",
type: "get",
data: {uid:DELETE_ID},
dataType: "JSON",
success: function(res){
alert("删除成功");
location.reload();
}
})
});
}
# ajax的get可以不用csrf
def order_delete(request):
uid = request.GET.get("uid")
models.Order.objects.filter(id=uid).delete()
data_dict = {"status": True}
return JsonResponse(data_dict)
编辑其实和添加差不多奥!
所以此处,我编辑和添加使用的同一个对话框。
但是有一个问题,那就是当你点击这个对话框的保存时,怎么确定是编辑还是添加呢?
为此我们应该再设置一个全局变量,EDIT_ID,当点击添加的时候,这个设置为undefined,当点击编辑的时候设置为对应的id,这样就可以根据此变量区分开来了。
# ajax的get可以不用csrf def order_detail(request): uid = request.GET.get("uid") # 方法一: # row_object = models.Order.objects.filter(id=uid).first() # data_dict = { # "status": True, # "data": { # "title": row_object.title, # "price": row_object.price, # "status": row_object.status, # "admin": row_object.admin_id # } # } # return JsonResponse(data_dict) # values相当于obj变成了字典 row_dict = models.Order.objects.filter(id=uid).values("title", "price", "status", "admin_id").first() data_dict = { "status": True, "data": row_dict } return JsonResponse(data_dict) @csrf_exempt def order_edit(request): uid = request.GET.get("uid") row_object = models.Order.objects.filter(id=uid).first() form = OrderModelForm(data=request.POST, instance=row_object) if form.is_valid(): form.save() data_dict = {"status": True} return JsonResponse(data_dict) data_dict = {"status": False, "error": form.errors} return HttpResponse(json.dumps(data_dict))
对应的js代码如下:
function bindBtnSaveEvent(){ $("#btnSave").click(function(){ $(".error-msg").empty(); if(EDIT_ID){ doEdit(); }else{ doAdd(); } }); } function doEdit(){ $.ajax({ url: "/order/edit/?uid="+EDIT_ID, type: "post", data: $("#formAdd").serialize(), dataType: "JSON", success: function(res){ if(res.status){ alert("编辑任务成功"); $("#formAdd")[0].reset(); $('#myModal').modal('hide'); location.reload(); }else{ $.each(res.error,function(name,data){ $("#id_"+name).next().text(data[0]); }) } } }) } function doAdd(){ $.ajax({ url: "/order/add/", type: "post", data: $("#formAdd").serialize(), dataType: "JSON", success: function(res){ if(res.status){ alert("添加任务成功"); $("#formAdd")[0].reset(); $('#myModal').modal('hide'); location.reload(); }else{ $.each(res.error,function(name,data){ $("#id_"+name).next().text(data[0]); }) } } }) }
数据统计这一块使用echarts绘图比较方便,很多样例官网都有相应的代码,只是对于需要更改的数据,可以通过ajax发送请求传递数据,此处不多讲,详细内容看官网。
文件上传的提出,是因为有这样的需求。
比如你浏览网站,有时候收集信息,不是说让你填写表单,而是让你上传文件,那就要使用文件上传的内容了。
def upload_list(request): if request.method == "GET": return render(request, "upload_list.html") print(request.POST) # 请求体中的数据 print(request.FILES) # 请求发过来的文件 # < QueryDict: {'csrfmiddlewaretoken': ['8bdmV6XCTVyUSGI92LxmVp9iWPIdyKuKTNP0EbqcdOqUIJuSnO2YYPRjlxaFXsDE'], # 'username': ['wxm']} > # < MultiValueDict: {'avatar': [ < TemporaryUploadedFile: 证件照.jpg(image / jpeg) >]} > file_object = request.FILES.get("avatar") print(file_object.name) # 证件照.jpg f = open(file_object.name, mode="wb") for chunk in file_object.chunks(): f.write(chunk) f.close() return HttpResponse("请求成功")
对应的html:
{% extends 'layout.html' %}
{% block content %}
<form method="post" enctype="multipart/form-data">
{% csrf_token %}
<input type="text" name="username">
<input type="file" name="avatar">
<input type="submit" value="提交">
</form>
{% endblock %}
最后它给我上传到我的项目根目录了!
还有半个小时成绩就出来了,好激动好紧张好慌啊!!
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。