Reputation: 6739
In my rails app which is json only, I want to send a 406 code whenever someone calls my rails app with accept header set to anything except application/json. I also want it to send a 415 when I get the content type set to anything except application / json
My controllers have respond_to :json put on them. I only render json in all actions. However how do I ensure that I return error code 406/415 for all calls for anything that is called for all other accept headers/content-type and with format set to anything except json.
Eg. If I my resource is books/1 I want to allow books/1.json or books/1 with application/json in accept header and content type
Any ideas on how I can do these two actions?
Upvotes: 15
Views: 21454
Reputation: 10285
On rails 4.2+ respond_to has been removed, so unless you want to import the full responders gem just for this, your best bet is to roll your own. This is what I'm using in my rails 5 api:
class ApplicationController < ActionController::API
before_action :force_json
private
def force_json
# if params[_json] it means request was parsed as json
# if body.read.blank? there was no body (GET/DELETE) so content-type was meaningless anyway
head :not_acceptable unless params['_json'] || request.body.read.blank?
end
end
Upvotes: -1
Reputation: 10423
Basically, you can limit your responses in two ways.
First, there is respond_to
for your controllers. This would automatically trigger a 406 Not Acceptable
if a request for a format is made which is not defined.
Example:
class SomeController < ApplicationController
respond_to :json
def show
@record = Record.find params[:id]
respond_with @record
end
end
The other way would be to add a before_filter
to check for the format and react accordingly.
Example:
class ApplicationController < ActionController::Base
before_filter :check_format
def check_format
render :nothing => true, :status => 406 unless params[:format] == 'json' || request.headers["Accept"] =~ /json/
end
end
Upvotes: 37
Reputation: 15788
You can do it with a before_filter in ApplicationController
before_filter :ensure_json_request
def ensure_json_request
return if params[:format] == "json" || request.headers["Accept"] =~ /json/
render :nothing => true, :status => 406
end
Upvotes: 10