標籤:
原文:http://stackoverflow.com/questions/4113299/ruby-on-rails-server-options
Apache vs Nginx他們都是web伺服器,都能伺服靜態檔案。Apache更加流行,擁有更多的功能;Nginx則相對功能少、小巧、快速。Apache 和 Nginx都能在盒子外(out-of-the-box)伺服Ruby伺服器,為此你需要使用另外的外掛程式來組合他們。Apache 和 Nginx都能作為反向 Proxy,就是說他們能夠把進來的HTTP請求轉寄給其他伺服器,接著把該伺服器的響應轉給用戶端。
Mongrel以及其他production模式的伺服器vs WEBrickMongrel是ruby實現的應用伺服器,具體來說:1,在自己的進程空間中載入Ruby app.2, 建立一個TCP socket,允許它可以和外部世界(例如Internet)通訊。Mongrel在這個socket上監聽HTTP請求,並把請求資料轉寄給Ruby app。3,Ruby app返回一個描述HTTP響應的對象,Mongrel將其轉換為真正的HTTP響應位元組,並發回到socket中。 然後Mongrel已經不再維護了,其他替代伺服器是:
- Phusion Passenger
- Unicorn
- Thin
- Puma
- Trinidad (JRuby only)
- TorqueBox (JRuby only)
接下來我會講一講他們和Mongrel的區別 WEBrick和Mongrel很像,區別如下:
- webrick不適合用於production模式。WEBrick完全是用ruby寫的,Mongrel以及其他ruby app 伺服器,部分ruby部分C,主要是ruby,但它的HTTP 解析器為了效能是用C寫的
- WEBrick比較慢且不夠強壯,有普遍知道的記憶體流失問題,以及HTTP解析問題。
- 因為WEBrick是ruby預設內建的,所以WEBrick經常用於development模式下作為預設伺服器,而其他伺服器則需要另外安裝。不建議在production模式下是用WEBrick伺服器,雖然因為某些原因,Heroku選擇了WEBrick作為預設伺服器,他們以前是使用的Thin,但我不知道他們為什麼換到了WEBrick
app伺服器世界
- 當前所有的Ruby app 伺服器都是http類型的,一些伺服器直接將80連接埠暴露到internet中,另一些則沒有
- 暴露80連接埠的:Phusion Passenger, Rainbows
- 沒有直接暴露的:Mongrel, Unicorn, Thin, Puma. 這些伺服器必須必須置於反向 Proxy伺服器之後,比如Apache and Nginx。
- 我不瞭解Trinidad and TorqueBox,,所以就忽略了
為什麼有些伺服器必須置於反向 Proxy之後呢?
- 一些伺服器的一個進程在同一時間只能處理一個請求,如果你想同時處理兩個請求,你就需要啟動多個伺服器執行個體,都伺服同一個Ruby app。這種多進程app 伺服器稱為app伺服器叢集(比如Mongrel Cluster, Thin Cluster)。你必須啟動Apache 或者 Nginx,給叢集做反向 Proxy,Apache/Nginx會處理好叢集中不同應用執行個體間的分發工作。(更多內容參見章節 "I/O並行存取模型").
- 網頁伺服器可以緩衝請求和響應。有些用戶端的發送資料、接收資料的速度緩慢,web伺服器可以隔離app server和慢用戶端。你當然不希望app server 在等待用戶端收發資料時什麼也不幹。Apache 和 Nginx 擅長同時很多事情,因為他們是多線程或者基於事件的。
- 大多數的app server可以伺服靜態檔案,但不是很擅長。Apache 和 Nginx的速度更快。
- 人們經常直接使用Apache 或者 Nginx伺服靜態檔案,而不會處理前向請求(forward requests),這是比較安全的策略。Apache 和Nginx足夠聰明,可以保護app server遠離惡意請求。
為什麼有些伺服器可以直接暴露在Internet中?
- Phusion Passenger和其他app server不一樣,其中一個比較特點是可以融入其他伺服器。
- Rainbows的作者公開指出,Rainbows可以直接暴露在internet中。他十分不會在解析HTTP過程中遭受攻擊。still, the author provides no warranty and says that usage is at own risk.
Application 伺服器對比在這一章中,我會比較我提到的大多數伺服器,但不包括Phusion Passenger。Phusion Passenger和其他的不一樣,我會單獨開出一章。我還會忽略Trinidad 和 TorqueBox,因為我對他們不是很瞭解。只有你用到JRuby的時候才會涉及到他們。
- Mongrel是塊暴露的石頭。像之前提到的,Mongrel僅僅是單線程、多進程,所以它只用於叢集(cluster)中。沒有進程監控,意味著如果叢集中一個進程崩潰了,則需要手動重啟。人們需要使用額外的進程來照看Mongrel,比如Monit 和 God。
- Unicorn是從Mongrel中fork出來的。支援監控一定數量的的進程:如果一個進程崩潰了,則會被主進程自動重啟。它能讓所有進程都監聽同一個共用的socket,而不是每個進程獨自使用單獨的socket。這會簡化反向 Proxy的配置。像Mongrel一樣,也是單線程、多進程。
- Thin利用EventMachine庫,實現基於事件的 I/O model。它並不是使用Mongrel的HTTP解析器,沒有基於Mongrel。它的叢集節點沒有進程監控,所以你需要去監控進程是否崩潰。每個進程監聽獨自的socket,不像Unicorn一樣共用socket。理論上來說,Thin的I/O模式允許高並發,這也是Thin被應用的大部分場合。一個Thin的進程只能處理一個並發請求,所以你還需要叢集。關於這個古怪的性質,更多內容參見“I/O並行存取模型”。
- Puma也是從Mongrel中fork出來的,但和Unicorn不一樣的是,Puma被設計成多進程的。目前不支援叢集。你需要特別確認的是你能實現多核(You need to take special care to ensure that you can utilize multiple cores)。更多內容參見“I/O並行存取模型”。
- Rainbows通過給不同的庫實現多種並行存取模型。
I/O並行存取模型
- 單線程,多進程。Ruby app Server中比較常見、流行的I/O模型,主要是因為Ruby生態系統多線程支援比較差。一個進程同時僅且只能同時處理一個請求,網頁伺服器通過多進程來進行均衡負載。這種模型比較穩定,開發人員不會輕易造成並發bug。這種模型適合執行快速的短請求,不適合速度慢、長請求阻塞I/O的運算,例如 調用HTTP API。
- 純多線程。現在Ruby生態系統已經很支援多線程了,所以這種I/O模型變得切實可行。多線程支援高I/O並發,既適合短請求也適合長請求。開發人員也很容易造成並發bug,幸運的是大多數架構按照這種方式設計,所以也不太可能發生。有一個需要注意的事情是,因為使用了全域解譯器鎖(GIL),MRI Ruby 解譯器不能均衡使用多個CPU核心,即使有多個線程。為此,你可以使用多個進程,每個進程使用一個CPU核心。JRuby 和 Rubinius沒有GIL,所以他們的一個進程可以均衡負載多個CPU核心 。
- 結合多線程、多進程。Phusion Passenger Enterprise 4以後版本實現了。你可以輕易在以下模式切換:單進程多線程,純多線程,多進程多線程。這種模式給出了最好的選擇方式。
- 事件。這種模式和之前提到的模式不一樣。它允許極高的I/O並發,以及非常適合長請求。為實現此功能,需要從應用到架構詳的詳細支援。然而主要的架構(Rails和Sinatra)並不支援事件模型。這也是實際上一個Thin進程同時不能處理多個請求的原因,就像單線程多進程模型一樣。只有專門的架構才充分利用事件I/O模式,例如Cramp。
[ 翻譯]ruby rails相關的常見伺服器