Deferred requests with merb, ebb and thin
Posted by ezmobius Fri, 18 Apr 2008 06:20:00 GMT
There is a classic tradeoff between threaded servers and event driven servers. Event driven servers tend to be much faster than threaded servers when all the requests are fairly fast. But the event model falls down if you have long requests like file uploads or reporting actions. This is because the long action blocks the event loop, effectively keeping other requests from running.
There are two new event driven ruby webservers at your disposal these days, Thin and Ebb. Both of these servers support the Rack web server interface that merb uses. Until now both of these servers were not the best choice for file uploads or long blocking actions but that’s all changing.
Both ebb and thin have added a deferred?(env) method to their rack adapter interface. Both webservers will call this method on your Rack @app object before they call your call(env) method. This allows your rack adapter to determine if the request should be run in its own thread if it’s slow.
I’ve just committed support for this deferred_actions construct in merb-core. If you want to run on thin or ebb but you have say a file upload action and some slow reporting actions you could add this to your init.rb in your app:
Merb::Config[:deferred_actions] = ["/uploads/create", "/reports/longaction"]
What this means is that all of your actions will run in fast event driven mode except for requests to /uploads/create and /reports/longaction. Any request for either of these urls will be served from a newly spawned thread, all other requests will be served by the main event loop.
This allows us to have the best of both world. Combining threaded and event driven styles to use the strengths of both makes a lot of sense here.
Cheers to the authors of ebb and thin for making the same interface. All of this requires the HEAD versions of ebb or thin so if you want to play along at home you will need to build thin or ebb from source on github: ebb and thin