The problem is that, according to what I see in developer tools and the ‘events’ panel in Debug mode, subscriptions is called every minute or so, and that creates a new WebSocket connection. As a consequence, I end up with plenty of WebSocket connections open unless I refresh the page.
Has anyone seen this before? What’s the fix? I tried Google/SO/etc but couldn’t find any answer.
I think your Sub.map ParseMessage (Login.subscriptions) will create a subscription to the ParseMessageMsg in your application, resulting in Login.subscriptions being called each time a ParseMessage is produced.
I think what you want is
pageSubscriptions : Flags -> Page -> Sub Msg
pageSubscriptions flags page =
case page of
....
Login _ ->
Login.subscriptions -- subscription created only once
I assume you’re referring to the use of Html.map in the viewPage function. That takes the Msg values produced by the submodules and maps them onto a Msg defined in the Main module (e.g. it converts a Page.Login.Msg to a Main.Msg, which is necessary for it to be handled by the Main.update function).
All of this is very separate from the Sub msg values produced by your top level subscriptions function. The only time you would want to use Sub.map is if you wanted to “listen” for some other Msg value that gets produced, and then produce a different Msg as a result.
In the case of your websocket connection, that is not what you want to do. There, you want to create a single subscription that produces ParseMessage when a message comes in.
So, thanks for the answer, but Sub.map wasn’t the issue. It seems the problem is the fact I call WebSocket.listen each time subscription is called, which happens regularly due to it being called after update as far as I can see.
How can I prevent the socket to be started each time? Is there any trick?
This code seems right to me. The websocket library should be keeping track of which connections are already open and not re-opening them.
I can think of two things that might be going wrong:
The url passed to WebSocket.listen changes. In this case, the library would open a new connection for each url.
The subscriptions method might be switching between returning WebSocket.listen and not. In this case, though, I’d expect a lot of opened connections but also a lot of closed ones.