近期在搞乙個簡單的專案和庫存管理系統,用flask+gunicorn邊學邊做,有一些心得如下,和大家分享。老司機們別笑;)
1. gunicorn真好用
a) flask自己的伺服器效能很差,動不動抽風,只適合拿來開發和除錯用。用gunicorn按(1 + 2 * ncpu)個worker啟動之後,在只有10+使用者量的系統裡再沒碰到效能問題,絲般順滑。
c) 使用gunicorn之後,更新程式也不用去kill process了。我現在的更新方法是自己電腦上的新版本**git push到**服務上,然後雲伺服器上git pull。記住gunicorn的daemon程序的pid,通過傳送hup訊號給gunicorn的daemon程序,它就會自動kill並boot新的worker程序。命令如下:
$ kill –sighup
d) 我的gunicorn啟動命令:
$ nohup gunicorn --workers=3 : -b host:port &
2. orm很方便
a) 儘管orm存在效能問題,不過可以通過自己定製sql語句優化。我在之前基於zabbix2.x版本資料庫做後台開發的專案中嘗試不用orm,寫了很多很多sql**。後來需求改了,重構的體驗太差了,非常地不靈活。現在老老實實先用orm做初步開發,非常的舒適。
b) 倒序查詢示例:
db.session.query.order_by(db.desc(user.id)).all()
c) 參考,目前我所有的db.relationship都用了lazy引數。遇到過乙個小問題,比如我想知道user關聯的`proeject`表中有幾個專案,我直接len(u.projects)就出錯了。因為u.projects其實還是個query類。我暫時的fix方法是len(u.projects.all())。後續應該引入sqlalchemy中的func類裡的count作更加合適的改寫。
d) merge好方便。前期開發偷懶用的sqlite,後來需要遷移資料到mysql,需要sqlalchemy做類似於「insert … on duplicate key update …」的功能(這裡還有乙個坑是把大文字寫入mysql時要把表的編碼設定成utf8mb4,utf8會報」只支援3個位元組」的異常)。
3. 修改flask-bootstrap預設採用的外國cdn源
預設flask會先找本地有沒有jquery和bootstrap的資源,沒有就載入cdn。我覺得cdn肯定比我的1m小水管快,那這cdn源的定製就是個問題了。
>>> cdns = bootstrap[『cdns』]
>>> cdns
>>> cdns['bootstrap']
>>> cdns['bootstrap'].primary
>>> cdns['bootstrap'].fallback
>>> cdns['bootstrap'].fallback.baseurl
''跟到這裡,我們如果把這個baseurl修改了,且static目錄下沒有已經存放的bootstrap的css和js資源時,網頁會載入我們修改後的cdn url。
當然我們可以直接修改flask-bootstrap的原始碼來更改cdn,不過這樣我們要把**部署到其他環境時就不能pip install -r requirements.txt就能執行了。
關鍵**如下:
from flask_bootstrap import bootstrap, webcdn# ...省略**...
bootstrap_cdn = webcdn(bootstrap_url)
# ...省略**...
4. flask-wtf的一些問題
偷懶起見,我直接採用wtf.quick_form()巨集來渲染頁面表單。但是我有乙個需求,類似於「修改資料」的頁面,表單給使用者時,輸入項帶上資料庫中原先有的資料,以避免使用者還需要再填寫一遍。一開始我用的方法是在form例項的field具體屬性上,我修改它的`default`屬性,類似這樣:
class form(flaskform):name = stringfield('what\'s your name?')
submit = submitfield('submit')
def view_func():
if requet.method == 'post':
pass
else: # request.method == 'get'
form = form()
name_old = get_name_from_db() # 從資料庫拿到了名字
form.name.default = name_old
return render_template('form.html', form=form)
然後我發現渲染出來的頁面並沒有帶上name_old。根據stack overflow上相關的問題,根據不同的wtform版本,這個方法有的管用有的不管用。
目前wtforms針對預設填入值的功能,正確的實現方法是在建立表單物件時傳入乙個data字典,把上面**改成這樣:
class form(flaskform):name = stringfield('what\'s your name?')
submit = submitfield('submit')
def view_func():
if requet.method == 'post':
pass
else: # request.method == 'get'
name_old = get_name_from_db() # 從資料庫拿到了名字
form = form(data=)
return render_template('form.html', form=form)
flask開發專案筆記
開啟cmd視窗 5.7.18mysql安裝路徑 一 安裝虛擬環境 1 安裝虛擬環境pip install virtualenv 2 建立虛擬環境virtualenv flask env 3 cd到 flask env scripts activate啟用 啟用後目錄前多了乙個 flask env 表...
Flask專案筆記 2
密碼加密時,採用的是sha256加密,但不能直接對密碼進行加密,因為密碼相同的話,其加密後的值就相同,有暴露的風險,所以在給密碼加密時還需在讀取到的密碼中加乙個鹽值 salt 即一串隨機的字串 然後在對其進行加密 property裝飾器 接收儲存完資料,需要儲存登陸狀態到session中 儲存登入狀...
Flask專案結構
專案排版 首先建立專案目錄 mkdir flask tutorial cd flask tutorial接下來按照前一篇講過的安裝flask步驟進行安裝,並新建乙個虛擬環境。flask應用可以簡單到使用乙個單檔案,例如hello.py from flask import flask defhello...