SlideShare a Scribd company logo
1 of 54
Download to read offline
Your best friend Rack
What is Rack?
     Rack provides a minimal interface

“     between webservers supporting
       Ruby and Ruby frameworks.

Transparently integrates in your existing
           rails, sinatra apps

 Helps you easily create a middleware
     standalone application stack
Yeah! but... what is
         Rack?
 A Rack application is a Ruby object
  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.
A basic Rack app
    diagram
Minimum server
  interface you said?
app = lambda d o |env|
  [200,
    { 'Content-Type' => 'text/html'
   'Hello World']
end
run app
Where does Rack sit?
Rack is a full
middleware stack
Allows a modular design
What is a middleware?
    Rack application that is designed

“     to run in conjunction with
    another Rack application, which
          acts as the endpoint
...
 Think of a Rack middleware as a filter
receiving the Rack environment for the
request from the previous middleware

   Does some work with or on the
      request's environment

Then calls the next middleware in the
                chain
...
      The last Rack application in the

“      chain is the application itself

     Any middleware in the chain can
return the Rack response itself, thus
preventing the rest of the middlewares
     in the chain from executing
Installation
$... $ gem install rack
Successfully installed rack-1.2.1
1 gem installed
Installing ri documentation for rack-1.2.1...
Building YARD (yri) index for rack-1.2.1...
Installing RDoc documentation for rack-1.2.1...
Let's talk more Rack
status, headers, body = object

[200,
  { 'Content-Type' => 'text/html' }
  'Hello World']
Stacking apps
m o d u l e MyModule
   c l a s s Upcase
       d e f initialize app
           @app = app
       end
    d e f call env
       p 'upcase'
       status, headers, body =
       [status, headers, [body.
    end
  end
end
...
m o d u l e MyModule
   c l a s s Reverse
       d e f initialize app
           @app = app
       end
    d e f call env
       p 'reverse'
       status, headers, body =
       [status, headers, [body.
    end
  end
end
...
use MyModule::Upcase
use MyModule::Reverse
use Rack::ContentLength
app = lambda { |env| [200, { 'Content
run app
...
$...$ rackup stacked1.ru &
[1] 2123
...$ curl localhost:9292
"upcase"
"reverse"
127.0.0.1 - - [03/Nov/2010 16:15:34] "GET / HTTP/
DLROW OLLEH
...$
What happened?
A Decorator pattern happens

    In OOP, the decorator pattern is

“      a design pattern that allows
     new/additional behaviour to be
        added to an existing object
              dynamically
Basic API
use(middleware, **args, &block) adds
      a middleware to the stack

 run(app) dispatches to an application

  map(path, &block) constructs a
 Rack::URLMap in a convenient way
Basic API - usage
       example
r e q u i r e 'rack-validate'

use Rack::Validate

map '/hello' d o
  run lambda d o |env|
    [200,
      { 'Content-Type' => 'text/html'
      'Hello World']
  end
end
Rake::Validate from
http://coderack.org/
Basic optional usage -
   Rack::Builder
Provides an optional DSL
app = Rack::Builder.new d o
  map "/hello" d o
    run lambda d o |env|
      [200,
        { 'Content-Type' => 'text/html'
        'Hello World']
    end
  end
end
Rack convenience
 Wanna develop outside of existing
 frameworks, implement your own
   ones, or develop middleware?

Rack provides many helpers to create
Rack applications quickly and without
  doing the same web stuff all over
Rack::Request
req = Rack::Request.new(env)
req.post?
req.params["data"]
Rack::Response
res = Response.new
res.write "<title>Lobstericious!</title>"
res.write "<pre>"
res.write lobster
res.write "</pre>"
res.write "<p><a href='#{href}'>flip!</a>
res.write "<p><a href='?flip=crash'>crash
res.finish
use Rack::CommonLogger
Writes a log statement to STDOUT in the Apache
      common log format for each request
         use Rack::ShowExceptions
   Renders a nice looking errors page for all
            unhandled exceptions
                use Rack::Lint
 Ensures that your Rack application conforms to
   the Rack spec. Rack::Lint will generate an
exception if the response of your application does
              not meet the Rack spec
And many more
     Rack::Auth::Basic

   Rack::Session::Cookie

       Rack::Sendfile

     http://coderack.org/

http://rack.rubyforge.org/doc/
Is this testable?
   Use your favorite framework

It provides Rack::MockRequest and
        Rack::MockResponse
With bacon

      Bacon is a small RSpec clone

“    weighing less than 350 LoC but
    nevertheless providing all essential
                 features.
MockRequest
describe Rack::Static d o
  root = File.expand_path(File.dirname(_ _ F I L E _ _
                                        _
  OPTIONS = {:urls => ["/cgi"], :root => root

  @request =
    Rack::MockRequest.new(
      Rack::Static.new(DummyApp.new, OPTIONS
  it "serves files" d o
    res = @request.get("/cgi/test")
    res.should.be.ok
    res.body.should =~ /ruby/
  end
end
MockResponse
describe Rack::Chunked d o
  before d o
    @env = Rack::MockRequest.
      env_for('/', 'HTTP_VERSION' => '1.1', 'REQUEST_METH
  end

  should 'chunk responses with no Content-Length' d o
    app = lambda { |env| [200, {}, ['Hello',
    response = Rack::MockResponse.new(
      *Rack::Chunked.new(app).call(@env))
    response.headers.should.n o t .i n c l u d e 'Content-Le
                                n     i
    response.headers['Transfer-Encoding'].should
    response.body.should.equal
        "5rnHellorn1rn rn6rnWorld!rn0rnrn"
  end
end
Why do we care?
   Supported web servers
     Mongrel, EventedMongrel,
       SwiftipliedMongrel

WEBrick, FCGI, CGI, SCGI, LiteSpeed

               Thin
These web servers include
handlers in their distributions
       Ebb, Fuzed, Glassfish v3

 Phusion Passenger (which is mod_rack
       for Apache and for nginx)

     Rainbows!, Unicorn, Zbatery
Any valid Rack app will run
the same on all these handlers,
  without changing anything
Supported web
   frameworks
Camping, Coset, Halcyon, Mack

       Maveric, Merb,
 Racktools::SimpleApplication

  Ramaze, Rum, Sinatra, Sin

       Vintage, Waves

   Wee, … and many others.
Of course Ruby on Rails
Rails has adopted the Rack philosophy
       throughout the framework

    A Rails application is actually a
     collection of Rack and Rails
 middleware components that all work
 together to form the completed whole
Listing the rails middleware
            stack
$...(master) $ rake middleware
(in /home/chischaschos/Projects/salary-manager)
use ActionDispatch::Static
use Rack::Lock
use ActiveSupport::Cache::Strategy::LocalCache
use Rack::Runtime
use Rails::Rack::Logger
use ActionDispatch::ShowExceptions
use ActionDispatch::RemoteIp
use Rack::Sendfile
use ActionDispatch::Callbacks
use ActiveRecord::ConnectionAdapters::ConnectionManagement
use ActiveRecord::QueryCache
use ActionDispatch::Cookies
use ActionDispatch::Session::CookieStore
use ActionDispatch::Flash
use ActionDispatch::ParamsParser
use Rack::MethodOverride
use ActionDispatch::Head
use ActionDispatch::BestStandardsSupport
use Warden::Manager
use Sass::Plugin::Rack
run SalaryManager::Application.routes
Things to note
 The Rack application being run with
the run directive at the end of the list of
 middlewares is the Rails application's
                 routes
Rails controllers are
   rack compliant
  A controller declaration
c l a s s HomeController < ApplicationCont
   d e f index
       render :text => "I'm your home cont
   end
end
Rails console testing (had to
    shorten the output)
$ruby-1.8.7-p302 > ...$ rails console
Loading development environment (Rails 3.0.0)
ruby-1.8.7-p302 > app = RailsRackApp::Application
ruby-1.8.7-p302 > app.class
 => ActionDispatch::Routing::RouteSet
ruby-1.8.7-p302 > env = {'REQUEST_METHOD' => 'GET
 => {"PATH_INFO"=>"/home/index", "REQUEST_METHOD"
ruby-1.8.7-p302 > status, headers, body = app.cal
 => [200, {"ETag"=>""d47cb2eec6f22cb9ff6fbb21cd3
ruby-1.8.7-p302 > body.body
 => "I'm yout home controller's body"
Rack app from a controller
       declaration
$ruby-1.8.7-p302 > app = HomeController.action :i
 => #<Proc:0xb6e26664@/home/chischaschos/.rvm/gem
ruby-1.8.7-p302 > app.respond_to? 'call'
 => true
ruby-1.8.7-p302 > status, headers, body = app.cal
=> [200, {"ETag"=>""d47cb2eec6f22cb9ff6fbb21cd34
ruby-1.8.7-p302 > body.body
 => "I'm yout home controller's body"
There are two different ways to
 install Rack components into
     your Rails application
 1 - Either configure your Rack application as part
      of your application's middleware stack

  2 - Or you can route URI paths directly to the
 Rack application from you application's routes
1.1 - Installing a component into your
               application
          lib/average_time.rb
 c l a s s AverageRuntime
    @@requests = 0
    @@total_runtime = 0.0
   d e f initialize(app)
      @app = app
   end

   d e f call(env)
      code, headers, body = @app.call(env

     @@requests += 1
     @@total_runtime += headers['X-Runtime'
     headers['X-AverageRuntime'] =
       (@@total_runtime / @@requests).to_s

     [code, headers, body]
   end
1.2 - Inserting the middleware
          config/application.rb
r e q u i r e File.expand_path('../boot', _ _ F I L E _ _
r e q u i r e 'rails/all'
Bundler.r e q u i r e (:default, Rails.env)
              r
m o d u l e RailsRackApp
   c l a s s Application < Rails::Application

     # starts the important part
     config.autoload_paths += %W(#{config
     config.middleware.insert_before Rack
       "AverageRuntime"
     # end the important part
    config.encoding = "utf-8"
    config.filter_parameters += [:password
  end
end
1.3 - Verifying middleware is in the
                stack
$...$ rake middleware
(in /home/chischaschos/Projects/rack-testing/rails-rack-app)
use ActionDispatch::Static
use Rack::Lock
use AverageRuntime
use ActiveSupport::Cache::Strategy::LocalCache
use Rack::Runtime
use Rails::Rack::Logger
use ActionDispatch::ShowExceptions
use ActionDispatch::RemoteIp
use Rack::Sendfile
use ActionDispatch::Callbacks
use ActiveRecord::ConnectionAdapters::ConnectionManagement
use ActiveRecord::QueryCache
use ActionDispatch::Cookies
use ActionDispatch::Session::CookieStore
use ActionDispatch::Flash
use ActionDispatch::ParamsParser
use Rack::MethodOverride
use ActionDispatch::Head
use ActionDispatch::BestStandardsSupport
run RailsRackApp::Application.routes
1.4 Testing our middleware
Look at X-Averageruntime: header
 $...$ curl -I localhost:3000
 HTTP/1.1 404 Not Found
 Connection: Keep-Alive
 Content-Type: text/html
 Date: Fri, 05 Nov 2010 16:04:43 GMT
 Server: WEBrick/1.3.1 (Ruby/1.8.7/2010-08-16)
 X-Runtime: 0.312526
 Content-Length: 621
 X-Averageruntime: 0.312526
2.1 - Routing to a rack application
         lib/walking_arrow.rb
c l a s s WalkingArrow
  ARROW = '=>'
  @@spaces = 0
  d e f call(env)
     @@spaces += 1
     [200, {'Content-Type' => 'text/plain'},
  end
end
2.2 - Add a route
        lib/walking_arrow.rb
r e q u i r e 'lib/walking_arrow.rb'
RailsRackApp::Application.routes.draw
   get 'home/index'
   get 'walkingarrow' => WalkingArrow.new
end
2.3 Testing our middleware
              Walk!!!
$...$ curl localhost:3000/walkingarrow
 =>
...$ curl localhost:3000/walkingarrow
  =>
...$ curl localhost:3000/walkingarrow
    =>
...$ curl localhost:3000/walkingarrow
     =>
...$ curl localhost:3000/walkingarrow
       =>
...$ curl localhost:3000/walkingarrow
        =>
Before diving into rack
  and rails creation
 Learn and play with some examples

    http://guides.rubyonrails.org
           /railsonrack.html
Do you have ideas on
   how to use it?
Most sincere thanks to
     http://rack.rubyforge.org/doc/

  http://rails-nutshell.labs.oreilly.com
                /ch07.html

http://rubylearning.com/blog/2010/09/21
   /writing-modular-web-applications-
  with-rack/?utmsource=twitterfeed&
           utmmedium=twitter

              And Mendo
References
github repo and examples

  chischaschos twitter

More Related Content

What's hot

Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...Ryan Weaver
 
Remedie: Building a desktop app with HTTP::Engine, SQLite and jQuery
Remedie: Building a desktop app with HTTP::Engine, SQLite and jQueryRemedie: Building a desktop app with HTTP::Engine, SQLite and jQuery
Remedie: Building a desktop app with HTTP::Engine, SQLite and jQueryTatsuhiko Miyagawa
 
The Evolution of Airbnb's Frontend
The Evolution of Airbnb's FrontendThe Evolution of Airbnb's Frontend
The Evolution of Airbnb's FrontendSpike Brehm
 
Introduction to Rails - presented by Arman Ortega
Introduction to Rails - presented by Arman OrtegaIntroduction to Rails - presented by Arman Ortega
Introduction to Rails - presented by Arman Ortegaarman o
 
REST APIs in Laravel 101
REST APIs in Laravel 101REST APIs in Laravel 101
REST APIs in Laravel 101Samantha Geitz
 
AnsibleFest 2014 - Role Tips and Tricks
AnsibleFest 2014 - Role Tips and TricksAnsibleFest 2014 - Role Tips and Tricks
AnsibleFest 2014 - Role Tips and Tricksjimi-c
 
Inside Bokete: Web Application with Mojolicious and others
Inside Bokete:  Web Application with Mojolicious and othersInside Bokete:  Web Application with Mojolicious and others
Inside Bokete: Web Application with Mojolicious and othersYusuke Wada
 
Single Page Web Applications with CoffeeScript, Backbone and Jasmine
Single Page Web Applications with CoffeeScript, Backbone and JasmineSingle Page Web Applications with CoffeeScript, Backbone and Jasmine
Single Page Web Applications with CoffeeScript, Backbone and JasminePaulo Ragonha
 
Fast Web Applications Development with Ruby on Rails on Oracle
Fast Web Applications Development with Ruby on Rails on OracleFast Web Applications Development with Ruby on Rails on Oracle
Fast Web Applications Development with Ruby on Rails on OracleRaimonds Simanovskis
 
Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...
Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...
Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...Alberto Perdomo
 
Building web framework with Rack
Building web framework with RackBuilding web framework with Rack
Building web framework with Racksickill
 
Laravel 5 In Depth
Laravel 5 In DepthLaravel 5 In Depth
Laravel 5 In DepthKirk Bushell
 
CodeIgniter PHP MVC Framework
CodeIgniter PHP MVC FrameworkCodeIgniter PHP MVC Framework
CodeIgniter PHP MVC FrameworkBo-Yi Wu
 
Apache Jackrabbit Oak - Scale your content repository to the cloud
Apache Jackrabbit Oak - Scale your content repository to the cloudApache Jackrabbit Oak - Scale your content repository to the cloud
Apache Jackrabbit Oak - Scale your content repository to the cloudRobert Munteanu
 
Symfony bundle fo asynchronous job processing
Symfony bundle fo asynchronous job processingSymfony bundle fo asynchronous job processing
Symfony bundle fo asynchronous job processingWojciech Ciołko
 
Cloud meets Fog & Puppet A Story of Version Controlled Infrastructure
Cloud meets Fog & Puppet A Story of Version Controlled InfrastructureCloud meets Fog & Puppet A Story of Version Controlled Infrastructure
Cloud meets Fog & Puppet A Story of Version Controlled InfrastructureHabeeb Rahman
 

What's hot (20)

Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
 
Remedie: Building a desktop app with HTTP::Engine, SQLite and jQuery
Remedie: Building a desktop app with HTTP::Engine, SQLite and jQueryRemedie: Building a desktop app with HTTP::Engine, SQLite and jQuery
Remedie: Building a desktop app with HTTP::Engine, SQLite and jQuery
 
The Evolution of Airbnb's Frontend
The Evolution of Airbnb's FrontendThe Evolution of Airbnb's Frontend
The Evolution of Airbnb's Frontend
 
Introduction to Rails - presented by Arman Ortega
Introduction to Rails - presented by Arman OrtegaIntroduction to Rails - presented by Arman Ortega
Introduction to Rails - presented by Arman Ortega
 
REST APIs in Laravel 101
REST APIs in Laravel 101REST APIs in Laravel 101
REST APIs in Laravel 101
 
AnsibleFest 2014 - Role Tips and Tricks
AnsibleFest 2014 - Role Tips and TricksAnsibleFest 2014 - Role Tips and Tricks
AnsibleFest 2014 - Role Tips and Tricks
 
Tatsumaki
TatsumakiTatsumaki
Tatsumaki
 
Inside Bokete: Web Application with Mojolicious and others
Inside Bokete:  Web Application with Mojolicious and othersInside Bokete:  Web Application with Mojolicious and others
Inside Bokete: Web Application with Mojolicious and others
 
Single Page Web Applications with CoffeeScript, Backbone and Jasmine
Single Page Web Applications with CoffeeScript, Backbone and JasmineSingle Page Web Applications with CoffeeScript, Backbone and Jasmine
Single Page Web Applications with CoffeeScript, Backbone and Jasmine
 
Fast Web Applications Development with Ruby on Rails on Oracle
Fast Web Applications Development with Ruby on Rails on OracleFast Web Applications Development with Ruby on Rails on Oracle
Fast Web Applications Development with Ruby on Rails on Oracle
 
Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...
Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...
Strangers In The Night: Ruby, Rack y Sinatra - Herramientas potentes para con...
 
Getting Started With Aura
Getting Started With AuraGetting Started With Aura
Getting Started With Aura
 
Building web framework with Rack
Building web framework with RackBuilding web framework with Rack
Building web framework with Rack
 
Laravel 5 In Depth
Laravel 5 In DepthLaravel 5 In Depth
Laravel 5 In Depth
 
CodeIgniter PHP MVC Framework
CodeIgniter PHP MVC FrameworkCodeIgniter PHP MVC Framework
CodeIgniter PHP MVC Framework
 
Apache Jackrabbit Oak - Scale your content repository to the cloud
Apache Jackrabbit Oak - Scale your content repository to the cloudApache Jackrabbit Oak - Scale your content repository to the cloud
Apache Jackrabbit Oak - Scale your content repository to the cloud
 
Symfony bundle fo asynchronous job processing
Symfony bundle fo asynchronous job processingSymfony bundle fo asynchronous job processing
Symfony bundle fo asynchronous job processing
 
Cloud meets Fog & Puppet A Story of Version Controlled Infrastructure
Cloud meets Fog & Puppet A Story of Version Controlled InfrastructureCloud meets Fog & Puppet A Story of Version Controlled Infrastructure
Cloud meets Fog & Puppet A Story of Version Controlled Infrastructure
 
Express JS
Express JSExpress JS
Express JS
 
Catalyst MVC
Catalyst MVCCatalyst MVC
Catalyst MVC
 

Similar to What is Rack? A concise overview of the Ruby web server interface

Using and scaling Rack and Rack-based middleware
Using and scaling Rack and Rack-based middlewareUsing and scaling Rack and Rack-based middleware
Using and scaling Rack and Rack-based middlewareAlona Mekhovova
 
Phoenix for Rails Devs
Phoenix for Rails DevsPhoenix for Rails Devs
Phoenix for Rails DevsDiacode
 
How and why i roll my own node.js framework
How and why i roll my own node.js frameworkHow and why i roll my own node.js framework
How and why i roll my own node.js frameworkBen Lin
 
Crossing the Bridge: Connecting Rails and your Front-end Framework
Crossing the Bridge: Connecting Rails and your Front-end FrameworkCrossing the Bridge: Connecting Rails and your Front-end Framework
Crossing the Bridge: Connecting Rails and your Front-end FrameworkDaniel Spector
 
Ruby On Rails
Ruby On RailsRuby On Rails
Ruby On Railsanides
 
Rails in the bowels
Rails in the bowelsRails in the bowels
Rails in the bowelsCreditas
 
TorqueBox - Ruby Hoedown 2011
TorqueBox - Ruby Hoedown 2011TorqueBox - Ruby Hoedown 2011
TorqueBox - Ruby Hoedown 2011Lance Ball
 
Rails Engine | Modular application
Rails Engine | Modular applicationRails Engine | Modular application
Rails Engine | Modular applicationmirrec
 
Clojure and the Web
Clojure and the WebClojure and the Web
Clojure and the Webnickmbailey
 
Creating a modern web application using Symfony API Platform, ReactJS and Red...
Creating a modern web application using Symfony API Platform, ReactJS and Red...Creating a modern web application using Symfony API Platform, ReactJS and Red...
Creating a modern web application using Symfony API Platform, ReactJS and Red...Jesus Manuel Olivas
 
Ruby on Rails - Introduction
Ruby on Rails - IntroductionRuby on Rails - Introduction
Ruby on Rails - IntroductionVagmi Mudumbai
 
Rails web api 开发
Rails web api 开发Rails web api 开发
Rails web api 开发shaokun
 

Similar to What is Rack? A concise overview of the Ruby web server interface (20)

Rack
RackRack
Rack
 
Rack
RackRack
Rack
 
Rack
RackRack
Rack
 
Using and scaling Rack and Rack-based middleware
Using and scaling Rack and Rack-based middlewareUsing and scaling Rack and Rack-based middleware
Using and scaling Rack and Rack-based middleware
 
Dev streams2
Dev streams2Dev streams2
Dev streams2
 
Phoenix for Rails Devs
Phoenix for Rails DevsPhoenix for Rails Devs
Phoenix for Rails Devs
 
RoR guide_p1
RoR guide_p1RoR guide_p1
RoR guide_p1
 
How and why i roll my own node.js framework
How and why i roll my own node.js frameworkHow and why i roll my own node.js framework
How and why i roll my own node.js framework
 
Crossing the Bridge: Connecting Rails and your Front-end Framework
Crossing the Bridge: Connecting Rails and your Front-end FrameworkCrossing the Bridge: Connecting Rails and your Front-end Framework
Crossing the Bridge: Connecting Rails and your Front-end Framework
 
Ruby On Rails
Ruby On RailsRuby On Rails
Ruby On Rails
 
Rails in the bowels
Rails in the bowelsRails in the bowels
Rails in the bowels
 
TorqueBox - Ruby Hoedown 2011
TorqueBox - Ruby Hoedown 2011TorqueBox - Ruby Hoedown 2011
TorqueBox - Ruby Hoedown 2011
 
Rails Engine | Modular application
Rails Engine | Modular applicationRails Engine | Modular application
Rails Engine | Modular application
 
Clojure and the Web
Clojure and the WebClojure and the Web
Clojure and the Web
 
Creating a modern web application using Symfony API Platform, ReactJS and Red...
Creating a modern web application using Symfony API Platform, ReactJS and Red...Creating a modern web application using Symfony API Platform, ReactJS and Red...
Creating a modern web application using Symfony API Platform, ReactJS and Red...
 
Rack
RackRack
Rack
 
Ruby on Rails - Introduction
Ruby on Rails - IntroductionRuby on Rails - Introduction
Ruby on Rails - Introduction
 
Rails web api 开发
Rails web api 开发Rails web api 开发
Rails web api 开发
 
Arquitecturas de microservicios - Medianet Software
Arquitecturas de microservicios   -  Medianet SoftwareArquitecturas de microservicios   -  Medianet Software
Arquitecturas de microservicios - Medianet Software
 
rails.html
rails.htmlrails.html
rails.html
 

Recently uploaded

Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...apidays
 
Presentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreterPresentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreternaman860154
 
What Are The Drone Anti-jamming Systems Technology?
What Are The Drone Anti-jamming Systems Technology?What Are The Drone Anti-jamming Systems Technology?
What Are The Drone Anti-jamming Systems Technology?Antenna Manufacturer Coco
 
[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdfhans926745
 
Real Time Object Detection Using Open CV
Real Time Object Detection Using Open CVReal Time Object Detection Using Open CV
Real Time Object Detection Using Open CVKhem
 
IAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsIAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsEnterprise Knowledge
 
Advantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessAdvantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessPixlogix Infotech
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc
 
Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)wesley chun
 
How to convert PDF to text with Nanonets
How to convert PDF to text with NanonetsHow to convert PDF to text with Nanonets
How to convert PDF to text with Nanonetsnaman860154
 
GenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day PresentationGenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day PresentationMichael W. Hawkins
 
Automating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps ScriptAutomating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps Scriptwesley chun
 
Slack Application Development 101 Slides
Slack Application Development 101 SlidesSlack Application Development 101 Slides
Slack Application Development 101 Slidespraypatel2
 
08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking Men08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking MenDelhi Call girls
 
A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)Gabriella Davis
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountPuma Security, LLC
 
08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking Men08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking MenDelhi Call girls
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processorsdebabhi2
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptxHampshireHUG
 
Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024The Digital Insurer
 

Recently uploaded (20)

Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 
Presentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreterPresentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreter
 
What Are The Drone Anti-jamming Systems Technology?
What Are The Drone Anti-jamming Systems Technology?What Are The Drone Anti-jamming Systems Technology?
What Are The Drone Anti-jamming Systems Technology?
 
[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf[2024]Digital Global Overview Report 2024 Meltwater.pdf
[2024]Digital Global Overview Report 2024 Meltwater.pdf
 
Real Time Object Detection Using Open CV
Real Time Object Detection Using Open CVReal Time Object Detection Using Open CV
Real Time Object Detection Using Open CV
 
IAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI SolutionsIAC 2024 - IA Fast Track to Search Focused AI Solutions
IAC 2024 - IA Fast Track to Search Focused AI Solutions
 
Advantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessAdvantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your Business
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
 
Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)
 
How to convert PDF to text with Nanonets
How to convert PDF to text with NanonetsHow to convert PDF to text with Nanonets
How to convert PDF to text with Nanonets
 
GenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day PresentationGenCyber Cyber Security Day Presentation
GenCyber Cyber Security Day Presentation
 
Automating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps ScriptAutomating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps Script
 
Slack Application Development 101 Slides
Slack Application Development 101 SlidesSlack Application Development 101 Slides
Slack Application Development 101 Slides
 
08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking Men08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking Men
 
A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path Mount
 
08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking Men08448380779 Call Girls In Civil Lines Women Seeking Men
08448380779 Call Girls In Civil Lines Women Seeking Men
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processors
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
 
Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024
 

What is Rack? A concise overview of the Ruby web server interface

  • 2. What is Rack? Rack provides a minimal interface “ between webservers supporting Ruby and Ruby frameworks. Transparently integrates in your existing rails, sinatra apps Helps you easily create a middleware standalone application stack
  • 3. Yeah! but... what is Rack? A Rack application is a Ruby object 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.
  • 4. A basic Rack app diagram
  • 5. Minimum server interface you said? app = lambda d o |env| [200, { 'Content-Type' => 'text/html' 'Hello World'] end run app
  • 7. Rack is a full middleware stack
  • 9. What is a middleware? Rack application that is designed “ to run in conjunction with another Rack application, which acts as the endpoint
  • 10. ... Think of a Rack middleware as a filter receiving the Rack environment for the request from the previous middleware Does some work with or on the request's environment Then calls the next middleware in the chain
  • 11. ... The last Rack application in the “ chain is the application itself Any middleware in the chain can return the Rack response itself, thus preventing the rest of the middlewares in the chain from executing
  • 12. Installation $... $ gem install rack Successfully installed rack-1.2.1 1 gem installed Installing ri documentation for rack-1.2.1... Building YARD (yri) index for rack-1.2.1... Installing RDoc documentation for rack-1.2.1...
  • 13. Let's talk more Rack status, headers, body = object [200, { 'Content-Type' => 'text/html' } 'Hello World']
  • 14. Stacking apps m o d u l e MyModule c l a s s Upcase d e f initialize app @app = app end d e f call env p 'upcase' status, headers, body = [status, headers, [body. end end end
  • 15. ... m o d u l e MyModule c l a s s Reverse d e f initialize app @app = app end d e f call env p 'reverse' status, headers, body = [status, headers, [body. end end end
  • 16. ... use MyModule::Upcase use MyModule::Reverse use Rack::ContentLength app = lambda { |env| [200, { 'Content run app
  • 17. ... $...$ rackup stacked1.ru & [1] 2123 ...$ curl localhost:9292 "upcase" "reverse" 127.0.0.1 - - [03/Nov/2010 16:15:34] "GET / HTTP/ DLROW OLLEH ...$
  • 18. What happened? A Decorator pattern happens In OOP, the decorator pattern is “ a design pattern that allows new/additional behaviour to be added to an existing object dynamically
  • 19.
  • 20. Basic API use(middleware, **args, &block) adds a middleware to the stack run(app) dispatches to an application map(path, &block) constructs a Rack::URLMap in a convenient way
  • 21. Basic API - usage example r e q u i r e 'rack-validate' use Rack::Validate map '/hello' d o run lambda d o |env| [200, { 'Content-Type' => 'text/html' 'Hello World'] end end
  • 23. Basic optional usage - Rack::Builder Provides an optional DSL app = Rack::Builder.new d o map "/hello" d o run lambda d o |env| [200, { 'Content-Type' => 'text/html' 'Hello World'] end end end
  • 24. Rack convenience Wanna develop outside of existing frameworks, implement your own ones, or develop middleware? Rack provides many helpers to create Rack applications quickly and without doing the same web stuff all over
  • 26. Rack::Response res = Response.new res.write "<title>Lobstericious!</title>" res.write "<pre>" res.write lobster res.write "</pre>" res.write "<p><a href='#{href}'>flip!</a> res.write "<p><a href='?flip=crash'>crash res.finish
  • 27. use Rack::CommonLogger Writes a log statement to STDOUT in the Apache common log format for each request use Rack::ShowExceptions Renders a nice looking errors page for all unhandled exceptions use Rack::Lint Ensures that your Rack application conforms to the Rack spec. Rack::Lint will generate an exception if the response of your application does not meet the Rack spec
  • 28. And many more Rack::Auth::Basic Rack::Session::Cookie Rack::Sendfile http://coderack.org/ http://rack.rubyforge.org/doc/
  • 29. Is this testable? Use your favorite framework It provides Rack::MockRequest and Rack::MockResponse
  • 30. With bacon Bacon is a small RSpec clone “ weighing less than 350 LoC but nevertheless providing all essential features.
  • 31. MockRequest describe Rack::Static d o root = File.expand_path(File.dirname(_ _ F I L E _ _ _ OPTIONS = {:urls => ["/cgi"], :root => root @request = Rack::MockRequest.new( Rack::Static.new(DummyApp.new, OPTIONS it "serves files" d o res = @request.get("/cgi/test") res.should.be.ok res.body.should =~ /ruby/ end end
  • 32. MockResponse describe Rack::Chunked d o before d o @env = Rack::MockRequest. env_for('/', 'HTTP_VERSION' => '1.1', 'REQUEST_METH end should 'chunk responses with no Content-Length' d o app = lambda { |env| [200, {}, ['Hello', response = Rack::MockResponse.new( *Rack::Chunked.new(app).call(@env)) response.headers.should.n o t .i n c l u d e 'Content-Le n i response.headers['Transfer-Encoding'].should response.body.should.equal "5rnHellorn1rn rn6rnWorld!rn0rnrn" end end
  • 33. Why do we care? Supported web servers Mongrel, EventedMongrel, SwiftipliedMongrel WEBrick, FCGI, CGI, SCGI, LiteSpeed Thin
  • 34. These web servers include handlers in their distributions Ebb, Fuzed, Glassfish v3 Phusion Passenger (which is mod_rack for Apache and for nginx) Rainbows!, Unicorn, Zbatery
  • 35. Any valid Rack app will run the same on all these handlers, without changing anything
  • 36. Supported web frameworks Camping, Coset, Halcyon, Mack Maveric, Merb, Racktools::SimpleApplication Ramaze, Rum, Sinatra, Sin Vintage, Waves Wee, … and many others.
  • 37. Of course Ruby on Rails Rails has adopted the Rack philosophy throughout the framework A Rails application is actually a collection of Rack and Rails middleware components that all work together to form the completed whole
  • 38. Listing the rails middleware stack $...(master) $ rake middleware (in /home/chischaschos/Projects/salary-manager) use ActionDispatch::Static use Rack::Lock use ActiveSupport::Cache::Strategy::LocalCache use Rack::Runtime use Rails::Rack::Logger use ActionDispatch::ShowExceptions use ActionDispatch::RemoteIp use Rack::Sendfile use ActionDispatch::Callbacks use ActiveRecord::ConnectionAdapters::ConnectionManagement use ActiveRecord::QueryCache use ActionDispatch::Cookies use ActionDispatch::Session::CookieStore use ActionDispatch::Flash use ActionDispatch::ParamsParser use Rack::MethodOverride use ActionDispatch::Head use ActionDispatch::BestStandardsSupport use Warden::Manager use Sass::Plugin::Rack run SalaryManager::Application.routes
  • 39. Things to note The Rack application being run with the run directive at the end of the list of middlewares is the Rails application's routes
  • 40. Rails controllers are rack compliant A controller declaration c l a s s HomeController < ApplicationCont d e f index render :text => "I'm your home cont end end
  • 41. Rails console testing (had to shorten the output) $ruby-1.8.7-p302 > ...$ rails console Loading development environment (Rails 3.0.0) ruby-1.8.7-p302 > app = RailsRackApp::Application ruby-1.8.7-p302 > app.class => ActionDispatch::Routing::RouteSet ruby-1.8.7-p302 > env = {'REQUEST_METHOD' => 'GET => {"PATH_INFO"=>"/home/index", "REQUEST_METHOD" ruby-1.8.7-p302 > status, headers, body = app.cal => [200, {"ETag"=>""d47cb2eec6f22cb9ff6fbb21cd3 ruby-1.8.7-p302 > body.body => "I'm yout home controller's body"
  • 42. Rack app from a controller declaration $ruby-1.8.7-p302 > app = HomeController.action :i => #<Proc:0xb6e26664@/home/chischaschos/.rvm/gem ruby-1.8.7-p302 > app.respond_to? 'call' => true ruby-1.8.7-p302 > status, headers, body = app.cal => [200, {"ETag"=>""d47cb2eec6f22cb9ff6fbb21cd34 ruby-1.8.7-p302 > body.body => "I'm yout home controller's body"
  • 43. There are two different ways to install Rack components into your Rails application 1 - Either configure your Rack application as part of your application's middleware stack 2 - Or you can route URI paths directly to the Rack application from you application's routes
  • 44. 1.1 - Installing a component into your application lib/average_time.rb c l a s s AverageRuntime @@requests = 0 @@total_runtime = 0.0 d e f initialize(app) @app = app end d e f call(env) code, headers, body = @app.call(env @@requests += 1 @@total_runtime += headers['X-Runtime' headers['X-AverageRuntime'] = (@@total_runtime / @@requests).to_s [code, headers, body] end
  • 45. 1.2 - Inserting the middleware config/application.rb r e q u i r e File.expand_path('../boot', _ _ F I L E _ _ r e q u i r e 'rails/all' Bundler.r e q u i r e (:default, Rails.env) r m o d u l e RailsRackApp c l a s s Application < Rails::Application # starts the important part config.autoload_paths += %W(#{config config.middleware.insert_before Rack "AverageRuntime" # end the important part config.encoding = "utf-8" config.filter_parameters += [:password end end
  • 46. 1.3 - Verifying middleware is in the stack $...$ rake middleware (in /home/chischaschos/Projects/rack-testing/rails-rack-app) use ActionDispatch::Static use Rack::Lock use AverageRuntime use ActiveSupport::Cache::Strategy::LocalCache use Rack::Runtime use Rails::Rack::Logger use ActionDispatch::ShowExceptions use ActionDispatch::RemoteIp use Rack::Sendfile use ActionDispatch::Callbacks use ActiveRecord::ConnectionAdapters::ConnectionManagement use ActiveRecord::QueryCache use ActionDispatch::Cookies use ActionDispatch::Session::CookieStore use ActionDispatch::Flash use ActionDispatch::ParamsParser use Rack::MethodOverride use ActionDispatch::Head use ActionDispatch::BestStandardsSupport run RailsRackApp::Application.routes
  • 47. 1.4 Testing our middleware Look at X-Averageruntime: header $...$ curl -I localhost:3000 HTTP/1.1 404 Not Found Connection: Keep-Alive Content-Type: text/html Date: Fri, 05 Nov 2010 16:04:43 GMT Server: WEBrick/1.3.1 (Ruby/1.8.7/2010-08-16) X-Runtime: 0.312526 Content-Length: 621 X-Averageruntime: 0.312526
  • 48. 2.1 - Routing to a rack application lib/walking_arrow.rb c l a s s WalkingArrow ARROW = '=>' @@spaces = 0 d e f call(env) @@spaces += 1 [200, {'Content-Type' => 'text/plain'}, end end
  • 49. 2.2 - Add a route lib/walking_arrow.rb r e q u i r e 'lib/walking_arrow.rb' RailsRackApp::Application.routes.draw get 'home/index' get 'walkingarrow' => WalkingArrow.new end
  • 50. 2.3 Testing our middleware Walk!!! $...$ curl localhost:3000/walkingarrow => ...$ curl localhost:3000/walkingarrow => ...$ curl localhost:3000/walkingarrow => ...$ curl localhost:3000/walkingarrow => ...$ curl localhost:3000/walkingarrow => ...$ curl localhost:3000/walkingarrow =>
  • 51. Before diving into rack and rails creation Learn and play with some examples http://guides.rubyonrails.org /railsonrack.html
  • 52. Do you have ideas on how to use it?
  • 53. Most sincere thanks to http://rack.rubyforge.org/doc/ http://rails-nutshell.labs.oreilly.com /ch07.html http://rubylearning.com/blog/2010/09/21 /writing-modular-web-applications- with-rack/?utmsource=twitterfeed& utmmedium=twitter And Mendo
  • 54. References github repo and examples chischaschos twitter