Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Handle throwing in controller action in log subscriber #41223

Merged
merged 1 commit into from Jan 24, 2021

Conversation

janko
Copy link
Contributor

@janko janko commented Jan 23, 2021

Summary

When throw was used in a controller action, and there is matching catch around the request in a Rack middleware, then :exception won't be present in the event payload.

This is because ActiveSupport::Notifications::Instrumenter.instrument sets :exception in a rescue handler, but rescue is never called in a throw/catch scenario:

catch(:halt) do
  begin
    throw :halt
  rescue Exception => e
    puts "rescue" # never reached
  ensure
    puts "ensure"
  end
end

Missing :exception was actually handled prior to Rails 6.1.0, but an optimization updated the code to assume :exception was present. I found it easiest to just revert the commit. This PR can therefore be considered a regression fix.

Other Information

I've experienced this issue when using Rodauth with Rails, which throws :halt when redirecting (with Rodauth middleware catching :halt), and there are use cases in which Rodauth's redirect method is called inside a controller action.

@rails-bot rails-bot bot added the actionpack label Jan 23, 2021
@janko janko force-pushed the controller-throw-log-subscriber branch 2 times, most recently from 21868b9 to da34a83 Compare January 23, 2021 23:22
When throw was used in a controller action, and there is matching catch
around the request in a Rack middleware, then :exception won't be
present in the event payload.

This is because ActiveSupport::Notifications::Instrumenter.instrument
sets :exception in a rescue handler, but rescue is never called in a
throw/catch scenario:

  catch(:halt) do
    begin
      throw :halt
    rescue Exception => e
      puts "rescue" # never reached
    ensure
      puts "ensure"
    end
  end

Missing :exception was actually handled prior to Rails 6.1.0, but an
optimization updated the code to assume this was present. So this can be
considered a regression fix.
@janko janko force-pushed the controller-throw-log-subscriber branch from da34a83 to 53adf53 Compare January 24, 2021 08:53
@kamipo kamipo merged commit b32823a into rails:main Jan 24, 2021
@kamipo
Copy link
Member

kamipo commented Jan 24, 2021

The test failures are already fixed in current main branch #41203.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants