Monday 13 June 2011

Rack on Rails and Custom webserver



Rails on Rack

What would be interesting
  • Where does  Rack fit in web framework
  • How to install
  • Build our own framework
  • Use our middle ware in Rails.
Rack is an interface for Ruby webserver. It provides a minimal interface between webservers supporting Ruby and Ruby frameworks.


Rack provides an interface between different web servers and your application, Making it very simple for your application to be compatible with any web server that supports Rack - Passenger, Litespeed, Mongrel, Thin, Ebb, Webrick etc ...

It is also possible to use multiple frameworks in a single application. Rails and Sinatra integration is a good example.

Think of Middle ware as a Rails before_filter/after_filter that are reusable across different rack supported frameworks. Ex: We can use the same 'anti_spamming' middle ware for our Rails app, Sinatra app etc ..

Rack handlers

Rack in our web frame work



Installation
  • gem install rack
  • Require 'rack' for further usage
  • "rake middle ware" gives you the list of classes/modules usable as middle ware in our application
Rack specification

A Rack application is a Ruby object(not a class) that responds to call. It takes exactly one argument, the environment, and returns an Array of exactly three values: The status, the headers and the body.

 class HelloWorld

     def call(env)
         [200, {"Content-Type" => "text/html" }, "Hello Rack !"]
     end

 end

sample Rack environment is pasted here

sample Rack environment


We will have another syntax to bring a Rack server up and running, Using various handlers.

require 'rubygems'
require 'rack'

Rack::Handler::WEBrick.run proc{|env| [200, {"Content-Type" => "text/html"}, "Hello Rack"]}, :Port => 9292
...
...
INFO  WEBrick::HTTPServer#start: pid=4557 port=19292

Now the server is running on 19292 port and 'http://localhost:19292/' gives "Hello Rack"

Some of the other Rack handlers are listed below,
  • Rack::Handler::CGI
  • Rack::Handler::EventedMongrel
  • Rack::Handler::FastCGI
  • Rack::Handler::LSWS
  • Rack::Handler::Mongrel
  • Rack::Handler::SCGI
  • Rack::Handler::WEBrick
  • Rack::Handler::Thin

Custom middle ware for Rails

Use an existing rails application or create a new one.
$ rackup   #will bring up the rack server. This depends on the values in config.ru file in RAILS_ROOT.

# config.ru
rub Proc.new {|env|  [200, {"Content-Type" => ""text/html"},  "Hello Rack!"]}

#environment.rb
config.middleware.use(new_middleware, args) # adds a new middle ware at the end of middle ware stack.


Example :
 Adding a middle ware to an existing Rails application. This filter redirects page to 'google' if the requested resource is not present with in rails app.

my_rack_middle_ware.rb
require 'rubygems'
require 'rack'

class MyRackMiddleWare
    def initialize(app)
        @app = app
    end

    def call(env)
        #executes the request using Rails app
        status, headers, body = @app.call(env)
        if status == 404
            [301, {"Location" => 'http://www.google.com'}, 'redirecting to google as the requested resource is not available']
        else
            [status, headers, body]
        end
    end   
end
Add middle ware details in the 'environment.rb'
  config.middleware.use(MyRackMiddleWare) # Make sure to require the file.

 Run the application and try for an invalid page in the URL, the page should get redirected to google.











1 comment: