On Sun Oct 07 07:06:42 2018, pliablepixels@gmail.com wrote:
Show quoted text> Good day, thank you for your excellent library. I have a usage question
> which may be a feature request as well, if an option doesn't exist today.
>
> I have am using your library to handle WSS connections from clients. I
> however need to be able to fork inside the server process so that the main
> loop continues while the fork handles communication with the child. This
> requires that the connection negotiation happens inside the child due to
> SSL state issues.
>
> I am initiating work on the on_connect handler of your library. Is there a
> pre-handler which I can intercept on an incoming TCP connection and then
> fork() and let the child handle the SSL upgrade?
>
> Thanks
You probably shouldn't be forking on a per-connection basis to avoid blocking the main process. The problem you are encountering is probably because Net::WebSocket::Server implements its own select-based event loop that you either aren't using or that isn't suitable for your needs. You shouldn't try to circumvent its event loop at the per-client level, as it defeats the resource benefits of using an event loop for client multiplexing. You should assume that once you call start(), Net::WebSocket::Server has control of the process. However, you have a few options:
Net::WebSocket::Server provides a few basic methods to support some simple main loop logic. If you specify tick_period, your on_tick handler will be called roughly that frequently; if you put your main loop logic there, possibly with some checks for each subtask to see whether enough time has passed, you might get what you need. If your main loop logic requires the detection of read/write availability on filehandles, you can also register event handlers via watch_readable and watch_writable. If you can meet those criteria, this is probably the option with the least effort for you.
If you really want control of your main process, but also want to use Net::WebSocket::Server, another option would be to run the entire Net::WebSocket::Server (and all of its child connections) in a single subprocess. This will require additional complexity to pass data between your main process and the server process, but could get you up and running quickly if you already have a lot of code that depends on Net::WebSocket::Server otherwise. (Admittedly, you'd also have to solve the communication problem if you manage to put each child in a subprocess as you describe.) In general, it's best to avoid this approach, but it might work for you.
I don't know the full scope of your project, but if what you need is a more complete (but more complex) event loop, I recommend using AnyEvent with AnyEvent::WebSocket::Server. This will require a rewrite of your project, but is flexible enough to support a very wide variety of projects. This option gives you many more ways to handle many more kinds of events, but still recommends that you to put your main loop in a timer-based callback like the Net::WebSocket::Server on_tick approach I outlined above.
Ultimately, you should probably avoid forking entirely - the goal of any event loop is to let one process handle many things as work is required for them. If you can reframe the work from your main loop into work that can be done in response to an event (like a periodic timer or changes in a file or data on a socket), your program will be simpler and use fewer resources.