15.外鍵

 

外鍵

在MySQL中,表有兩種引擎,一種是InnoDB,另一種是myisam。若是使用的是InnoDB引擎,是支持外鍵約束的。外鍵的存在使得ORM框架在處理表關係的時候異常的強大。所以這裏咱們首先來介紹下外鍵在Django中的使用。javascript

類定義爲class ForeignKey(to,on_delete,**options)。第一個參數是引用的是哪一個模型,第二個參數是在使用外鍵引用的模型數據被刪除了,這個字段該如何處理,好比有CASCADESET_NULL等。這裏以一個實際案例來講明。好比有一個User和一個Article兩個模型。一個User能夠發表多篇文章,一個Article只能有一個Author,而且經過外鍵進行引用。那麼相關的示例代碼以下:html

class User(models.Model):
    username = models.CharField(max_length=20)
    password = models.CharField(max_length=100)


class Article(models.Model):
    title = models.CharField(max_length=100)
    content = models.TextField()

    author = models.ForeignKey("User",on_delete=models.CASCADE)


以上使用ForeignKey來定義模型之間的關係。即在article的實例中能夠經過author屬性來操做對應的User模型。這樣使用起來很是的方便。示例代碼以下:java

article = Article(title='abc',content='123')
author = User(username='張三',password='111111')
article.author = author
article.save()

# 修改article.author上的值
article.author.username = '李四'
article.save()


爲何使用了ForeignKey後,就能經過author訪問到對應的user對象呢。所以在底層,Django爲Article表添加了一個屬性名_id的字段(好比author的字段名稱是author_id),這個字段是一個外鍵,記錄着對應的做者的主鍵。之後經過article.author訪問的時候,其實是先經過author_id找到對應的數據,而後再提取User表中的這條數據,造成一個模型。python

若是想要引用另一個app的模型,那麼應該在傳遞to參數的時候,使用app.model_name進行指定。以上例爲例,若是User和Article不是在同一個app中,那麼在引用的時候的示例代碼以下:ios

# User模型在user這個app中
class User(models.Model):
    username = models.CharField(max_length=20)
    password = models.CharField(max_length=100)

# Article模型在article這個app中
class Article(models.Model):
    title = models.CharField(max_length=100)
    content = models.TextField()

    author = models.ForeignKey("user.User",on_delete=models.CASCADE)


若是模型的外鍵引用的是自己本身這個模型,那麼to參數能夠爲’self’,或者是這個模型的名字。在論壇開發中,通常評論均可以進行二級評論,便可以針對另一個評論進行評論,那麼在定義模型的時候就須要使用外鍵來引用自身。示例代碼以下:web

class Comment(models.Model):
    content = models.TextField()
    origin_comment = models.ForeignKey('self',on_delete=models.CASCADE,null=True)
    # 或者
    # origin_comment = models.ForeignKey('Comment',on_delete=models.CASCADE,null=True)


外鍵刪除操做:
若是一個模型使用了外鍵。那麼在對方那個模型被刪掉後,該進行什麼樣的操做。能夠經過on_delete來指定。能夠指定的類型以下:數據庫

1.CASCADE:級聯操做。若是外鍵對應的那條數據被刪除了,那麼這條數據也會被刪除。
2. PROTECT:受保護。即只要這條數據引用了外鍵的那條數據,那麼就不能刪除外鍵的那條數據。
3. SET_NULL:設置爲空。若是外鍵的那條數據被刪除了,那麼在本條數據上就將這個字段設置爲空。若是設置這個選項,前提是要指定這個字段能夠爲空。
4. SET_DEFAULT:設置默認值。若是外鍵的那條數據被刪除了,那麼本條數據上就將這個字段設置爲默認值。若是設置這個選項,前提是要指定這個字段一個默認值。
5. SET():若是外鍵的那條數據被刪除了。那麼將會獲取SET函數中的值來做爲這個外鍵的值。SET函數能夠接收一個能夠調用的對象(好比函數或者方法),若是是能夠調用的對象,那麼會將這個對象調用後的結果做爲值返回回去。
6. DO_NOTHING:不採起任何行爲。一切全看數據庫級別的約束。django

以上這些選項只是Django級別的,數據級別依舊是RESTRICT!api

模型中Meta配置:

對於一些模型級別的配置。咱們能夠在模型中定義一個類,叫作Meta。而後在這個類中添加一些類屬性來控制模型的做用。好比咱們想要在數據庫映射的時候使用本身指定的表名,而不是使用模型的名稱。那麼咱們能夠在Meta類中添加一個db_table的屬性。示例代碼以下:markdown

class Book(models.Model):
    name = models.CharField(max_length=20,null=False)
    desc = models.CharField(max_length=100,name='description',db_column="description1")

class Meta:
    db_table = 'book_model'

如下將對Meta類中的一些經常使用配置進行解釋。

db_table:

這個模型映射到數據庫中的表名。若是沒有指定這個參數,那麼在映射的時候將會使用模型名來做爲默認的表名。

ordering:

設置在提取數據的排序方式。後面章節會講到如何查找數據。好比我想在查找數據的時候根據添加的時間排序,那麼示例代碼以下:

class Book(models.Model):
name = models.CharField(max_length=20,null=False)
desc = models.CharField(max_length=100,name='description',db_column="description1")
pub_date = models.DateTimeField(auto_now_add=True)

class Meta:
db_table = 'book_model'
ordering = ['pub_date']

更多的配置後面會慢慢介紹到。
官方文檔:https://docs.djangoproject.com/en/2.0/ref/models/options/

相關文章
相關標籤/搜索