<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
當我們在django中新增或修改了資料庫model後,一般需要執行makemigrations、migrate把我們的model類生成相應的資料庫表,或修改對應的表結構。這是非常方便的。
但我們在實際使用中執行這兩個命令經常會出現意向不到的報錯。下面為你詳細講解這兩個命令,讓你更從容的使用他們!
makemigrations會把我們寫的model生成資料庫遷移檔案
比如我們建立一個一個Product的模型
class Product(models.Model): id = models.AutoField(primary_key=True) key = models.CharField(max_length=255) created = models.DateTimeField() suite_id = models.IntegerField(blank=True, null=True) report_version_id = models.IntegerField(null=True) class Meta: db_table = 'client'
然後執行命令python manage.py makemigrations
會生成遷移檔案(如果沒有生成遷移檔案,記得新增【apps.py】檔案並設定,再將其app名稱加入INSTALLED_APPS中)
如果我們有多個apps的檔案可以指定app名稱進行遷移檔案的生成,命令
python manage.py makemigrations [app_label]
一般我們使用這個命令就夠了!
當然還有其他命令給我們使用比如執行
python manage.py makemigrations --dry-run --verbosity 3
生成遷移檔案的程式碼
可以使用 python manage.py makemigrations --no-header
生成不帶django版本和遷移時間註釋的遷移檔案
我們可以在對應的model程式碼中加入設定項managed=False
來忽略遷移 這個時候再執行makemigrations
的時候則不會對該model進行遷移程式碼的生成!
還有一些其他命令,但都不常用,可以閱讀官方檔案瞭解
在類似於使用git做協同開發時,我們應該有一個規範就是團隊中的每一個人都應該避免修改同一個model檔案。但不可能保證每次的提交都能避免 migrations 的衝突!
這個時候我們可以使用python manage.py makemigrations --merge
進行合併來自動修復衝突,但這隻適用於簡單的model衝突合併。如果太複雜了建議閱讀django的【writing-migrations】部分進行手動修改遷移檔案
將遷移檔案集同步到資料庫中.
如果想指定某個app遷移的話可以使用
python3 manage.py migrate [app_label]
如果想指定某個migrations檔案的話可以使用
python3 manage.py migrate [app_label] [migration_name]
例如:python manage.py migrate cases 0011_auto_20220726_1440
在我們使用django-admin startproject
建立一個專案時後,如果需要使用django 的使用者管理、資料庫遷移等功能時就還需要設定好資料庫連線,然後執行migrate
資料庫會生成這些表
在表【django_migrations】中會記錄每次的mirage記錄。
有個問題是,我們的專案並沒有遷移檔案,那migrate是走哪拿到遷移檔案進行遷移的呢?
我們可以在【C:Users電腦使用者名稱AppDataLocalProgramsPythonPython39Libsite-packagesdjangocontribauthmigrations】下找到自帶的使用者模型遷移檔案。
我們還可以加引數 --database DATABASE
來指定遷移的資料庫
也可以使用--plan
顯示將要執行的遷移計劃
有些時候,我們直接對資料庫表欄位進行了修改操作,而沒有修改對應的model程式碼時,再執行makemigrations
、migrate
會報錯!
類似如下操作:
1)我們直接在資料庫表中刪除key這個欄位
2)然後在對應的model程式碼中刪除 【key】這個欄位
3)這個時候再執行makemigrations
、migrate
,會發現migrate
的時候報錯了
報錯的原因是我們先在資料庫中刪除了key
這個欄位,然後去修改的model檔案進行遷移檔案的生成和遷移。當migrate
的時候會執行刪除key
這個操作,但我們的表裡面已經沒有這個欄位了,所以會報錯!
當遇到這種情況的時候,我們可以使用migrate --fake
來進行修復。
它會將將向目標的遷移操作標記為已應用,但不實際執行 SQL 來更改資料庫結構。
另外使用migrate --fake-initial
可以對具有由CreateModel(建表操作)的遷移操作時,如果資料庫表已經存在,則允許 Django 跳過應用程式的初始遷移 。此選項適用於首次針對預先存在使用遷移的資料庫執行遷移時使用。但是,此選項不會檢查匹配表名稱之外的匹配資料庫架構,因此只有在您確信現有架構與初始遷移中記錄的架構匹配時才可以安全使用!
還有的其他命令操作不常用,需要了解可以參考官方檔案
如果有外來鍵的情況下,通過migrate
會在資料庫中建立相應的外來鍵約束。這是一個很不錯的功能。在學校老師教學時,也會要求我們建立外來鍵約束。
但在實際應用中並不是一個好的選擇,而且在《阿里Java開發規範手冊》中也明確規定:【強制】不得使用外來鍵與級聯,一切外來鍵概念必須在應用層解決
為什麼要做這樣的規定呢?我們可以舉一個例子來說明:
現在我們建立了兩個Model:【product和project】,【project】的porduct
欄位,關聯Product
class Product(models.Model): id = models.AutoField(primary_key=True) created = models.DateTimeField() product_name = models.CharField(max_length=100, null=True) class Meta: db_table = 'product' class Project(models.Model): id = models.AutoField(primary_key=True) product = models.ForeignKey(to=Product, on_delete=models.PROTECT) project_name = models.CharField(max_length=100, null=True) class Meta: db_table = 'project'
然後我們進行遷移修改資料庫表
可以看到【project】表有了一條外來鍵約束的記錄
當我們對【project】表增加一條project_id
為 1 的記錄的時候,由於【product】表不存在相應的記錄會導致報錯:
可以看出,這個約束的存在,會保證表間資料的關係的完整性。更不容易出現髒資料。這是外來鍵約束非常明顯的優點!
但也存在著不可忽略的缺點:
效能問題
我們剛建立了兩張表【project】和【product】,【project】表通過project_id
欄位與【product】表做了外來鍵約束。
這個時候,當我們每次往【project】表插入資料的時候,它會先去【product】中查詢是否有對應的關聯資料,如果通過程式來控制可以不進行這次查詢。但設立了外來鍵約束,就一定會去進行該查詢。這實際是冗餘的。當關聯的欄位少的時候可能沒啥影響,但一但關聯欄位多了後,這種影響就尤其明顯!
死鎖
在我們每次修改【project】資料時,都需要去【product】表檢查資料,需要獲取額外的鎖。如果在高並行大流量的事務場景下,外來鍵約束更容易造成死鎖!
開發/測試效率的降低
在我們日常的測試過程中,經常會遇到發現了一個BUG想復現或者方便測試的情況,會直接改資料庫表的資料來達到方便測試的效果。
雖然這及不規範,但實際情況就是能夠提升我們很多效率。這是毋庸置疑的!可是,這樣的操作也會帶來一些問題,比如因為資料導致的BUG,但實際並不是程式的BUG,或者發現不了一些潛在的BUG。
所以我的建議是:如果是業務相對複雜的話,可以在測試環境使用外來鍵約束,但上了生產環境需要去掉!如果業務相對簡單,那完全可以刪除外來鍵約束!
在django中,即便你刪除了資料庫中的外來鍵約束,只要你model程式碼裡的外來鍵關係還在,則還是可以使用它的ORM進行外來鍵操作的,沒有區別!
inspectdb
命令會檢查你的settings檔案指向的資料庫,將其資料庫表生成對應的django模型程式碼並列印出來
也可以inspectdb
指定的模型 inspectdb product
以上就是Django中Migrate和Makemigrations實操詳解的詳細內容,更多關於Django Migrate Makemigrations的資料請關注it145.com其它相關文章!
相關文章
<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
综合看Anker超能充系列的性价比很高,并且与不仅和iPhone12/苹果<em>Mac</em>Book很配,而且适合多设备充电需求的日常使用或差旅场景,不管是安卓还是Switch同样也能用得上它,希望这次分享能给准备购入充电器的小伙伴们有所
2021-06-01 09:31:42
除了L4WUDU与吴亦凡已经多次共事,成为了明面上的厂牌成员,吴亦凡还曾带领20XXCLUB全队参加2020年的一场音乐节,这也是20XXCLUB首次全员合照,王嗣尧Turbo、陈彦希Regi、<em>Mac</em> Ova Seas、林渝植等人全部出场。然而让
2021-06-01 09:31:34
目前应用IPFS的机构:1 谷歌<em>浏览器</em>支持IPFS分布式协议 2 万维网 (历史档案博物馆)数据库 3 火狐<em>浏览器</em>支持 IPFS分布式协议 4 EOS 等数字货币数据存储 5 美国国会图书馆,历史资料永久保存在 IPFS 6 加
2021-06-01 09:31:24
开拓者的车机是兼容苹果和<em>安卓</em>,虽然我不怎么用,但确实兼顾了我家人的很多需求:副驾的门板还配有解锁开关,有的时候老婆开车,下车的时候偶尔会忘记解锁,我在副驾驶可以自己开门:第二排设计很好,不仅配置了一个很大的
2021-06-01 09:30:48
不仅是<em>安卓</em>手机,苹果手机的降价力度也是前所未有了,iPhone12也“跳水价”了,发布价是6799元,如今已经跌至5308元,降价幅度超过1400元,最新定价确认了。iPhone12是苹果首款5G手机,同时也是全球首款5nm芯片的智能机,它
2021-06-01 09:30:45