I want to send some http requests to a target, but not all at once, I’d like to send a request once a second. My demo would be:
open Core
open Async
open Cohttp
open Cohttp_async
let mock_lst = [111; 222; 333; 666; 234; 982]
let g_log = "log.txt"
let wlog msg :unit Deferred.t =
Writer.with_file g_log
~f:(fun w -> Writer.write_line w msg; return ())
let seq_send url param : unit Deferred.t =
let uri = Uri.of_string (url^"?"^param) in
let%bind _, body = Cohttp_async.Client.get uri in
let%bind body = Body.to_string body in
wlog body
let ord_send lst =
List.iteri lst
~f:(fun idx ele ->
after (sec (float_of_int idx)) >>= fun () ->
(seq_send "http://127.0.0.1:9001/" (string_of_int ele)))
let () =
Command.async
~summary:"test"
Command.Spec.(
empty
)
(fun () -> ord_send mock_lst)
|> Command.run
I tried to compile and there’s an error
$ corebuild -pkg async,cohttp,cohttp.async osend.native
...
Error: This expression has type unit Conduit_async.io
but an expression was expected of type unit
...
The error code snippet:
after (sec (float_of_int idx)) >>= fun () ->
(seq_send "http://127.0.0.1:9001/" (string_of_int ele)))
I tried to debug by reading the type of each function:
# Async.after;;
- : Time.Span.t -> unit Conduit_async.io = <fun>
And
# Deferred.bind;;
- : 'a Conduit_async.io -> f:('a -> 'b Conduit_async.io) -> 'b Conduit_async.io = <fun>
My code after (sec (float_of_int idx))
has type unit Conduit_async.io
which should match the first parameter of Deferred.bind
.
The second parameter of Deferred.bind
would be f:('a -> 'b Conduit_async.io)
, my function is fun () -> (seq_send "http://127.0.0.1:9001/" (string_of_int ele)))
should be matched(unit -> unit Conduit_async.io
)
I was wondering what’s going on with my code?