When/Where to use RemoveHandler?

The documentation insists that it is important that we remove handlers when we’re done with them but it doesn’t say why. Nor does it talk about what to do if your handler is never called.

For example, let’s say that I have a URLConnection that is instantiated in code and I create two handlers… one for the ContentReceived event and one for the Error event.

Connection = New URLConnection
AddHandler Connection.ContentReceived, WeakAddressOf HandleList
AddHandler Connection.Error, WeakAddressOf HandleError

As per the documentation, we should include a RemoveHandler statement after handling the events…

Private Sub HandleList(sender As URLConnection, URL As String, HTTPStatus As Integer, content As String)
  #If TargetMacOS
    #Pragma unused sender
  #EndIf
  
  // Do something with the data received...

  // Remove the Handler...
  RemoveHandler Connection.ContentReceived, WeakAddressOf HandleList
  
End Sub
Private Sub HandleError(sender As URLConnection, e As RuntimeException)
  #If TargetMacOS
    #Pragma unused sender
  #EndIf

  // Do something about the error...
  MessageBox(e.Message)

  // Remove the Handler...
  RemoveHandler Connection.Error, WeakAddressOf HandleError

End Sub

Logically, only one of these events are going to be called. Is that going to be a problem?

If so, is it perhaps better to put the RemoveHandler statements in the Destructor of the class instead? That way all Handlers are removed.

1 Like

Or is it common practise to remove both handlers in both methods. Knowing that only one of them will be called, removing both either way also solves the problem, yes?

I am wondering why removing the handlers is so important. Do they remain in memory even after the object, within which they were created, is destroyed?

[quote=496843:@Kristin Green]The documentation insists that it is important that we remove handlers when we’re done with them but it doesn’t say why.
[/quote]
Depending on how you initially created it it adds a reference to the item that contains the method and that can prevent the item from being properly destroyed if you never remove the reference (ie/ never removehandler)

[quote=496843:@Kristin Green]Nor does it talk about what to do if your handler is never called.
[/quote]
Not being called is not an issue insofar as references are concerned or whether you should remove the handler
If you added a handler you should remove it

[quote=496900:@Norman Palardy]Not being called is not an issue insofar as references are concerned or whether you should remove the handler
If you added a handler you should remove it[/quote]

So, do you think I should remove both handlers at the end of both handler methods? As below?

Private Sub HandleList(sender As URLConnection, URL As String, HTTPStatus As Integer, content As String)
  #If TargetMacOS
    #Pragma unused sender
  #EndIf
  
  // Do something with the data received...

  // Remove all of the Handlers...
  RemoveHandler Connection.ContentReceived, WeakAddressOf HandleList
  RemoveHandler Connection.Error, WeakAddressOf HandleError
  
End Sub

[code]
Private Sub HandleError(sender As URLConnection, e As RuntimeException)
#If TargetMacOS
#Pragma unused sender
#EndIf

// Do something about the error…
MessageBox(e.Message)

// Remove all of the Handlers…
RemoveHandler Connection.ContentReceived, WeakAddressOf HandleList
RemoveHandler Connection.Error, WeakAddressOf HandleError

End Sub[/code]

Would it be just as good to simply put the remove handler statements once in the destructor of the class that added them? Or would there be a performance penalty associated with keeping them around?

Whether you should remove them at that point is hard for me to say
The destructor of the object that added them seems like a better place BUT, if they manage to create a reference cycle then the destructor may not execute and now you just leak objects

Be particularly careful with WeakAddressOf
There is no way to test whether the target has been nil’d and that can cause its own unique set of issues
<https://xojo.com/issue/26060>

Personally I try really really hard to avoid using AddHandler as much as I can

i would say as long the object Connection is valid
the events should be processed.
if you subclass this URLConnection
you can add the events by menu and do not need
to use add/ remove handler.