What have you found for these years?

2009-05-14

event-driven rails?

我發覺 rails 這種一個 process 只能處理一個 request 的方式,
實在是太容易寫出 concurrency 非常低落的程式... 又尤其用 rmagick 縮圖,
速度實在太慢太慢難以接受,改掉這部份後,又變成 exiftool 太慢,
雖然我不確定有沒有可能是 popen 的關係,這還要測測看。

但總之,太容易寫出無法使用的 web app.

那麼,有沒有可能用 epoll 之類的東西,寫出 event-driven 的 web app?
我想這應該才是正確的架構?畢竟不管是 multi-process, 還是 multi-thread,
對於 concurrency 似乎都不是理想的解決方式。抑或是,像是 erlang 那樣?
雖然我不知道這樣能不能算是 event-driven, 只是 os 層級的東西,
似乎必然會碰上資源耗竭的問題...

rails 到底是否 scale, 看起來好像很有爭議,但其實我看過很多人,
認為 rails 無法 scale 是基本到根本無須爭論的問題。
雖然我還不太敢非常肯定地說,但總覺得這搞不好確實是 java 到底快不快的問題。

總而言之,當初的架構幾乎已經全部拆掉重寫了。
這樣 rails 快速開發的意義不知道在哪?
雖然那也是因為根本從來沒上線過,那當然快速開發變得毫無意義...

而誰知道怎麼會拖得這麼漫長呢?(聳肩)

而為了把原本一個 session 要做完的事,不必要地得拆成無數個小塊。
使用者上傳 100 張圖,然後顯示 100 張「縮圖中」的圖?不太對吧?
還是應該在縮好圖之前隱藏起來?如果可以 keep 住 connection,
那不是很好嗎?雖然一樣不能跑個十分鐘,但至少跑個一分鐘應該沒問題。
但在 rails 的架構下,恐怕極限是「一秒鐘」,不然就很可能受到 DoS 攻擊。

唉我也沒辦法搞這就是了。只能就現有架構上去調整...
調整架構,真的遠遠比砍掉重練要來得困難很多很多 :(
但是搞不好調一下就能動了,這件事意外地讓人難以抗拒啊。

於是又是焦油坑,是嗎?

現在這樣就已經瘋狂複雜了... 而我已經設法簡化到我能想像的程度了。
本來是想保留 request 中縮圖的功能,現在為了簡化完全砍掉。

原本很單純一個 request, 一個 sequence 就能做完的事,變得如此複雜:

web node, upload:
1. mogilefs 存 z 圖
2. 送出 o 圖的 job 給 kestrel, 忽略 timeout 1 秒
3. 送出其他所有圖的 job 給 kestrel, 忽略 timeout, 全部共 1 秒
4. 至此最多花費 3 秒,如果全部 timeout...
5. 回應 client

web node, 改標題:
1. 重傳外連圖 job, resizer 還沒做前會先出舊圖,做好新圖會蓋過去,不管 checksum

web node, 旋轉: (還沒做)
1. 送旋轉 job 給 rotator

resizer:
1. 把 o 圖從 z 圖轉過去,第一優先,失敗的話重傳 job,
已存在的話忽略掉。 timeout 該如何?不能直接忽略,否則會有問題。
2. 轉其他圖,依序從最優先開始做。找不到 o 圖的話,重傳 o job 和現在的 job.
發生任何其他錯誤,重傳現在的 job. timeout 則忽略。

image server:
1. 找到圖的話,直接出去,有 url 對 path 的 cache
2. 找不到圖的話,從 o 圖縮圖;找不到 o 圖的話,重傳 o job.
不忽略 timeout, 因為無法 recover, 就吐 500 回去。
或是 http 有 try again 的 status?
3. 外連圖找不到縮圖的話,直接吐 500 不管,因為相依性太高,要處理太複雜

rotator: (還沒做)
1. 需存取 db
2. 讀 o 圖旋轉並寫入,產生新 checksum, re-pend cron job, save.
3. 所有非 o 圖的縮圖重傳 job. resizer 無條件寫入,就算原縮圖已存在

0 retries:

Post a Comment

All texts are licensed under CC Attribution 3.0