第一步: 设计app

1. 根据业务需求,设计合适的app板块,这里,我们将拥有goods,trade,user_operation, users四个app

2. 然后去注册app

第二步: 设计users.models

1. users.models.py

  1. from datetime import datetime # 用于addtime字段
  2.  
  3. from django.db import models
    from django.contrib.auth.models import AbstractUser
  4.  
  5. # 用户信息,继承django自带的AbstractUser
    class UserProfile(AbstractUser):
    # 注册的时候,姓名可以为空
    name = models.CharField(max_length=30, null=True, blank=True, verbose_name="姓名")
    birthday = models.DateField(null=True, blank=True, verbose_name="出生年月")
    gender = models.CharField(max_length=6, choices=(("male", "男"), ("female", "女")), default="female",
    verbose_name="性别")
    # 电话不能为空
    mobile = models.CharField(max_length=11, verbose_name="电话")
    email = models.EmailField(max_length=100, null=True, blank=True, verbose_name="邮箱")
  6.  
  7. class Meta:
    verbose_name = "用户"
    verbose_name_plural = verbose_name
  8.  
  9. def __str__(self):
    return self.name
  10.  
  11. # 手机验证码,可以放在redis内存中,也可以存在数据库中,这里我们存在数据库中
    class VerifyCode(models.Model):
    code = models.CharField(max_length=10, verbose_name="验证码")
    mobile = models.DateField(max_length=11, verbose_name="电话")
    # 千万不要写成datetime.now(),否则在编译的时候就添加时间了
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  12.  
  13. class Meta:
    verbose_name = "短信验证码"
    verbose_name_plural = verbose_name
  14.  
  15. def __str__(self):
    return self.code

2. 千万别忘记这个设置, 有了这个,django才知道你要用自己的user表

settings.py

  1. AUTH_USER_MODEL='users.UserProfile'

第三步: 设计goods.models

首先分析goods需要多少个类,可发现从分类上来看有三类,第一类与第二类是一对多的关系,第二类与第三类也是一对多的关系,因此需要创建三个类,但是这种做法并不灵活,如果以后要改成2个类,或者改成4个类,就很麻烦,这里有一种方法可以实现一个类就可以无限分类的目的

1. goods.models.py

  1. from datetime import datetime
  2.  
  3. from django.db import models
    from DjangoUeditor.models import UEditorField
  4.  
  5. # 商品类别
    class GoodsCategory(models.Model):
    """
    商品类别
    name 商品中文名
    code 商品英文名
    """
    CATEGORY_TYPE = (
    (1, "一级类目"),
    (2, "二级类目"),
    (3, "三级类目"),
    )
    # help_text 用在后面生成文档中
    name = models.CharField(default="", max_length=30, verbose_name="类别名", help_text="类别名")
    code = models.CharField(default="", max_length=30, verbose_name="类别code", help_text="类别code")
    desc = models.TextField(default="", verbose_name="类别描述", help_text="类别描述")
    category_type = models.IntegerField(choices=CATEGORY_TYPE, verbose_name="类目级别", help_text="类目级别")
    # "self"关键字就可以实现自己外键自己,从而达到无限分类的目的
    parent_category = models.ForeignKey("self", null=True, blank=True, verbose_name="父类目级别", help_text="父类目级别",
    # 后面查询的时候会用到related_name
    related_name="sub_cat")
    is_tab = models.BooleanField(default=False, verbose_name="是否导航", help_text="是否导航")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  6.  
  7. class Meta:
    verbose_name = "商品类别"
    verbose_name_plural = verbose_name
  8.  
  9. def __str__(self):
    return self.name
  10.  
  11. # 品牌信息
    class GoodsCategoryBrand(models.Model):
    """
    品牌名与品牌图片
    """
    # 这个外键指定了哪些类别才拥有品牌信息
    category = models.ForeignKey(GoodsCategory, null=True, blank=True, verbose_name="商品类目")
    name = models.CharField(max_length=30, default="", verbose_name="品牌名", help_text="品牌名")
    desc = models.TextField(max_length=200, default="", verbose_name="品牌描述", help_text="品牌描述")
    image = models.ImageField(max_length=200, upload_to="brand/images")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  12.  
  13. class Meta:
    verbose_name = "品牌信息"
    verbose_name_plural = verbose_name
  14.  
  15. def __str__(self):
    return self.name
  16.  
  17. # 商品详情
    class Goods(models.Model):
    category = models.ForeignKey(GoodsCategory, verbose_name="商品类目")
    goods_sn = models.CharField(max_length=50, default="", verbose_name="商品唯一货号")
    name = models.CharField(max_length=100, verbose_name="商品名")
    click_num = models.IntegerField(default=0, verbose_name="点击数")
    sold_num = models.IntegerField(default=0, verbose_name="商品销售量")
    fav_num = models.IntegerField(default=0, verbose_name="收藏数")
    goods_num = models.IntegerField(default=0, verbose_name="库存数")
    market_price = models.FloatField(default=0, verbose_name="市场价格")
    shop_price = models.FloatField(default=0, verbose_name="本店价格")
    goods_brief = models.TextField(default=500, verbose_name="商品简短描述")
    goods_desc = UEditorField(verbose_name="内容", imagePath="goods/images/", width=1000, height=300,
    filePath="goods/files/", default="")
    ship_free = models.BooleanField(default=True, verbose_name="是否承担运费")
    # 商品封面图
    goods_front_image = models.ImageField(upload_to="", null=True, blank=True, verbose_name="封面图")
    # 是否是新品
    is_new = models.BooleanField(default=False, verbose_name="是否新品")
    # 是否是热卖商品
    is_hot = models.BooleanField(default=False, verbose_name="是否热销")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  18.  
  19. class Meta:
    verbose_name = "商品详情"
    verbose_name_plural = verbose_name
  20.  
  21. def __str__(self):
    return self.name
  22.  
  23. # 商品轮播图
    class GoodsImage(models.Model):
    goods = models.ForeignKey(Goods, verbose_name="商品", related_name="images")
    image = models.ImageField(upload_to="", verbose_name="图片", null=True, blank=True)
  24.  
  25. add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  26.  
  27. class Meta:
    verbose_name = "商品图片"
    verbose_name_plural = verbose_name
  28.  
  29. def __str__(self):
    return self.goods.name
  30.  
  31. # 首页的轮播商品
    class Banner(models.Model):
    goods = models.ForeignKey(Goods, verbose_name="商品")
    image = models.ImageField(upload_to="banner/", verbose_name="轮播图片")
    index = models.IntegerField(default=0, verbose_name="轮播顺序")
  32.  
  33. add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  34.  
  35. class Meta:
    verbose_name = "轮播商品"
    verbose_name_plural = verbose_name
  36.  
  37. def __str__(self):
    return self.goods.name

第四步: 设计trade.models

首先分析trade需要多少个表,电商里面有两个概念很重要: 购物车, 和订单

  1. 同一个商品对同一个用户来说, 只有一条记录,只是数量不一样

  2. 一旦点击去结算, 那么购物车就会被清空,而变成订单

  1. from datetime import datetime
  2.  
  3. from django.db import models
    from django.contrib.auth import get_user_model
  4.  
  5. from goods.models import Goods
    User=get_user_model()
  6.  
  7. # 购物车
    class ShoppingCart(models.Model):
    uer=models.ForeignKey(User,verbose_name="用户")
    goods=models.ForeignKey(Goods,verbose_name="商品")
    nums=models.IntegerField(default=0,verbose_name="购买数量")
  8.  
  9. add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  10.  
  11. class Meta:
    verbose_name = "购物车"
    verbose_name_plural = verbose_name
  12.  
  13. def __str__(self):
    return f"{self.goods.name}({self.nums})"
  14.  
  15. # 订单详情
    class OrderInfo:
    ORDER_STATUS=(
    ("success","成功"),
    ("cancel","取消"),
    ("cancel","待支付"),
    )
    user=models.ForeignKey(User)
    order_sn=models.CharField(max_length=30,unique=True,verbose_name="订单号")
    trade_no=models.CharField(max_length=100,unique=True,null=True,blank=True,verbose_name="交易号")
    pay_status=models.CharField(choices=ORDER_STATUS,max_length=10,verbose_name="订单状态")
    post_script=models.CharField(max_length=200,verbose_name="订单留言")
    order_mount=models.FloatField(default=0.0,verbose_name="订单金额")
    pay_time=models.DateTimeField(null=True,blank=True,verbose_name="支付时间")
  16.  
  17. # 用户信息
    address = models.CharField(max_length=100, default="", verbose_name="收货地址")
    signer_name = models.CharField(max_length=20, default="", verbose_name="签收人")
    singer_mobile = models.CharField(max_length=11, verbose_name="联系电话")
  18.  
  19. add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  20.  
  21. class Meta:
    verbose_name = "订单"
    verbose_name_plural = verbose_name
  22.  
  23. def __str__(self):
    return str(self.order_sn)
  24.  
  25. # 订单的商品详情(与订单是多对一)
    class OrderGoods(models.Model):
    order = models.ForeignKey(OrderInfo, verbose_name="订单信息", related_name="goods")
    goods = models.ForeignKey(Goods, verbose_name="商品")
    goods_num = models.IntegerField(default=0, verbose_name="商品数量")
  26.  
  27. add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  28.  
  29. class Meta:
    verbose_name = "订单商品"
    verbose_name_plural = verbose_name
  30.  
  31. def __str__(self):
    return str(self.order.order_sn)
  32.  
  1. 4. 会自动生成文件夹 node_modules,里面

第五步: 设计useroperation.models

首先分析需要多少个表, 用户收藏, 用户收货地址, 用户评论

  1. from datetime import datetime
  2.  
  3. from django.db import models
    from django.contrib.auth import get_user_model
  4.  
  5. from goods.models import Goods
  6.  
  7. User = get_user_model()
  8.  
  9. # 用户收藏
    class UserFav(models.Model):
    user = models.ForeignKey(User, verbose_name="用户")
    goods = models.ForeignKey(Goods, verbose_name="商品")
  10.  
  11. add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  12.  
  13. class Meta:
    verbose_name = "用户收藏"
    verbose_name_plural = verbose_name
  14.  
  15. def __str__(self):
    return self.user.name
  16.  
  17. # 用户留言
    class UserLeavingMessage(models.Model):
    MESSAGE_CHOICES = (
    (1, "留言"),
    (2, "投诉"),
    (3, "询问"),
    (4, "售后"),
    (5, "求购")
    )
    user = models.ForeignKey(User, verbose_name="用户")
    message_type = models.IntegerField(default=1, choices=MESSAGE_CHOICES, verbose_name="留言类型",
    help_text="留言类型: 1(留言),2(投诉),3(询问),4(售后),5(求购)")
    subject = models.CharField(max_length=100, default="", verbose_name="主题")
    message = models.TextField(default="", verbose_name="留言内容", help_text="留言内容")
    file = models.FileField(upload_to="message/images/", verbose_name="上传的文件", help_text="上传的文件")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  18.  
  19. class Meta:
    verbose_name = "用户留言"
    verbose_name_plural = verbose_name
  20.  
  21. def __str__(self):
    return self.subject
  22.  
  23. # 用户收货地址
    class UserAddress(models.Model):
    user = models.ForeignKey(User, verbose_name="用户")
    district = models.CharField(max_length=100, default="", verbose_name="区域")
    address = models.CharField(max_length=100, default="", verbose_name="详细地址")
    signer_name = models.CharField(max_length=100, default="", verbose_name="签收人")
    signer_mobile = models.CharField(max_length=11, default="", verbose_name="电话")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加时间")
  24.  
  25. class Meta:
    verbose_name = "收货地址"
    verbose_name_plural = verbose_name
  26.  
  27. def __str__(self):
    return self.address

第六步: makemigrations和migrate

不赘述, 补充一点的就是如果遇到migrate不生效, 应该如何解决? 见下图, 删除后, 重新makemigrations和migrate即可

------  over  -----------

settings.py

  1. AUTH_USER_MODEL='users.UserProfile'

4. 会自动生成文件夹 ,node_modules,里面

settings.py

  1. AUTH_USER_MODEL='users.UserProfile'

4. 会自动生成文件夹 ,node_modules,里面

(生鲜项目)02. app与model设计的更多相关文章

  1. 3- vue django restful framework 打造生鲜超市 - model设计和资源导入

    3- vue django restful framework 打造生鲜超市 - model设计和资源导入 使用Python3.6与Django2.0.2(Django-rest-framework) ...

  2. Java生鲜电商平台-API接口设计之token、timestamp、sign 具体架构与实现(APP/小程序,传输安全)

    Java生鲜电商平台-API接口设计之token.timestamp.sign 具体设计与实现 说明:在实际的业务中,难免会跟第三方系统进行数据的交互与传递,那么如何保证数据在传输过程中的安全呢(防窃 ...

  3. Java生鲜电商平台-小程序或者APP优惠券的设计与源码实战

    Java生鲜电商平台-小程序或者APP优惠券的设计与源码实战 说明:Java生鲜电商平台-小程序或者APP优惠券的设计与源码实战,优惠券是一种常见的促销方式,在规定的周期内购买对应商品类型和额度的商品 ...

  4. [转]Android App整体架构设计的思考

    1. 架构设计的目的 对程序进行架构设计的原因,归根到底是为了提高生产力.通过设计使程序模块化,做到模块内部的高聚合和模块之间的低耦合.这样做的好处是使得程序在开发的过程中,开发人员只需要专注于一点, ...

  5. Java开源生鲜电商平台-通知模块设计与架构(源码可下载)

    Java开源生鲜电商平台-通知模块设计与架构(源码可下载) 说明:对于一个生鲜的B2B平台而言,通知对于我们实际的运营而言来讲分为三种方式:           1. 消息推送:(采用极光推送)   ...

  6. Java生鲜电商平台-系统报表设计与架构

    Java生鲜电商平台-系统报表设计与架构 说明:任何一个运行的平台都需要一个很清楚的报表来显示,那么作为Java开源生鲜电商平台而言,我们应该如何设计报表呢?或者说我们希望报表来看到什么数据呢?   ...

  7. 网站开发学习Python实现-Django的models学习-生鲜项目(6.3.2)

    @ 目录 1.说明 2.模型类的设计 3.代码的具体实现 4.详情地址 关于作者 1.说明 models是django的很重要的部分,所以深入研究. 本文章的所研究项目为黑马教育python课程中的项 ...

  8. 15款优秀移动APP产品原型设计工具

    一新来小盆友问:“移动产品原型设计都用啥工具?” 答:“@#¥……&%*” 又问:“能详细说下各个工具吗?我比较一下” “……” 好吧,谁让我那么的爱分享而你又是小美女呢 ———————正文开 ...

  9. Android App的架构设计:从VM、MVC、MVP到MVVM

    随着Android应用开发规模的扩大,客户端业务逻辑也越来越复杂,已然不是简单的数据展示了.如同后端开发遇到瓶颈时采用的组件拆分思想,客户端也需要进行架构设计,拆分视图和数据,解除模块之间的耦合,提高 ...

随机推荐

  1. 《逆袭团队》第九次团队作业:Beta冲刺与验收准备

    项目 内容 软件工程 任课教师博客主页链接 作业链接地址 团队作业9:Beta冲刺与团队项目验收 团队名称 逆袭团队 具体目标 (1)掌握软件黑盒测试技术:(2)学会编制软件项目总结PPT.项目验收报 ...

  2. springboot 整合Swagger2的使用

    Swagger2相较于传统Api文档的优点 手写Api文档的几个痛点: 文档需要更新的时候,需要再次发送一份给前端,也就是文档更新交流不及时. 接口返回结果不明确 不能直接在线测试接口,通常需要使用工 ...

  3. HDU4091:Zombie’s Treasure Chest (分类-数学)

    题意:给两种宝石,体积S1,S2,价值V1,V2,背包容量n,求最大收益. 所有数据都在32位整数范围内. 思路:只有两种物品的背包,显然不是常见的背包,应该从背包之外的思路下手. 1:可以猜想其中一 ...

  4. AOP_原理

    什么是AOPAOP(Aspect-OrientedProgramming,面向方面编程),可以说是OOP(Object-Oriented Programing,面向对象编程)的补充和完善.OOP引入封 ...

  5. C++内存分配/分布——堆栈存储区

    FROM: C++内存分配方式详解——堆.栈.自由存储区.全局/静态存储区和常量存储区 栈,就是那些由编译器在需要的时候分配,在不需要的时候自动清除的变量的存储区.里面的变量通常是局部变量.函数参数等 ...

  6. 洛谷 P3605 [USACO17JAN]Promotion Counting晋升者计数

    题目描述 The cows have once again tried to form a startup company, failing to remember from past experie ...

  7. Optimal Marks SPOJ - OPTM(最小割)

    传送门 论文<最小割模型在信息学竞赛中的应用>原题 二进制不同位上互不影响,那么就按位跑网络流 每一位上,确定的点值为1的与S连一条容量为INF的有向边.为0的与T连一条容量为INF的有向 ...

  8. 2019.12.07 java基础

    编译时报错,叫做编译失败 class Demo01 { public static void main(String[] args) { int a; a=12; System.out.println ...

  9. C# 监测每个方法的执行次数和占用时间(测试5)

    又找到了一个bug 测试的类: public class Class11_1 { public virtual List<int> test2_1(List<tb_SensorRec ...

  10. 洛谷 P2312 解方程 题解

    P2312 解方程 题目描述 已知多项式方程: \[a_0+a_1x+a_2x^2+\cdots+a_nx^n=0\] 求这个方程在 [1,m][1,m] 内的整数解(\(n\) 和 \(m\) 均为 ...