Disable RackLogger in favor of manually hooking into actions' "handle" for logging requests

Hello :wave:

I’ve been spending a few hours investigating but couldn’t yet find a clean way - is it possible to disable rack_monitor completely? My intention is to hook around the Hanami::Action#call method, so it’s easier for actions to add some payload to the logging.

A practical example would be adding e.g.: “user_id: …” to the log payload - and considering that user authentication might happen during the Hanami::Action#call lifecycle.

Also for context, here’s how we can do that using Rails:

class AuthenticatedController < ApplicationController
  before_action :authenticate!

  def append_info_to_payload(payload)
    super
    payload[:usr] = {
      id: current_user&.id,
      email: current_user&.email
    }
  end

  # implementation details...
  # def authenticate!
  # def current_user
end

class LogSubscriber < ActiveSupport::LogSubscriber
  def process_action(event)
    info { { message: "Processed request", user: event.payload[:usr] }.to_json }
  end
  subscribe_log_level :process_action, :info
end

# detach old log subscriber
ActiveSupport::Notifications.unsubscribe("process_action.action_controller")

# attach my new log subscriber
::LogSubscriber.attach_to :action_controller

NOTE: Not directly related to the topic but I think it’s also related - I’m also looking to swap Dry::Logger for SemanticLogger (which all of our other services are now using). As of now I’m doing that by:

# lib/rack_semantic_logger.rb
# patch Hanami RackLogger so it understands that SemanticLogger is compatible
Hanami::Web::RackLogger::UniversalLogger.singleton_class.prepend(
  Module.new do
    private def compatible_logger?(*)
      true
    end
  end
)
# Rack middleware to add some http-specific tags to all logs
class RackSemanticLogger
  def initialize(app, logger: SemanticLogger[Rack])
    @logger = logger
    @app = app
  end
  def call(env)
    request = Rack::Request.new(env)
    named_tags = {
      url: request.url,
      host: request.host,
      user_agent: request.user_agent,
      # etc...
    }

    @logger.tagged(http: named_tags) { @app.(env) }
  end
end

# config.ru
# NOTE: this is done in config.ru as it was the only way I found to
#   wrap rack_monitor logs in my `@logger.tagged { }` block
use RackSemanticLogger

# app configuration in config/app.rb
$stdout.sync = true
config.logger = SemanticLogger[Hanami]
SemanticLogger.default_level = settings.log_level
SemanticLogger.add_appender(io: $stdout, formatter: MyCustomFormatter.new)