Skip to content

Instantly share code, notes, and snippets.

@viola
Created September 26, 2011 22:19
Show Gist options
  • Save viola/1243572 to your computer and use it in GitHub Desktop.
Save viola/1243572 to your computer and use it in GitHub Desktop.
Render 405 response for ActionController::UnknownHttpMethod exceptions
ActionController::UnknownHttpMethod exception found under rails 3.0.1
$ cat lib/http_method_not_allowed.rb
# Render 405 response for ActionController::UnknownHttpMethod exceptions like:
# (ActionController::UnknownHttpMethod) "CONNECT, accepted HTTP methods are get, head, put, post, delete, and options"
# (ActionController::UnknownHttpMethod) "PROPFIND, accepted HTTP methods are get, head, put, post, delete, and options"
class HttpMethodNotAllowed
def initialize(app)
@app = app
end
def call(env)
# irb(main):001:0> ActionController::Request::HTTP_METHODS # => ["get", "head", "put", "post", "delete", "options"]
if !ActionController::Request::HTTP_METHODS.include?(env["REQUEST_METHOD"].downcase)
Rails.logger.info("ActionController::UnknownHttpMethod: #{env.inspect}")
[405, {"Content-Type" => "text/plain"}, ["Method Not Allowed"]]
else
@status, @headers, @response = @app.call(env)
[@status, @headers, @response]
end
end
end
Use HttpMethodNotAllowed as middleware config/application.rb
config.middleware.use "HttpMethodNotAllowed"
@hundredwatt
Copy link

Found this through Google and modified for Rails 4:

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

  def call(env)
    if !ActionDispatch::Request::HTTP_METHODS.include?(env["REQUEST_METHOD"].upcase)
      Rails.logger.info("ActionController::UnknownHttpMethod: #{env.inspect}")
      [405, {"Content-Type" => "text/plain"}, ["Method Not Allowed"]]
    else
      @status, @headers, @response = @app.call(env)
      [@status, @headers, @response]
    end
  end
end

@viola
Copy link
Author

viola commented Sep 22, 2014

👍

@dleve123
Copy link

dleve123 commented Oct 8, 2014

The HttpMethodNotAllowed did its job perfectly for me, but I needed to get the middleware close to the top of the stack to get it to work as expected. A config.middleware.insert_before(0, HttpMethodNotAllowed) did the trick. I'm on Rails 4.0.4.

Do you guys know of a more general way to suppress the 500 errors that Rack throws for things like this?

@kazmin
Copy link

kazmin commented May 14, 2015

With the comment from dleve123 it worked :), thanks!

@aashish
Copy link

aashish commented May 23, 2016

getting error
config/application.rb:69:inclass:Application': uninitialized constant HelloWorld::Application::HttpMethodNotAllowed (NameError)
`

@aashish
Copy link

aashish commented May 23, 2016

fixed by adding the following on in application.rb
require File.expand_path('../../lib/http_method_not_allowed', __FILE__)

@n00dle
Copy link

n00dle commented Aug 8, 2018

This works to suppress the error.

@dleve123 to suppress rack exceptions in general, set RACK_ENV to deployment.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment