Sha256: 37b31f6995ad6c5b6f7ce378977c700ee4bde6373352d9b158b34757f5f279d2

Contents?: true

Size: 1.71 KB

Versions: 3

Compression:

Stored size: 1.71 KB

Contents

class InboundRequestsLoggerMiddleware
  attr_accessor :only_state_change, :path_regexp, :skip_body_regexp

  def initialize(app, only_state_change: true, path_regexp: /.*/, skip_body_regexp: nil)
    @app = app
    self.only_state_change = only_state_change
    self.path_regexp = path_regexp
    self.skip_body_regexp = skip_body_regexp
  end

  def call(env)
    request = ActionDispatch::Request.new(env)
    logging = log?(env, request)
    if logging
      env["INBOUND_REQUEST_LOG"] = InboundRequestLog.from_request(request)
      request.body.rewind
    end
    status, headers, body = @app.call(env)
    if logging
      updates = {response_code: status, ended_at: Time.current}
      updates[:response_body] = parsed_body(body) if log_response_body?(env)
      # this usually works. let's be optimistic.
      begin
        env["INBOUND_REQUEST_LOG"].update_columns(updates)
      rescue JSON::GeneratorError => _e # this can be raised by activerecord if the string is not UTF-8.
        env["INBOUND_REQUEST_LOG"].update_columns(updates.except(:response_body))
      end
    end
    [status, headers, body]
  end

  private

  def log_response_body?(env)
    skip_body_regexp.nil? || env["PATH_INFO"] !~ skip_body_regexp
  end

  def log?(env, request)
    env["PATH_INFO"] =~ path_regexp && (!only_state_change || request_with_state_change?(request))
  end

  def parsed_body(body)
    return unless body.present?

    if body.respond_to?(:body)
      JSON.parse(body.body)
    elsif body.respond_to?(:[])
      JSON.parse(body[0])
    else
      body
    end
  rescue JSON::ParserError, ArgumentError
    body
  end

  def request_with_state_change?(request)
    request.post? || request.put? || request.patch? || request.delete?
  end
end

Version data entries

3 entries across 3 versions & 1 rubygems

Version Path
rails_api_logger-0.8.1 lib/rails_api_logger/inbound_requests_logger_middleware.rb
rails_api_logger-0.8.0 lib/rails_api_logger/inbound_requests_logger_middleware.rb
rails_api_logger-0.7.0 lib/rails_api_logger/inbound_requests_logger_middleware.rb