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
Would make sense to have a "addChannelClosedHandler"? #52
Comments
Hi, adding a function that's called for channel exceptions sounds like a good idea. But I'm not sure it makes sense to have another function for non-exceptional channel closes. AFAIK the only way a channel could be non-exceptionally closed is when the user calls |
Sounds perfectly reasonable to me! Thanks for the blazing-fast reply ;) |
Yes, I'd review and most probably merge it. |
Now that #53 has been merged, any chance for 0.12 to hit Hackage today? 😉 |
Pushed it to Hackage. I initially wanted to also remove that Thank you for your contribution! Let's hope we didn't break anything. |
Ha! Thank you very much! I am going to give a package a go next week, so if we did I will report back :) |
As a small success story, our patch seems to work, at least superficially. This is what I get from the logs inside my development environment, when the server is running but I kill the broker abruptly:
the message that you see, is triggered by this simple helper function: -- We explicitly filter out the two cases where a channel can be closed gracefully;
-- 1. When it received a ThreadKilled exception
-- 2. When a user is shutting it down as part of the normal connection closing routine.
reactToChannelException :: SomeException -> IO ()
reactToChannelException (asyncExceptionFromException -> Just ThreadKilled) = return ()
reactToChannelException (fromException -> Just (ConnectionClosedException "closed by user")) = return ()
reactToChannelException ex = do
yellow $ T.pack $ "Rebooting the server due to " <> show ex
rebootServer (I'm using the ViewPattern extension to make everything a bit more slick). |
Hi @hreinhardt ,
In production it would be nice to know and take action every time a channel is closed, for any reason. Since each channel connection is created in a separate thread, we are out of luck at the moment:
https://github.com/hreinhardt/amqp/blob/master/Network/AMQP/Internal.hs#L589
The library is rightfully using
finally
here, so all it would take is:addConnectionClosedHandler
, which would allow us to register new handlersfinally
block, to make sure we get notified.A perhaps even better solution would be to leverage
forkFinally
:http://hackage.haskell.org/package/base-4.7.0.2/docs/Control-Concurrent.html#v:forkFinally
This would allow us to expose two new functions,
addChannelClosedHandler
andaddChannelClosedExceptionHandler
. Simply pattern matching on the result given back fromforkFinally
would allow us to call one group on handlers rather than the other. This would have the benefit to react differently whether the channel is closed "naturally" or if an exception caused it to be closed. Bear in mind thought thatforkFinally
is available from base 4.7 onwards, so a bit of CPP would be needed to support prior to 7.8.xDo you think all of this would be an overkill?
Thanks a lot!
Alfredo
The text was updated successfully, but these errors were encountered: