Django 有哪些局限性?
Update 2016.6.26:
這幾年對 Django 改觀不少,以下答案幾乎重寫。
封裝太多不夠通用,當提供給你東西不能滿足定製需求,改動起來比較困難。 和 ORM捆綁嚴重,如果使用 NOSQL 很多組件用不了。使用它的 ORM 一不小心就會大量用上 foreign key ,join 等性能殺手,但對於不是很 care 性能的小項目來說是超好用的。
學習成本高? Django 比起 Flask, Tornado 來說可能文檔是後者的幾倍,要花更多的時間去掌握它。但成本是否真的高,和這是否缺點不好說。Django 入門看 tutorial 那幾章就夠了,後面的眾多組件完全可以用到的時候再翻手冊。而且這些組件都是官方維護,文檔、質量和更新都有得保證,Flask 的很多插件後繼維護乏力,而且相似功能的插件多,使用的時候容易患選擇困難症。曾教一個妹子寫 web ,先從 flask 入手,看完 flask 文檔後發現光憑框架還不夠寫些像樣的東西,還得再學 flask-sqlalchemy, flask-login, wtforms, flask-admin 等組件, 分頁什麼的都還得自己手寫,妹子學的很痛苦,臨時起意改學 Django,只看自帶文檔就夠了,沒多久就上手並能按自己心意寫 web 應用了。
Django 這幾年都一直在朝好的方面變化,比如拋棄fastcgi 全面轉向 wsgi, 多資料庫支持了,User 可以定製了,migration 內置了, 個人現在越來越喜歡用 Django。已重寫本回答……
Django 最大的問題是它已經為你預想了一套需求,並準備了針對這些需求的功能。在使用的時候,你要做的不是分析需求然後在 Django 的輔助下開發,而是按照手冊的指導開啟 Django 的這些功能。也就是說,你已經擁有了一把成型的鎚子,只能用來釘它能釘的釘子。
如果你的需求不能被 Django 的設計覆蓋了,那麼你能做的是修改需求,而不是修改應用。因為 Django 已經被重度設計過,再二次修改設計成本很高。一句話總結:Django 不是框架是應用
對靜態資源的管理比 Rails Asset pipeline 差距比較大。不只是官方 staticfiles,包括第三方的 asset manager 插件嘗試下來,也都沒有 Sprockets 好用,所以最終還是建了一個空的 Rails project 專門處理 Assets,然後讓 Django 通過 manifest 文件去調用這些資源。
對 NoSQL 資料庫沒有官方支持。雖然其他框架好像也沒有官方 NoSQL 支持,但因為 Django ORM 和其他組件是深度耦合的,所以如果用一個 NoSQL ORM 替換掉 Django ORM 的話,其他組件等於不能用了。現在有 Django NonRel 的分支可以支持 MongoDB 和其他一些 NoSQL 資料庫,雖然很好用,但因為不是官方分支,為了和上游版本兼容,需要付出的很多額外的代價。django的局限(相對web.py)而言,可能是封裝的太多了。因為你可以十分鐘內用django建起一個博客(自己百度),但是,同時也意味著它為你在幕後做了很多工作而且可能並不是最優化的。而,Python的思想,我認為, 是顯示聲明,一切都應該有明確的說明,而不是靠默認操作。因此,django想要做好的話,你可能得深入的了解它,完善它。如果你已經對它的代碼有了深入了解,也許,可以讓它變得更好
瀉藥啊,這不是我擅長的,我幫你再邀請幾個人吧。
硬要說局限,恐怕最大的局限就是支持 python 的主機相對較少吧。
不過鑒於你初期要用的也就只是一個主機而已,總是找得到的,所以這也不算什麼大問題。——如果你到了用VPS或者用物理主機的地步,那這也就更不是問題了,反正想裝什麼能裝什麼。只要是適合自己的,就是最好的框架。我從django 0.96的時候開始使用一直到現在,可以說一直看著django成長起來。
django被人詬病最多的地方無非就是ORM太重,模板性能太差等等,但是我想說的是這些常被人說三道四的地方,其實django都給出了替代的方案。
ORM:如果你嫌寫Model太麻煩,只想執行raw sql,那你可以參考 https://docs.djangoproject.com/en/1.4/topics/db/sql/ ,即使只用這部分,你也可以得到很多好處,不用再關心資料庫使用的是MySQL還是PostgreSQL,方便的建立和自動關閉資料庫鏈接。如果你覺得Django的ORM太差,完全可以在這基礎之上構建屬於自己的一個django的ORM,但是請自己好好考慮sql注入的風險吧。模板性能:模板只在你返回web請求的時候才會用到,如果你喜歡,完全可以使用其他的模板系統,比如jinja。如果是想寫一個hello world類型的項目,其他輕量級的框架看起來幾行代碼就實現了。而django需要你先運行 startproject,startapp之類的一堆命令,看上去好像很麻煩。但是隨著項目的越來越大,你需要集成的東西越來越多,你會發現django可以為你節省更多的時間。想要一個簡單又有一定定製性的後台數據管理?django的admin實在太方便了。想要一個用戶註冊系統?自帶的和網上各種app也是一大堆。想自動處理時區?想有多語言網站界面?等等這些django已經都為你考慮到了。django的djangoutils目錄也是一個不錯的寶庫,很多實用的小函數和類經常可以在這裡被發現。
如果說非要有什麼局限性的話,django和js的結合性確實比rails差很多,自己部署的話也比較麻煩(但是現在已經出現像dotcloud這樣的快速部署服務)。N年前的問題,偶然看到。最近剛做完一個Django項目,有感而發一下。學識不深,恐有不對。
幾年來常用Django做開發,也看著它從1.1、1.2一直走到今天的1.11。
它開始是用於傳統的資料庫與內容驅動型的網站開發的,不同於現在流行的微服務,它們只需一個大型單體應用就可以很好的滿足需求。如一個新聞網站,其主要需求是內容瀏覽,總的來說並不複雜。此時Django一直被人詬病的性能其實並不是問題(都用Python了還把性能放第一位顯然是走錯了道),而且它可以橫向擴展,可以做DB讀寫分離,可以方便地進行緩存(美妙的是你可以控制緩存的粒度,從一個視圖函數到整個網站,或者直接使用後端無關的緩存API控制單個變數)。所以,這種新聞類內容驅動的網站用Django是個絕佳的一站式選擇。甚至大型論壇也可以毫無壓力的使用Django構建。另外,它好用的ORM可以在構建有複雜數據模型的應用時讓你很輕鬆,它與各組件合作緊密,你用SQLAlchemy達不到這種產出/成本比。
但是,如果你要以現在流行的微服務、雲原生等方式構建你的應用,Django的優勢就並不明顯了。
首先,如果你要前後端完全分離,那麼Django的模板系統可以直接丟棄,那些方便的generic view、Form之類也基本不好用了(校驗前端post過來的數據用Form方便得想哭,當然你可以繼續使用,只不過不方便向前端傳遞了,當然仍然可以傳遞html片斷)。讓前端人員把他們寫的模板上傳到你的Django工程中,渲染後再輸出是不推薦的了。
其次,按微服務構建的話,Django那些好用的short cut如login_required等就少了出場機會。你一個Java寫的程序怎麼用?一定要用Django的話,你可以只使用它的auth模塊的底層api,並自己實現用戶token的構建、解析,就是說,用Django實現一個認證服務,並利用它那些方便的後端和ORM並將認證介面暴露出去。但是,你無法簡單地在代碼中直接login一個用戶了。
再次,殺手級的admin,在微服務架構下殺傷力銳減。各個服務都有自己獨立的庫,admin沒法直接管理。當然你可以為每個服務生成一個app並生成model。但……admin用戶要怎麼登錄呢?你得修改admin應用的登錄方式……各種問題隨之而來,可能此時會更希望使用各個服務提供的介面做一個統一的管理後台,或者由各服務的維護小組進行管理。
還有,各種神奇的中間件,也無法對整個網站起作用了。
總之,對於現在流行的微服務架構方式,Django優勢降低了。不過,並不是說它不能用。你仍然可以用Django快速實現一個微服務,比如用restframwork,並享受它帶來的種種便利。還有好用的單元測試框架,它幫你初始化測試用資料庫、開啟服務、讓你操作數據,並在測試結束後刪掉這個測試資料庫——這是我最喜歡的一部分。
雖然Django訂製性很高,種種不便有時可以通過訂製backend、middleware、用些變通手段等方式解決,但那真的不經濟,還不如選擇一個更簡單的框架或語言直接做。
在一個大型應用拆分成相對簡單的微服務之後,局部複雜度、各部件耦合性明顯降低,此時,那些並不怎麼複雜但卻更好上手的框架、語言就有了更多競爭的機會。比如,node.js和Goalng。
但……微服務是唯一正確的方式嗎?
如果每次升級帶來的不向下兼容也算的話,那這個是我個人最不滿意的局限性了。性能神碼的,還是要根據應用來決定。
只能用來釘它能釘的釘子。如果你的需求不能被 Django 的設計覆蓋了,那麼你能做的是修改需求,而不是修改應用。因為 Django 已經被重度設計過,再二次修改設計成本很高。
我現在在用django,沒覺得慢多少,當然不能和PHP比,這要看你的應用如何設計,代碼寫的好不好==原因,你覺得慢可以用CACHE嘛。
auth之類的預定義數據模型,是最大的便利,也是最大的"局限"
一此Web開發中的高級功能比如:防止表單重複提交,Java的框架內置有設置Token的方法。用Django的話就得自己寫一個decorator。
數據完整性或事務一致性支持1.4以後才支持select for update,更別說對樂觀鎖的支持,而Hibernate是內置支持的。模版。硬傷啊。別的就不多說了。。auth這個模塊是我最喜歡的,無法比擬mvt 結合使用有超強的功能,可以像python一樣傳遞位置參數和額外參數。
有人對django的局限做過論述,我在此引用一下,可以看下面兩篇博文: http://www.cnblogs.com/zhengyun_ustc/archive/2006/11/19/564917.htmlhttp://cookoo.iteye.com/blog/33182
這兩篇文章, 年代實在有點久遠, 當中提到的 Django 程式碼時常修改, 在這一兩年剛好是反過來的, RoR 常有不向下相容的更新, 身邊許多朋友都長踩到地雷, 而 Django 則是很穩定。
我倒是覺得沒有什麼侷限。推薦閱讀:
※寫Python的時候,你有哪些奇技淫巧??
※如何將django項目用Nginx部署到伺服器?
※PHP 比 Python 牛在哪?
※requests 和 scrapy 在不同的爬蟲應用中,各自有什麼優勢?
※Python 寫的爬蟲爬久了就假死怎麼回事?