iT邦幫忙

2019 iT 邦幫忙鐵人賽

DAY 10
1
Modern Web

From Django 1.11 to Django 2.1 系列 第 10

Day10 : Models & Admin (1)

Day9 介紹了透過Shell來完成CRUD的功能,而這種將關聯式資料庫映射到物件導向(OO)

這樣子的一個抽象化技術就叫做 ORM(Object-relational mapping),這樣子說你可能還不是很了解,那麼更直白的意思就是,我們不使用資料庫的語法,e.g. SQL,便能夠達成操作資料庫的事情

至於ORM更詳細的資料,因為不在我們討論的範圍內,大家可以再去GOOGLE ^ ^

眼尖的各位如果操作的時候有發現,任何我們從資料庫取回的資料,它的名稱都不具有可讀性

>>> from vendor.models import Vendor
>>> v1 = Vendor.objects.get(id=1)
>>> v1
<Vendor: Vendor object (1)>
>>>

上述範例,我們可以得知從 Vendor 資料庫撈 id = 1的資料,但是取回來的資料名稱是<Vendor: Vendor object (1)>,這對於我們在操作及管理上,實在不太方便

若是要將回傳的資料變得具有可讀性,我們可以將它的值設定為我們所熟知或是方便辨識的內容

要達到這個目的的方法就是去覆寫 __str__ , 它會去改變資料所要顯示的值

from django.db import models

class Vendor(models.Model):
	vendor_name = models.CharField(max_length = 20) # 攤販的名稱
	store_name = models.CharField(max_length = 10) # 攤販店家的名稱
	phone_number = models.CharField(max_length = 20) # 攤販的電話號碼
	address = models.CharField(max_length = 100) # 攤販的地址

    # 覆寫 __str__
	def __str__(self):
		return self.vendor_name

class Food(models.Model):
	food_name = models.CharField(max_length = 30) # 食物名稱
	price_name = models.DecimalField(max_digits = 3, decimal_places=0) # 食物價錢
	food_vendor = models.ForeignKey(Vendor, on_delete=models.CASCADE) # 代表這食物是由哪一個攤販所做的
	
	def __str__(self):
        return self.food_name

完成上述的事情,再重新載入類別 Vendor,你便可以看到它所回傳的值,已經變成Alex,也就是它的名稱(vendor_name)了!

>>> from vendor.models import Vendor
>>> v1 = Vendor.objects.get(id=1)
>>> v1
<Vendor: Alex>
>>>

因為我們只是在 Models 覆寫 __str__,而不是修改Models的資料型態,所以所們不需要進行 makemigrations

再進一步討論這張圖片,眼尖的各位不曉得會不會產生一個疑問,它的主鍵 (PK) 跑去哪了?
https://ithelp.ithome.com.tw/upload/images/20181010/201118292667uZ8qFY.jpg

沒有錯,這一張圖片上並沒有顯示PK的欄位,因為實際上,在沒有指定PK的值之後,Django都會默默地幫你加上 PK,也就是默默加上這一段 id = models.AutoField(primary_key=True)

若是你要手動指定,方法也很簡單,就是將欄位(Field)裡面填入primary_key=True,並且如果你有指定了這一段,Django就不會自動幫補上id = models.AutoField(primary_key=True)

這時你不免想問 : 既然我的PK存在,那我的PK要怎麼顯示呢?

方法就是額外新增一個管理該類別的類別

from django.db import models
# 新增
from django.contrib import admin

class Vendor(models.Model):
	vendor_name = models.CharField(max_length = 20) # 攤販的名稱
	store_name = models.CharField(max_length = 10) # 攤販店家的名稱
	phone_number = models.CharField(max_length = 20) # 攤販的電話號碼
	address = models.CharField(max_length = 100) # 攤販的地址



	def __str__(self):
		return self.vendor_name

...中間略

# 新增
class VendorAdmin(admin.ModelAdmin):
	list_display = ('id', 'vendor_name') 

上面主要進行了兩個步驟,分別是

  1. 新增 from django.contrib import admin
  2. 新增該類別的管理者 VendorAdmin
    取名為VendorAdmin是為了增加可讀性方便未來管理,list_display 是固定寫法(很重要!),管理類別Vendor要顯示哪一些內容,後面用tuple() or list[]都可以,只要將該欲顯示的欄位填入即可!

千萬不要取list_display以外的名稱,因為這是Django制式寫法,而且 Django看不懂也不會跟你報錯,這對於未來debug而言是一個很大的坑

再新增完上面的敘述之後,還要去 admin.py 進行設定

from django.contrib import admin
# 後方新增 你所建立的 "類別名稱",這裡我的名稱是VendorAdmin
from .models import Vendor, Food, VendorAdmbin

# Register your models here.
# 將管理者類別 VendorAdmin 填至該類別後方
admin.site.register(Vendor, VendorAdmbin)
admin.site.register(Food)

完成之後,便能夠看到欄位出現 id
https://ithelp.ithome.com.tw/upload/images/20181010/20111829gjD9BZaWJu.jpg

今天大致上講到這裡,其餘的明天繼續!

祝大家雙十快樂拉 ^ ^


上一篇
Day9 : 使用 Shell 創建資料
下一篇
Day11 : Models & Admin (2)
系列文
From Django 1.11 to Django 2.1 30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

1 則留言

0
昌昌
iT邦新手 5 級 ‧ 2019-01-19 11:10:55

admin.py

import 裡面寫錯囉!!

VendorAdmbin => VendorAdmin

我要留言

立即登入留言