lib/flapjack/gateways/jsonapi.rb in flapjack-1.1.0 vs lib/flapjack/gateways/jsonapi.rb in flapjack-1.2.0rc1

- old
+ new

@@ -87,10 +87,17 @@ @entity = entity @check = check end end + class EntityChecksNotFound < RuntimeError + attr_reader :entity_checks + def initialize(entity_checks) + @entity_checks = entity_checks + end + end + class ResourceLocked < RuntimeError attr_reader :resource def initialize(resource) @resource = resource end @@ -98,41 +105,49 @@ set :dump_errors, false set :protection, :except => :path_traversal - rescue_error = Proc.new {|status, exception, request_info, *msg| - if !msg || msg.empty? - trace = exception.backtrace.join("\n") - msg = "#{exception.class} - #{exception.message}" - msg_str = "#{msg}\n#{trace}" - else - msg_str = msg.join(", ") - end - case - when status < 500 - @logger.warn "Error: #{msg_str}" - else - @logger.error "Error: #{msg_str}" - end + @rescue_exception = Proc.new {|env, e| - response_body = {:errors => msg}.to_json + rescue_error = Proc.new {|status, exception, request_info, *msg| + if !msg || msg.empty? + trace = exception.backtrace.join("\n") + msg = "#{exception.class} - #{exception.message}" + msg_str = "#{msg}\n#{trace}" + else + msg_str = msg.join(", ") + end + case + when status < 500 + @logger.warn "Error: #{msg_str}" + else + @logger.error "Error: #{msg_str}" + end - query_string = (request_info[:query_string].respond_to?(:length) && - request_info[:query_string].length > 0) ? "?#{request_info[:query_string]}" : "" - if @logger.debug? - @logger.debug("Returning #{status} for #{request_info[:request_method]} " + - "#{request_info[:path_info]}#{query_string}, body: #{response_body}") - elsif @logger.info? - @logger.info("Returning #{status} for #{request_info[:request_method]} " + - "#{request_info[:path_info]}#{query_string}") - end + response_body = Flapjack.dump_json(:errors => msg) - [status, {}, response_body] - } + query_string = (request_info[:query_string].respond_to?(:length) && + request_info[:query_string].length > 0) ? "?#{request_info[:query_string]}" : "" + if @logger.debug? + @logger.debug("Returning #{status} for #{request_info[:request_method]} " + + "#{request_info[:path_info]}#{query_string}, body: #{response_body}") + elsif @logger.info? + @logger.info("Returning #{status} for #{request_info[:request_method]} " + + "#{request_info[:path_info]}#{query_string}") + end - rescue_exception = Proc.new {|env, e| + headers = if 'DELETE'.eql?(request_info[:request_method]) + # not set by default for delete, but the error structure is JSON + {'Content-Type' => JSONAPI_MEDIA_TYPE} + else + {} + end + + [status, headers, response_body] + } + request_info = { :path_info => env['REQUEST_PATH'], :request_method => env['REQUEST_METHOD'], :query_string => env['QUERY_STRING'] } @@ -145,19 +160,25 @@ rescue_error.call(404, e, request_info,"could not find notification rule '#{e.notification_rule_id}'") when Flapjack::Gateways::JSONAPI::NotificationRulesNotFound rescue_error.call(404, e, request_info, "could not find notification rules '" + e.notification_rule_ids.join(', ') + "'") when Flapjack::Gateways::JSONAPI::EntityNotFound rescue_error.call(404, e, request_info, "could not find entity '#{e.entity}'") + when Flapjack::Gateways::JSONAPI::EntitiesNotFound + entity_ids = "'" + e.entity_ids.join("', '") + "'" + rescue_error.call(404, e, request_info, "could not find entities: #{entity_ids}") when Flapjack::Gateways::JSONAPI::EntityCheckNotFound rescue_error.call(404, e, request_info, "could not find entity check '#{e.check}'") + when Flapjack::Gateways::JSONAPI::EntityChecksNotFound + checks = "'" + e.entity_checks.join("', '") + "'" + rescue_error.call(404, e, request_info, "could not find entity checks: #{checks}") when Flapjack::Gateways::JSONAPI::ResourceLocked rescue_error.call(423, e, request_info, "unable to obtain lock for resource '#{e.resource}'") else rescue_error.call(500, e, request_info) end } - use ::Rack::FiberPool, :size => 25, :rescue_exception => rescue_exception + use ::Rack::FiberPool, :size => 25, :rescue_exception => @rescue_exception use ::Rack::MethodOverride use Flapjack::Gateways::JSONAPI::Rack::JsonParamsParser class << self @@ -203,11 +224,11 @@ end before do input = nil query_string = (request.query_string.respond_to?(:length) && - request.query_string.length > 0) ? "?#{request.query_string}" : "" + (request.query_string.length > 0)) ? "?#{request.query_string}" : "" if logger.debug? input = env['rack.input'].read logger.debug("#{request.request_method} #{request.path_info}#{query_string} #{input}") elsif logger.info? input = env['rack.input'].read @@ -254,11 +275,11 @@ end def err(status, *msg) msg_str = msg.join(", ") logger.info "Error: #{msg_str}" - [status, {}, {:errors => msg}.to_json] + [status, {}, Flapjack.dump_json(:errors => msg)] end def is_json_request? Flapjack::Gateways::JSONAPI::JSON_REQUEST_MIME_TYPES.include?(request.content_type.split(/\s*[;,]\s*/, 2).first) end @@ -388,10 +409,10 @@ end # bare 'params' may have splat/captures for regex route, see # https://github.com/sinatra/sinatra/issues/453 post '*' do - halt(405) unless request.params.empty? || is_json_request? || is_jsonapi_request + halt(405) unless request.params.empty? || is_json_request? || is_jsonapi_request? content_type JSONAPI_MEDIA_TYPE cors_headers pass end