How to limit the resource formats in the Rails routes file
content-type, rest, routes, ruby-on-rails
Solution
Since Rails uses the equivalent of a wildcard to handle formats ".:format" it's a bit more difficult to prevent things on the route side.
Instead of this, it's pretty easy way to catch any non HTML requests in a before filter. Here's one way this might look:
class ApplicationController < ActionController::Base
before_filter :check_format
private
def check_format
if request.format != Mime::HTML
raise ActionController::RoutingError, "Format #{params[:format].inspect} not supported for #{request.path.inspect}"
end
end
end
ActionController::RoutingErrors are handled as 404 errors which is sensible. In the event that you do have an action that needs to support something other than HTML, just use:
skip_before_filter :check_format, :only => ACTION_NAME
Problem
When routing resources in Rails the optional format attribute is automatically appended to the generated routes. This is so that the resource in question can be requested as either XML, HTML etc. Which formats that is actually allowed is usually described in the controller using `respond_to`. But in many cases you only want to support HTML and it feels like an overhead to write `respond_to :html` in every action in every controller. It would therefore be cool if there where a way to limit to allowed content types already when building the routes in the routes.rb file, e.g. ``` map.resources :users, :formats => :html map.resources :users, :formats => [:html, :xml] map.resources :users, :formats => {:index => :html, :show => [:html, :xml]} ``` Is there a way to achieve this either native or via a plugin? P.S. The usual way to work around this is to just ignore the problem and don't use `respond_to` in the actions. But this actually doesn't limit the allowed content types. Instead it just expects that a template exists in the views directory for each possible content type. If one doesn't exist when requested, the system will throw a HTTP 500 error.