I'm developing a web service in Ocaml
on top of MirageOS(Unix) and at the moment I'm having some trouble with Lwt.async()
. The Lwt documentation states the following:
val async : (unit -> 'a t) -> unit
async f starts a thread without waiting for the result. If it fails (now or later), the exception is given to Lwt.async_exception_hook.
You should use this function if you want to start a thread that might fail and don't care what its return value is, nor when it terminates (for instance, because it is looping).
So I immediately considered Lwt.async as a good candidate to run some tests and check that actually the execution is asynchronous. Unfortunately it's not working as expected. My code is the following:
let http_callback conn_id req _body =
Lwt.return(Uri.path (Cohttp.Request.uri req))
>>= function
| "/tester" -> Cohttp_lwt_body.to_string _body >>= fun res ->
log_lwt ~inject:(fun f -> f "Testing") >>= fun () ->
Lwt.async(fun () -> TEST.start 100 res !listOfIP);
H.respond_string ~status:`OK ~body:("DONE") ()
in
let spec = H.make ~callback:http_callback () in
CON.listen conduit (`TCP 8080) (H.listen spec)
For the sake of clarity, TEST.start executes a series of threaded operations. I assume that it doesn't really matter what the function inside Lwt.async is doing, considering that whatever returns/does should be ignored. Am I wrong?
In the end, my question is: why actually the client has to wait for the thread to receive the OK response? With or without async the behaviour is basically the same.
Control will only switch back to the HTTP handler if the async thread blocks waiting for something. If it just uses the CPU 100% until it's done then the async thread will probably run to completion first. Try putting a sleep in the tests to check.