class Squash::Rails::Rack

Rack middleware that catches exceptions thrown outside the scope of Rails's request processing. This middleware is automatically added to your stack when you include the `squash_rails` gem.

Public Class Methods

new(app) click to toggle source

Instantiates the middleware.

@param [Array] app The middleware stack.

# File lib/squash/rails/rack.rb, line 28
def initialize(app)
  @app = app
end

Public Instance Methods

call(env) click to toggle source

Rescues any exceptions thrown downstream, notifies Squash, then re-raises them.

@param [Hash] env The Rack environment. @return [Hash] The Rack result to pass up the stack.

# File lib/squash/rails/rack.rb, line 38
def call(env)
  @env = env

  begin
    result = @app.call(env)
  rescue ::Exception => ex
    unless ex.instance_variable_get(:@_squash_controller_notified)
      @env['squash.notified'] = ::Squash::Ruby.notify(ex, squash_rack_data)
    end
    raise ex
  end

  result
end
filter_for_squash(data, kind) click to toggle source

@abstract

Override this method to implement filtering of sensitive data in the headers, cookies, and rack hashes (see {#squash_rack_data}). The method signature is the same as `Squash::Ruby#filter_for_squash`, but `kind` can also be `:env` for the Rack environment hash.

# File lib/squash/rails/rack.rb, line 60
def filter_for_squash(data, kind)
  data
end
squash_rack_data() click to toggle source

@return [Hash<Symbol, Object>] The additional information this

middleware gives to `Squash::Ruby.notify`.
# File lib/squash/rails/rack.rb, line 67
def squash_rack_data
  data = {
      :environment    => environment_name,
      :root           => root_path,

      :headers        => filter_for_squash(request_headers, :headers),
      :request_method => @env['REQUEST_METHOD'].to_s.upcase,
      :schema         => @env['rack.url_scheme'],
      :host           => @env['SERVER_NAME'],
      :port           => @env['SERVER_PORT'],
      :path           => @env['PATH_INFO'],
      :query          => @env['QUERY_STRING'],

      :params         => filter_for_squash(@env['action_dispatch.request.parameters'], :params),
      :session        => filter_for_squash(@env['rack.session'], :session),
      :cookies        => filter_for_squash(@env['rack.request.cookie_hash'], :cookies),

      :"rack.env"     => filter_for_squash(@env, :rack)
  }

  if data[:session]
    flash_key    = defined?(ActionDispatch) ? ActionDispatch::Flash::KEY : 'flash'
    data[:flash] = filter_for_squash(data[:session].delete(flash_key) || {}, :flash)
  end

  data
end

Private Instance Methods

environment_name() click to toggle source
# File lib/squash/rails/rack.rb, line 97
def environment_name
  if defined?(::Rails)
    ::Rails.env.to_s
  else
    ENV['RAILS_ENV'] || ENV['RACK_ENV']
  end
end
request_headers() click to toggle source

Extract any rack key/value pairs where the key begins with HTTP_*

# File lib/squash/rails/rack.rb, line 106
def request_headers
  @env.select { |key, _| key[0, 5] == 'HTTP_' }
end
root_path() click to toggle source
# File lib/squash/rails/rack.rb, line 110
def root_path
  defined?(::Rails) ? ::Rails.root.to_s : ENV['RAILS_ROOT']
end