Question

In my mochiweb application, I am using a long held HTTP request. I wanted to detect when the connection with the user died, and I figured out how to do that by doing:

Socket = Req:get(socket),
inet:setopts(Socket, [{active, once}]),
receive
     {tcp_closed, Socket} ->
             % handle clean up
     Data ->
             % do something 
end.

This works when: user closes his tab/browser or refreshes the page. However, when the internet connection dies suddenly (say wifi signal lost all of a sudden), or when the browser crashes abnormally, I am not able to detect a tcp close.

Am I missing something, or is there any other way to achieve this?

Was it helpful?

Solution

There is a TCP keepalive protocol and it can be enabled with inet:setopts/2 under the option {keepalive, Boolean}.

I would suggest that you don't use it. The keep-alive timeout and max-retries tends to be system wide, and it is optional after all. Using timeouts on the protocol level is better.

The HTTP protocol has the status code Request Timeout which you can send to the client if it seems dead.

Check out the after clause in receive blocks that you can use to timeout waiting for data, or use the timer module, or use erlang:start_timer/3. They all have different performance characteristics and resource costs.

OTHER TIPS

There isn't a default "keep alive" (but can be enabled if supported) protocol over TCP: in case there is a connection fault when no data is exchanged, this translates to a "silent failure". You would need to account for this type of failure by yourself e.g. implement some form of connection probing.

How does this affect HTTP? HTTP is a stateless protocol - this means that every request is independent of every other. The "keep alive" functionality of HTTP doesn’t change that i.e. "silent failure" can still occur.

Only when data is exchanged can this condition be detected (or when TCP Keep Alive is enabled).

I would suggest sending the application level keep alive messages over HTTP chunked-encoding. Have your client/server smart enough to understand the keep alive messages and ignore them if they arrive on time or close and re-establish the connection again.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top