您现在的位置是: 网站首页 >Django >Vue+Django REST framework前后端分离生鲜电商 Django
【Vue+DRF生鲜电商】24.用户收货地址功能
admin2019年6月29日 22:07 【Django | Html | Vue 】 1223人已围观
Vue+Django REST framework前后端分离生鲜电商简介 Vue+Django REST framework 打造前后端分离的生鲜电商项目(慕课网视频)。 Github地址:https://github.com/xyliurui/DjangoOnlineFreshSupermarket ; Django版本:2.2、djangorestframework:3.9.2。 前端Vue模板可以直接联系我拿。
## 用户收货地址功能 对于收货地址,需要实现收货地址的增、删、改、查,所以需要继承的类有`mixins.ListModelMixin, mixins.UpdateModelMixin, mixins.DestroyModelMixin, mixins.CreateModelMixin, viewsets.GenericViewSet`,而这些类也可以合并为一个`viewsets.ModelViewSet`,点击去就可以看到继承关系: ![BLOG_20190629_221125_50](/media/blog/images/2019/06/BLOG_20190629_221125_50.png "博客图集BLOG_20190629_221125_50.png") ### 用户收货地址视图AddressViewSet 编辑 apps/user_operation/views.py ```python class AddressViewSet(viewsets.ModelViewSet): """ 收货地址管理 list: 获取收货地址 create: 添加收货地址 update: 更新收货地址 delete: 删除收货地址 """ permission_classes = (IsAuthenticated, IsOwnerOrReadOnly) # 用户必须登录才能访问 authentication_classes = (JWTAuthentication, SessionAuthentication) # 配置登录认证:支持JWT认证和DRF基本认证 ``` `permission_classes`和`authentication_classes`直接复制上面的即可,因为也需要用户登录认证才能完成的。 ### 用户收货地址序列化AddressSerializer 在前端上,用户的收货地址分为省市区 ![BLOG_20190629_221116_22](/media/blog/images/2019/06/BLOG_20190629_221116_22.png "博客图集BLOG_20190629_221116_22.png") 而之前我们定义的models中定义是不够的,原来的models为: ```python class UserAddress(models.Model): """ 用户收货地址 """ user = models.ForeignKey(User, verbose_name='用户', help_text='用户', on_delete=models.CASCADE, related_name='addresses') district = models.CharField(max_length=100, default='', verbose_name='区域', help_text='区域') address = models.CharField(max_length=200, default='', verbose_name='收货地址', help_text='收货地址') signer_name = models.CharField(max_length=20, default='', verbose_name='签收人', help_text='签收人') signer_mobile = models.CharField(max_length=11, verbose_name='联系电话', help_text='联系电话') add_time = models.DateTimeField(auto_now_add=True, verbose_name='添加时间') class Meta: verbose_name_plural = verbose_name = '收货地址' def __str__(self): return self.address ``` 所以需要进行修改,添加`province`和`city`两个字段 ```python class UserAddress(models.Model): """ 用户收货地址 """ user = models.ForeignKey(User, verbose_name='用户', help_text='用户', on_delete=models.CASCADE, related_name='addresses') province = models.CharField(max_length=100, default='', verbose_name='省份', help_text='省份') city = models.CharField(max_length=100, default='', verbose_name='城市', help_text='城市') district = models.CharField(max_length=100, default='', verbose_name='区域', help_text='区域') address = models.CharField(max_length=200, default='', verbose_name='收货地址', help_text='收货地址') signer_name = models.CharField(max_length=20, default='', verbose_name='签收人', help_text='签收人') signer_mobile = models.CharField(max_length=11, verbose_name='联系电话', help_text='联系电话') add_time = models.DateTimeField(auto_now_add=True, verbose_name='添加时间') class Meta: verbose_name_plural = verbose_name = '收货地址' def __str__(self): return self.address ``` 添加完成后一定要执行`makemigrations`和`migrate`。 编写收货地址序列化类,编辑 apps/user_operation/serializers.py 添加 ```python from .models import UserFav, UserLeavingMessage, UserAddress class AddressSerializer(serializers.ModelSerializer): user = serializers.HiddenField( default=serializers.CurrentUserDefault() # 表示user为隐藏字段,默认为获取当前登录用户 ) class Meta: model = UserAddress fields = ('id', 'user', 'province', 'city', 'district', 'address', 'signer_name', 'signer_mobile') ``` ### 完善用户收货地址视图AddressViewSet 添加序列化类`AddressSerializer` ```python from .serializers import UserFavSerializer, UserFavListSerializer, UserLeavingMessageSerializer, AddressSerializer from .models import UserFav, UserLeavingMessage, UserAddress class AddressViewSet(viewsets.ModelViewSet): """ 收货地址管理 list: 获取收货地址 create: 添加收货地址 update: 更新收货地址 delete: 删除收货地址 """ permission_classes = (IsAuthenticated, IsOwnerOrReadOnly) # 用户必须登录才能访问 authentication_classes = (JWTAuthentication, SessionAuthentication) # 配置登录认证:支持JWT认证和DRF基本认证 queryset = UserAddress.objects.all() serializer_class = AddressSerializer def get_queryset(self): return self.queryset.filter(user=self.request.user) ``` ### 注册收货地址url 编辑 DjangoOnlineFreshSupermarket/urls.py ,注册`address`这个url ```python from user_operation.views import UserFavViewSet, UserLeavingMessageViewSet, AddressViewSet router.register(r'address', AddressViewSet, base_name='address') # 用户收货地址 ``` 查看Server是否已经重启。 ### DRF Docs中测试address功能 访问 http://127.0.0.1:8000/docs/#address 可以看到新增的API ![BLOG_20190629_221104_70](/media/blog/images/2019/06/BLOG_20190629_221104_70.png "博客图集BLOG_20190629_221104_70.png") 在`create`中创建一个收货地址 ![BLOG_20190629_221058_96](/media/blog/images/2019/06/BLOG_20190629_221058_96.png "博客图集BLOG_20190629_221058_96.png") 添加完信息后,点击Send Request,就可以在右上角看到返回的数据 在`list`中点击Send Request就可以看到返回的列表信息 ![BLOG_20190629_221050_36](/media/blog/images/2019/06/BLOG_20190629_221050_36.png "博客图集BLOG_20190629_221050_36.png") ### Vue中收货地址接口联调 api放在 src/api/api.js 中 ```JavaScript //添加收货地址 export const addAddress = params => { return axios.post(`${local_host}/address/`, params) }; //删除收货地址 export const delAddress = addressId => { return axios.delete(`${local_host}/address/` + addressId + '/') }; //修改收货地址 export const updateAddress = (addressId, params) => { return axios.patch(`${local_host}/address/` + addressId + '/', params) }; //获取收货地址 export const getAddress = () => { return axios.get(`${local_host}/address/`) }; ``` Vue收获地址管理的页面在 src/views/member/receive.vue 中 当进入这个组件后,会调用`getReceiveInfo()` ```JavaScript created() { this.getReceiveInfo(); }, ``` 然后调用`getAddress()`,也就是请求`getAddress`的api ```JavaScript getReceiveInfo() { //获取收件人信息 getAddress().then((response) => { //console.log(response.data); this.receiveInfoArr = response.data; }).catch(function (error) { console.log(error); }); }, ``` 获取到数据之后,传递给`receiveInfoArr`,然后遍历得到所有地址列表 ```html <table width="100%" border="0" cellpadding="5" cellspacing="1" bgcolor="#dddddd" v-for="(item, index) in receiveInfoArr"> <tbody> <tr> <td align="right" bgcolor="#ffffff">配送区域:</td> <td colspan="3" align="left" bgcolor="#ffffff"> <div class="addr" @click="bubble(index)"> <v-distpicker :province="item.province" :city="item.city" :area="item.district" @province="updateProvince" @city="updateCity" @area="updateArea"></v-distpicker> </div> </td> </tr> <tr> <td align="right" bgcolor="#ffffff">收货人姓名:</td> <td align="left" bgcolor="#ffffff"><input name="consignee" type="text" class="inputBg" id="consignee_0" value="ssss" v-model="item.signer_name"> <span :class="{error:item.signer_name==''}">(必填)</span> </td> </tr> <tr> <td align="right" bgcolor="#ffffff">详细地址:</td> <td align="left" bgcolor="#ffffff"><input name="address" type="text" class="inputBg" id="address_0" v-model="item.address"> <span :class="{error:item.address==''}">(必填)</span></td> </tr> <tr> <td align="right" bgcolor="#ffffff">手机:</td> <td align="left" bgcolor="#ffffff"><input name="mobile" type="text" class="inputBg" id="mobile_0" v-model="item.signer_mobile"><span :class="{error:item.signer_mobile==''}">(必填)</span></td> </tr> <tr> <td align="right" bgcolor="#ffffff"> </td> <td colspan="3" align="center" bgcolor="#ffffff"> <button class="bnt_blue_2" @click="confirmUpdate(item.id, index)">确定修改</button> <button class="bnt_blue_2" @click="deleteInfo(item.id)">删除</button> </td> </tr> </tbody> </table> ``` 访问 http://127.0.0.1:8080/#/app/home/member/receive 可以看到前端展示的收货地址 ![BLOG_20190629_221038_11](/media/blog/images/2019/06/BLOG_20190629_221038_11.png "博客图集BLOG_20190629_221038_11.png") #### Vue中新增收货地址 ![BLOG_20190629_221032_86](/media/blog/images/2019/06/BLOG_20190629_221032_86.png "博客图集BLOG_20190629_221032_86.png") 添加完成之后,可以看到列表自动刷新了 ![BLOG_20190629_221027_39](/media/blog/images/2019/06/BLOG_20190629_221027_39.png "博客图集BLOG_20190629_221027_39.png") ```html <table width="100%" border="0" cellpadding="5" cellspacing="1" bgcolor="#dddddd"> <tbody> <tr> <td align="right" bgcolor="#ffffff">配送区域:</td> <td colspan="3" align="left" bgcolor="#ffffff"> <div class="addr"> <v-distpicker :province="newInfo.province" :city="newInfo.city" :area="newInfo.district" @province="getProvince" @city="getCity" @area="getArea"></v-distpicker> </div> </td> </tr> <tr> <td align="right" bgcolor="#ffffff">收货人姓名:</td> <td align="left" bgcolor="#ffffff"><input name="consignee" type="text" class="inputBg" id="consignee_0" value="ssss" v-model="newInfo.signer_name"> <span :class="{error:newInfo.signer_name==''}">(必填)</span></td> </tr> <tr> <td align="right" bgcolor="#ffffff">详细地址:</td> <td align="left" bgcolor="#ffffff"><input name="address" type="text" class="inputBg" id="address_0" v-model="newInfo.address"> <span :class="{error:newInfo.address==''}">(必填)</span></td> </tr> <tr> <td align="right" bgcolor="#ffffff">手机:</td> <td align="left" bgcolor="#ffffff"><input name="mobile" type="text" class="inputBg" id="mobile_0" v-model="newInfo.signer_mobile"><span :class="{error:newInfo.signer_mobile==''}">(必填)</span></td> </tr> <tr> <td align="right" bgcolor="#ffffff"> </td> <td colspan="3" align="center" bgcolor="#ffffff"> <button class="bnt_blue_2" @click="addReceive">新增收货地址</button> </td> </tr> </tbody> </table> ``` 当用户点击 新增收货地址 ,会调用`addReceive()`函数 ```JavaScript addReceive() { //提交收获信息 addAddress(this.newInfo).then((response) => { alert('添加成功'); // 重置新的 this.getReceiveInfo(); this.newInfo = Object.assign({}, this.newInfoEmpty); }).catch(function (error) { console.log(error); }); }, ``` 然后请求`addAddress`api,请求成功后,请求`getReceiveInfo()`刷新收货地址列表,清空输入框 #### Vue中删除收货地址 当用户点击`<button class="bnt_blue_2" @click="deleteInfo(item.id)">删除</button>`删除时,调用`deleteInfo(id, index)`函数 ```JavaScript deleteInfo(id, index) { // 删除收获人信息 delAddress(id).then((response) => { alert('删除成功'); this.getReceiveInfo(); }).catch(function (error) { console.log(error); }); } ``` 之后调用`delAddress(id)`api进行地址删除,删除成功后弹框提示,并刷新收货地址列表。 #### Vue中修改收货地址 当用户点击`<button class="bnt_blue_2" @click="confirmUpdate(item.id, index)">确定修改</button>`会调用`confirmUpdate(id, index)`函数 ```JavaScript confirmUpdate(id, index) { // 更新收获信息 updateAddress(id, this.receiveInfoArr[index]).then((response) => { alert('修改成功'); this.getReceiveInfo(); }).catch(function (error) { console.log(error); }); }, ``` 之后调用`updateAddress(id, this.receiveInfoArr[index])`api进行地址更新,更新成功后弹框提示,并刷新收货地址列表。 ![BLOG_20190629_221015_26](/media/blog/images/2019/06/BLOG_20190629_221015_26.png "博客图集BLOG_20190629_221015_26.png")
很赞哦! (0)
相关文章
文章交流
- emoji
当前用户
未登录,点击 登录专题目录
- 【Vue+DRF生鲜电商】01.课程结构介绍,开发环境搭建
- 【Vue+DRF生鲜电商】02.设置users、goods、trade、user_operation数据库并导入原始数据
- 【Vue+DRF生鲜电商】03.Restful API基础
- 【Vue+DRF生鲜电商】04.Vue项目结构介绍
- 【Vue+DRF生鲜电商】05.商品列表序列化普通方法
- 【Vue+DRF生鲜电商】06.DRF环境配置,使用Serializer类序列化商品列表
- 【Vue+DRF生鲜电商】07.序列化商品分页功能
- 【Vue+DRF生鲜电商】08.ViewSets & Routers显示商品列表
- 【Vue+DRF生鲜电商】09.使用DRF的filter过滤商品列表
- 【Vue+DRF生鲜电商】10.商品分类层级获取,Vue跨域请求商品分类
- 【Vue+DRF生鲜电商】11.Vue展示左侧分类、面包屑、排序、商品列表、分页
- 【Vue+DRF生鲜电商】12.用户登录之DRF Token认证登录原理和使用方法
- 【Vue+DRF生鲜电商】13.JWT用户认证原理配置,Vue登录接口调试
- 【Vue+DRF生鲜电商】14.用户注册发送短信验证码、登录字段验证
- 【Vue+DRF生鲜电商】15.用户注册使用信号量实现密码加密
- 【Vue+DRF生鲜电商】16.Vue中注册、退出功能交互
- 【Vue+DRF生鲜电商】17.DRF实现商品详情及热卖商品接口,Vue中显示商品详情和热卖
- 【Vue+DRF生鲜电商】18.用户收藏、取消收藏商品接口实现
- 【Vue+DRF生鲜电商】19.用户添加、删除收藏权限处理,根据商品id显示收藏,在Vue中实现收藏功能
- 【Vue+DRF生鲜电商】20.使用DRF自动生成文档的功能
- 【Vue+DRF生鲜电商】21.用户中心个人资料的展示,并在Vue中实现个人资料更新
- 【Vue+DRF生鲜电商】22.个人中心显示用户收藏功能,对收藏进行删除
- 【Vue+DRF生鲜电商】23.个人中心用户留言功能
- 【Vue+DRF生鲜电商】24.用户收货地址功能
- 【Vue+DRF生鲜电商】25.商品添加购物车接口功能,Vue和购物车联调
- 【Vue+DRF生鲜电商】26.使用Pycharm远程代码调试服务器Django代码
- 【Vue+DRF生鲜电商】26.订单接口功能,Vue和订单接口联调
- 【Vue+DRF生鲜电商】27.支付宝公钥,私钥,沙箱环境配置
- 【Vue+DRF生鲜电商】28.支付宝支付接口类解读,支付逻辑编辑
- 【Vue+DRF生鲜电商】29.线上服务支付宝接口和Vue联调,Django代理Vue运行
- 【Vue+DRF生鲜电商】30.首页轮播图、新品展示功能
- 【Vue+DRF生鲜电商】31.首页商品按分类显示推荐功能
- 【Vue+DRF生鲜电商】32.商品操作后计数更改,热搜榜关键字功能实现
- 【Vue+DRF生鲜电商】33.数据缓存、接口访问限速功能
- 【Vue+DRF生鲜电商】34.第三方登录(微博、qq和微信)之微博登录登录测试
- 【Vue+DRF生鲜电商】35.使用social-app-django集成第三方登录