Skip to main content
Known Participant
October 8, 2009
Question

Many threads on application.onDisconnect not firing but seemingly no solution

  • October 8, 2009
  • 1 reply
  • 1647 views

I've dug some threads up and included links at the end of this post. Have some more work to do researching it but figured I'd get the ball rolling.

Essentially one can't depend on application.onDisconnect() firing at the close of a client's browser.  It happens sometimes.  But with some apps, it just doesn't happen at all.  I've watched the FMS management console as I've repeatedly opened and closed a particular app I'm developing.  Connections don't die with each browser close.  The net result is a piling up of connections.  My app has a "connected users" list in it.  It gets packed with multiple connections from the same client.

Eventually, after 5-10 mins, the connections disappear on their own.  Not good though.  One of the functions in my app lets someone select a user in the list and send a direct chat.  This feature isn't working because disconnections are not registering real time.  Some of the people in the user list are not really there anymore.

I get the problem in both IE8 and FireFox 3.5.3 on FMS 3.52.  Others have reported the problem in various browsers and FMS versions going way back. Problem's been around for some time.

This guy has the same problem and a nice description, although he experienced only in IE:

onDisconnect Errors in Internet Explorer: (http://www.flashnewz.com/ondisconnect-errors-in-internet-explorer/)

After reading the accounts at the links gathered below, I get the feeling it might not necessarily be an FMS problem alone, but rather some combo of browser, SWFObject implementation, and perhaps particular features used (or not used) in the client ActionScript.  Nobody's seemed to nail down the precise combination though.

Pretty much a show stopper.  Has anyone developed viable work arounds?


Thread: onDisconnect() IE7 problem: (http://fmsguru.com/forum/messages.cfm?threadid=EEC6D52A-BAB2-526D-5CD9FF490332B8D8)
onDisconnect Not Firing in IE6/7 With SWFObject 2: (http://www.flashcomguru.com/index.cfm/2008/8/7/swfobject-problem-ie-fms)
Do not call onDisconnect when closing browser: (http://www.wowzamedia.com/forums/showthread.php?t=5521)
BUG -Flash Media Interactive Server 3: (http://www.justskins.com/forums/bug-flash-media-interactive-server-3-a-141282.html)
onDisconnect Event in FMS 2.0: (http://forums.adobe.com/thread/98366)
Topic: Detecting ungraceful disconnects? (http://www.flashcomguru.com/forum/forum_posts.asp?TID=2848&PN=0&TPN=2)

Why Flash Media Server does not call application.onDisconnect handler: (http://stackoverflow.com/questions/359727/why-flash-media-server-does-not-call-application-ondisconnect-handler)

    This topic has been closed for replies.

    1 reply

    Participating Frequently
    March 11, 2010

    FMS can only detect a dropped connection if the local TCP stack in the OS kernel receives a FIN or RST for that specific TCP connection from the far end (or from a proxy, etc. along the network path in the case of a intermediate component that may force close connections on an interval or something), or by actively trying to write some data to the connection where your local TCP stack ends up timing out the connection after trying its OS-dependent retransmission sequence and finally giving up, deciding that the far end went away without telling it.

    There are a variety of ways to "disconnect" a client without the TCP stack at the server being informed. For instance, if I dock my Thinkpad laptop and then unplug the network cable from the dock, no RST or FIN is sent. Weird   So the only way for a server to know I've gone away, is for it to try to send me some data and for its TCP stack to timeout in retransmissions.

    To deal with this scenario, you'll need to write server code to essentially send a heartbeat of some sort to idle clients. Your client app could ignore these, in which case the server TCP stack will let FMS know that client is disconnected after finishing all its retransmission attempts for that packet(s). Some OSes take longer than others to time out... If that's an issue and you want to enforce a harder deadline, you'd want your client to reply, and if you didn't hear a reply within a time limit you'd need to decide for your app, you could kill that client explicitly. Of course, in this case you run some risk of killing clients that are just on slow network links, or clients running on machines that are busy doing other work.

    TCP keepalive is useless and not helpful with any of this.

    Hope that helps,

    Seth

    calmchessplayer
    Inspiring
    March 12, 2010

    ////////////////////////////////////////////////////////////////////////////////////client side////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

    var nc = new NetConnection()

    nc.onStatus = function (o)
    {
    trace(o.code);
    };

    nc.connect("rtmp://YourAccount.rtmphost.com/AppDirectory");

    nc.imHere = function(p_b)
    {
    trace("imHere");
    return (true)
    };

    ////////////////////////////////////////////////////////////////server side//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

    load("Delegate.asc");

    application.onConnect = function(p_o)
    {
    this.acceptConnection(p_o);

    p_o.clientIsBad= function()
    {
      trace ("is bad")
      clearInterval(this.resultInt);
      clearInterval(this.checkInt);
      application.disconnect(this);
     
    };
    p_o.clientIsGood = function()
    {
      trace ("is good")
      clearInterval(this.resultInt);
    };

    p_o.checkValid = function()
    {
      trace("watcha!");
      clearInterval(this.resultInt)
      this.resultInt = setInterval( p_o, "clientIsBad", 2000 );
      this.call("imHere",{onResult:Delegate.create(p_o, this.clientIsGood),onStatus:Delegate.create()} );;

    };

    p_o.checkInt = setInterval( p_o, "checkValid", 120000 );
    };

    calmchessplayer
    Inspiring
    March 12, 2010

    the above script is for sending out a  "are you alive ping" if no ping then you dead and disconnected good day.