02-model設計

1、項目依賴包安裝

一、安裝Django(2.2.7)html

pip3 install django

二、安裝DjangoRestFramework前端

由於DjangoRestFramework是基於Django開發的,所以安裝以前必須安裝Djangopython

pip3 install djangorestframework

 

 

 三、安裝markdown和django-filtermysql

pip3 install markdown django-filter

 四、Pycharm建立項目git

  更換虛擬環境,這樣便於開發所安裝特定的包,然而包環境都有特定的,便於管理。github

 

 

 

 五、測試項目是否正常redis

  必定要將MxShop下的urls.py中的文件中的admin註釋掉,由於咱們沒有註冊admin因此必定會報錯,說是沒有定義admin,所以須要註釋在運行。sql

 

 

 

 

 

 測試成功,說明項目沒出現問題,接下來開始整個項目最重要的一環啦,項目中的設置。數據庫

六、settings.py中的數據庫設置(第一個是默認的,第二個是配置的)django

# Database
# https://docs.djangoproject.com/en/2.2/ref/settings/#databases

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.sqlite3',
        'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
    }
}
# Database
# https://docs.djangoproject.com/en/2.2/ref/settings/#databases

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.mysql',#聲明鏈接什麼數據庫
        'NAME': "mxshop",#數據庫的名字
        'USER': 'root',#數據庫用戶名
        'PASSWORD': '',#數據庫的密碼,
        'HOST': '127.0.0.1',#數據庫地址
        'PORT':'3306',#數據庫端口
    }
}

而後來到虛擬環境配置相關包

七、安裝pymysql進行相關配置

pip3 install pymysql

 

 八、數據庫建立

   

而後運行,發現有以下錯誤:

 說的是mysqlclient版本不一致,直接往報錯的一行點進去,找到報錯的點,而後進去註釋相關語句:(不要懼怕源碼,源碼都是咱們的工具,改動工具只是爲了更好地造坦克)

改動完,運行試試,就能夠發現完成啦,固然還有其餘辦法好比直接安裝驅動mysqlclient(支持全部版本),設置裏面數據庫配置,就能夠愉快比這個更快完成

 

 windows安裝這些包都容易出錯,所以能夠找到前面一篇那個包錯誤網址,進去直接搜索找到對應版本的包手動下載安裝。

九、安裝圖片處理包pillow

pip3 install -i https://pypi.douban.com/simple pillow

 

 

 十、項目中創建須要的文件包或者文件夾

   apps是將全部的應用拖到這下面,方便管理,extra_apps是將一些不想安裝到虛擬環境的包,下載源碼放到這裏面,這樣便於咱們修改源碼,打造咱們想要的狀況。media文件夾是保存上傳的一些文件。

十一、項目設置裏面設置識別路徑

添加這兩行代碼:#將appsextra_apps加入到路徑中來,以便撰寫代碼方便

import sys

sys.path.insert(0,BASE_DIR)
sys.path.insert(0,os.path.join(BASE_DIR,"apps"))
sys.path.insert(0,os.path.join(BASE_DIR,"extra_apps"))

 2、app應用模型設計

                

 一、建立應用

  根據前端顯示的頁面,分析出須要設計的app應用,而後建立應用

 

 

二、在項目settings.py註冊應用

# Application definition

INSTALLED_APPS = [
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'users.apps.UsersConfig',
    'users', #將咱們建立的app註冊到這裏面來 'goods',
    'trade',
    'user_operation',
]

 3、模型類設計

一、應用users模型類設計(編寫代碼須要遵循PEP8規範)

  咱們須要從新設計用戶的模型類,Django自帶的模型類不能知足咱們的要求,所以從新繼承django.contrib.auth.models.AbstractUser這個類,新增長咱們須要的新字段。

users.models.py:

from django.contrib.auth.models import AbstractUser

# Create your models here.


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="郵箱")

    class Meta:
        verbose_name = "用戶"
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.name

  通過分析,會發現與用戶相關的驗證碼,也須要保存到用戶這裏,固然能夠保存到redis裏更佳,爲了積累項目的流程,增長本身對項目的理解,須要將驗證碼保存到數據庫,以便於對整個項目開發有更深的理解。

users.models.py

from datetime import datetime


class VerifyCode(models.Model):
    """
    短信驗證碼
    """
    code = models.CharField(max_length=10,verbose_name="驗證碼")
    mobile = models.CharField(max_length=11, verbose_name="電話")
    #不用括號是模型類調用的時間,然而加括號是模型類遷移的時間
    add_time = models.DateTimeField(default=datetime.now,verbose_name="添加時間")

    class Meta:
        verbose_name = "短信驗證碼"
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.code

UserProfile設計完成以後,沒有替換系統的用戶,所以咱們須要到項目settings.py中去添加下面這一行:

AUTH_USER_MODEL = "users.UserProfile"

 

 

 二、應用goods的模型類設計(PEP8規範)

經過一個模型類完成商品的級別分類,

goods.models.py:

from datetime import datetime


from django.db import models
from DjangoUeditor.models import UEditorField

# Create your models here.


class GoodsCategory(models.Model):
    """
    商品類別(好比生鮮食品<----海鮮水產<---魚)
    這樣就能夠將全部商品放到一個表中
    """
    CATEGORY_TYPE = (
        (1,"一級類目"),
        (2,"二級類目"),
        (3,"三級類目")
    )
    #help_text之後文檔有用,related_name之後查詢有用
    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.CharField(choices=CATEGORY_TYPE,verbose_name="類目級別",help_text="類目級別")
    parent_category = models.ForeignKey("self",null=True,blank=True,verbose_name="父類目級別",related_name="sub_cat",help_text="父目錄")
    is_tab = models.BooleanField(default=False,verbose_name="是否導航",help_text="是否導航")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加時間")

    class Meta:
        verbose_name = "商品類別"
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.name


class GoodsCategoryBrand(models.Model):
    """
    品牌名
    """
    name = models.CharField(default="",max_length=30,verbose_name="品牌名",help_text="品牌名")
    desc = models.TextField(default="",max_length=200,verbose_name="品牌描述",help_text="品牌描述")
    image = models.ImageField(max_length=200,upload_to="brand/images/")
    add_time = models.DateTimeField(default=datetime.now,verbose_name="添加時間")

    class Meta:
        verbose_name = "品牌"
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.name


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(max_length=500, verbose_name="商品簡短描述")
    goods_desc = UEditorField(verbose_name=u"內容", 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="goods/images/", 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="添加時間")

    class Meta:
        verbose_name = '商品'
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.name


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="輪播順序")
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加時間")

    class Meta:
        verbose_name = '輪播商品'
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.goods.name


class GoodsImage(models.Model):
    """
    商品輪播圖
    """
    goods = models.ForeignKey(Goods, verbose_name="商品", related_name="images")
    image = models.ImageField(upload_to="", verbose_name="圖片", null=True, blank=True)
    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加時間")

    class Meta:
        verbose_name = '商品圖片'
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.goods.name
goods.models.py

代碼裏面的DjangoUeditor是富文本編輯器,是基於Django編寫的,所以去github上找到py3支持的版本,下載源碼,複製到extra_apps

 

 而後去到項目設置settings.py中註冊extra_apps中的DjangoUeditor

 

 三、應用trade的模型類設計(PEP8規範)

from datetime import datetime

from django.db import models
from django.contrib.auth import get_user_model

from goods.models import Goods
#這裏調用UserProfile直接調用django的配置方法,返回值就是UserProfile模型,
#這樣的好處就是,不用知道用戶模型類也能夠調用
User = get_user_model()
# Create your models here.


class ShoppingCart(models.Model):
    """
    購物車
    """
    user = models.ForeignKey(User, verbose_name=u"用戶")
    goods = models.ForeignKey(Goods, verbose_name=u"商品")
    nums = models.IntegerField(default=0, verbose_name="購買數量")

    add_time = models.DateTimeField(default=datetime.now, verbose_name=u"添加時間")

    class Meta:
        verbose_name = '購物車'
        verbose_name_plural = verbose_name
        unique_together = ("user", "goods")

    def __str__(self):
        return "%s(%d)".format(self.goods.name, self.nums)


class OrderInfo(models.Model):
    """
    訂單
    """
    ORDER_STATUS = (
        ("TRADE_SUCCESS", "成功"),
        ("TRADE_CLOSED", "超時關閉"),
        ("WAIT_BUYER_PAY", "交易建立"),
        ("TRADE_FINISHED", "交易結束"),
        ("paying", "待支付"),
    )

    user = models.ForeignKey(User, verbose_name="用戶")
    order_sn = models.CharField(max_length=30, null=True, blank=True, unique=True, verbose_name="訂單號")
    trade_no = models.CharField(max_length=100, unique=True, null=True, blank=True, verbose_name=u"交易號")
    pay_status = models.CharField(choices=ORDER_STATUS, default="paying", max_length=30, 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="支付時間")

    # 用戶信息
    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="聯繫電話")

    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加時間")

    class Meta:
        verbose_name = u"訂單"
        verbose_name_plural = verbose_name

    def __str__(self):
        return str(self.order_sn)


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="商品數量")

    add_time = models.DateTimeField(default=datetime.now, verbose_name="添加時間")

    class Meta:
        verbose_name = "訂單商品"
        verbose_name_plural = verbose_name

    def __str__(self):
        return str(self.order.order_sn)
trade.models.py

四、用戶操做models.py設計

from datetime import datetime

from django.db import models
from django.contrib.auth import get_user_model

from goods.models import Goods
# Create your models here.
User = get_user_model()


class UserFav(models.Model):
    """
    用戶收藏
    """
    user = models.ForeignKey(User, verbose_name="用戶")
    goods = models.ForeignKey(Goods, verbose_name="商品", help_text="商品id")
    add_time = models.DateTimeField(default=datetime.now, verbose_name=u"添加時間")

    class Meta:
        verbose_name = '用戶收藏'
        verbose_name_plural = verbose_name
        unique_together = ("user", "goods")

    def __str__(self):
        return self.user.username


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=u"留言類型: 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="添加時間")

    class Meta:
        verbose_name = "用戶留言"
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.subject


class UserAddress(models.Model):
    """
    用戶收貨地址
    """
    user = models.ForeignKey(User, verbose_name="用戶" )
    province = models.CharField(max_length=100, default="", verbose_name="省份")
    city = models.CharField(max_length=100, default="", 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="添加時間")

    class Meta:
        verbose_name = "收貨地址"
        verbose_name_plural = verbose_name

    def __str__(self):
        return self.address
user_operation.models.py

4、數據表遷移

一、數據表遷移makemigrations與migrate

  將Django模型類中的數據庫遷移生成數據表,是大大簡化咱們對數據庫的操做,節約大量時間,這樣開發效率大大提高,當使用makemigrations的時候,所有應用app下面會出現一個文件001-初始化文件,同時,在數據庫中的django-migration表中會有相應app的記錄,所以若是遷移表數據庫會出現對應app的兩條記錄,所以瞭解原理,之後遷移數據的時候,能夠刪除初始化文件001,或者刪除數據庫,第二次必須使用migrate纔會講對應的模型類轉化爲數據表,

 

下面這個錯誤是在Django2.0之後,在外鍵關係和一對一關係的時候,必須加上參數on_delete的值。

 

 

 

5、Xadmin後臺管理系統的配置

  由於作項目就是爲了磨鍊不一樣的技術,重複性的工做就不用再作,前面項目都作過先後端不分離項目,慕學在線網項目,所以利用Xadmin打造後臺管理系統直接能夠將配置好的複製進來,若是想要直接這個項目就作的話,那麼能夠本身去github上學習Xadmin的相關配置以及操做。

  將配置好的Xadmin插件複製到extra_apps,而後將每一個應用下面的adminx.py文件複製到特定的應用下面,adminx的做用也是將模型類註冊到後臺管理系統中操做。

完成以上操做那麼繼續下面的操做

一、項目設置中配置xadmin

# Application definition   註冊xadmin

INSTALLED_APPS = [
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'users.apps.UsersConfig',
    'goods',
    'trade',
    'user_operation',
    'DjangoUeditor',
    'xadmin',
    'crispy_forms',#這個是xadmin須要使用的
]

二、安裝xadmin的依賴包

  去github上搜索xadmin,而後找到依賴包。

 

 

 

 

 

   在虛擬環境中,安裝全部的依賴包。

pip3 install django-crispy-forms django-import-export django-reversion django-formtools future httplib2 six

 

 在安裝兩個包,是幫助咱們作excel文件的:

pip3 install xlwt xlsxwriter

 

 安裝完成後,須要遷移Xadmin的數據表

而後會發現,因爲Xadmin跟不上Django的版本節奏,所以將Xadmin中的源碼改動,下面這個博客錯誤記錄很全:

https://www.cnblogs.com/xingfuggz/p/10142388.html

完成以後,運行去數據庫庫查看一下,添加完成。接下來須要給xadmin註冊訪問路徑。

 三、註冊Xadmin路由(Mxshop/ulrs.py)

from django.urls import path
import xadmin
urlpatterns = [
    path('xadmin/', xadmin.site.urls),
]

註冊完xadmin以後,咱們應該建立咱們的超級管理員,去檢驗咱們的xadmin是否生效。

四、建立超級管理員

python manage.py createsuperuser

 

 建立以後來到項目設置裏面(settings.py)將時區換爲亞洲上海的。

 

 設置好後啓動,能夠運行,記住xadmin必須和Django匹配,不然會出現版本不相容的問題,github上有不少人對Xadmin進行修改,適合用於Django2.0之後的版本,

 

 

 

 而後再將這個註冊到設置裏面啓動訪問,而後發現成功

 

 

 

 進去所有都點一下,試試會不會出錯,而後發現報錯

 

 

直接點進去,根據報錯信息,說render函數獲得一個錯誤的參數,將93行註釋掉,這樣就能夠啓動啦

相關文章
相關標籤/搜索