Class: Rainbows::MaxBody
- Inherits:
-
Object
- Object
- Rainbows::MaxBody
- Defined in:
- lib/rainbows/max_body.rb
Overview
Middleware used to enforce client_max_body_size for TeeInput users.
There is no need to configure this middleware manually, it will automatically be configured for you based on the client_max_body_size setting.
For more fine-grained control, you may also define it per-endpoint in your Rack config.ru like this:
map "/limit_1M" do
use Rainbows::MaxBody, 1024*1024
run MyApp
end
map "/limit_10M" do
use Rainbows::MaxBody, 1024*1024*10
run MyApp
end
This is only compatible with concurrency models that expose a streaming “rack.input” to the Rack application. Thus it is NOT compatible with any of the following as they fully buffer the request body before the application dispatch:
-
:Coolio
-
:CoolioThreadPool
-
:CoolioThreadSpawn
-
:Epoll
-
:EventMachine
-
:NeverBlock
-
:Rev
-
:RevThreadPool
-
:RevThreadSpawn
-
:XEpoll
However, the global Rainbows::Configurator#client_max_body_size is compatible with all concurrency models Rainbows! supports.
Class Method Summary collapse
-
.setup ⇒ Object
this is called after forking, so it won’t ever affect the master if it’s reconfigured.
Instance Method Summary collapse
-
#call(env) ⇒ Object
our main Rack middleware endpoint.
-
#err ⇒ Object
Rack response returned when there’s an error.
-
#initialize(app, limit = nil) ⇒ MaxBody
constructor
This is automatically called when used with Rack::Builder#use.
- #limit_input!(env) ⇒ Object
Constructor Details
#initialize(app, limit = nil) ⇒ MaxBody
This is automatically called when used with Rack::Builder#use
42 43 44 45 46 47 48 49 |
# File 'lib/rainbows/max_body.rb', line 42 def initialize(app, limit = nil) case limit when Integer, nil else raise ArgumentError, "limit not an Integer" end @app, @limit = app, limit end |
Class Method Details
.setup ⇒ Object
this is called after forking, so it won’t ever affect the master if it’s reconfigured
67 68 69 70 71 72 73 74 75 76 77 78 79 |
# File 'lib/rainbows/max_body.rb', line 67 def self.setup # :nodoc: Rainbows.server.client_max_body_size or return case Rainbows.server.use when :Rev, :Coolio, :EventMachine, :NeverBlock, :RevThreadSpawn, :RevThreadPool, :CoolioThreadSpawn, :CoolioThreadPool, :Epoll, :XEpoll return end # force ourselves to the outermost middleware layer Rainbows.server.app = self.new(Rainbows.server.app) end |
Instance Method Details
#call(env) ⇒ Object
our main Rack middleware endpoint
52 53 54 55 56 57 58 59 60 61 62 63 |
# File 'lib/rainbows/max_body.rb', line 52 def call(env) @limit = Rainbows.server.client_max_body_size if nil == @limit catch(:rainbows_EFBIG) do len = env['CONTENT_LENGTH'] if len && len.to_i > @limit return err elsif /\Achunked\z/i =~ env['HTTP_TRANSFER_ENCODING'] limit_input!(env) end @app.call(env) end || err end |
#err ⇒ Object
Rack response returned when there’s an error
82 83 84 |
# File 'lib/rainbows/max_body.rb', line 82 def err # :nodoc: [ 413, { 'Content-Length' => '0', 'Content-Type' => 'text/plain' }, [] ] end |
#limit_input!(env) ⇒ Object
86 87 88 89 90 |
# File 'lib/rainbows/max_body.rb', line 86 def limit_input!(env) input = env['rack.input'] klass = input.respond_to?(:rewind) ? RewindableWrapper : Wrapper env['rack.input'] = klass.new(input, @limit) end |