此文為本人原創,最早發布于flask開發的第五章關于創建遷移腳本的問題(已解決) - cocode.cc。內容并不完善,持續更新,可隨意轉載。轉載請標明出處。
分享一點經驗,主要是自己的理解,希望能有所幫助。千辛萬苦部署好的數據庫,就不為了答題一一驗證了,全憑記憶回答,有不對的地方歡迎指出,會及時修改。
以下內容以執行文件名為manage.py
舉例,請自行調整。
-
影響
migrate
的是數據庫的結構。- 比方說你的
User
類中添加了一個 Column -nickname
,那么在保存 Model 之后建議執行python manage.py db migrate -m "add nickname
; - 而給 table 加入了新的方法,例如
def change_nick_name()
,是不需要migrate
的。如果migrate
,結果也是No change
; - 這一點可以留意一下,比較保險的辦法是覺得有必要的時候就嘗試一下
migrate
,反正No changes
對你的遷移也沒有影響。
- 比方說你的
-
在創建本地數據庫的時候,不要在
py shell
環境下執行db.create_all()
- 請使用
python manage.py db init
,python manage.py db upgrade
來創建本地數據庫。 - 通常我會模仿書本上在上面兩條指令之間再做一次
migrate
,但經驗告訴我,結果好像都是No changes
,畢竟,我init
之后沒有做過調整啊。 -
init
指令會根據Model.py
中的結構創建遷移文件夾migrations
,而upgrade
會根據migrations
下的內容,通過config.py
在找到正確的位置,并創建SQL,并在SQL中創建一個名為versions
的table來存放和遷移文件夾中相同的版本號。(重要) - 在開始的嘗試中,特別是往heroku上部署的過程中,經常會遇到許多數據庫的坑,如果實在走投無路,又確定是數據庫遷移問題,并且無法優雅地解決。你需要做的就是以下幾步:
(1). 休息一下,我知道你很累了
(2). 執行python manage.py db shell
,在py shell
環境下執行drop_all()
;或者直接刪了你的原有數據庫。
(3). 按照本段前面的提示重新創建本地SQL
(4).drop_all()
或者刪除并重新指定遠端數據庫
(5). 執行heroku run python manage.py db deploy
(假設你部署在heroku上,并已經完成了deploy的定義)
(6). 現在你的遠端和本地數據庫的版本是相同的了。
- 請使用
-
如果本地使用sqlite作為數據庫,千萬不要從
model.py
中刪除column
!- 這一點非常重要,因為根據我查到到資料顯示,sqlite是沒有“刪除行”這一個選項的。如果你刪除了某個
column
,這一操作能被migrate
正確記錄,但是在你upgrade
的時候就會報錯。然后想要還原migrate版本?抱歉,我不會……(歡迎朋友們指導一下,謝謝!)
- 這一點非常重要,因為根據我查到到資料顯示,sqlite是沒有“刪除行”這一個選項的。如果你刪除了某個
-
部署到遠端時,請確認你又
versions
文件夾- 我不確定
init
會不會有,在執行migrate
指令時,會更新versions
文件夾 - 如果沒有
versions
文件夾,遠端部署的時候也會報錯,請務必留意。
- 我不確定
-
理解每個遷移指令的含義
-
init
的作用是初始化遷移,創建migration
文件夾 -
migrate
的作用是根據model.py中的變化更新遷移,該指令會在migration/versions/
文件夾中新增一個版本文件,文件名為版本號。打開能夠看到對應model.py文件,修改前后新遷移版本發生的變化。 -
update
會將遷移中最新版本的結構應用到數據庫中(例如添加新增的列),并更新自動創建的version
表中的版本號。該版本號與migration/versions/
文件夾中對應。任何情況下,這兩個版本號不對應都會導致出錯。
-
我的帖子與回答都會持續更新。如果您覺得有幫助,煩請點個贊,這樣或許能幫到其它朋友。
如果我有誤導他人的地方,請與我聯系,我會及時修改。謝謝!
如果有需要的朋友,可以看看我的website,希望對大家有所幫助。
關于網頁中已有的功能都可以和我交流,歡迎查找bug,交流心得。謝謝!
(網站處于測試階段,請勿保存重要信息,數據丟失概不負責,還請見諒。)
辭職學習中,有工作機會歡迎與我聯系,謝謝!