package lwt

  1. Overview
  2. Docs
Promises, concurrency, and parallelized I/O

Install

Dune Dependency

Authors

Maintainers

Sources

3.2.0.tar.gz
sha256=24ce70284eb229df2588ea1cd4eb27f774475402f9d3c5a5a5781485c6140b23
md5=cf4256845e18c4d0f39afa7b32b3d6fe

Description

A promise is a value that may become determined in the future.

Lwt provides typed, composable promises. Promises that are resolved by I/O are resolved by Lwt in parallel.

Meanwhile, OCaml code, including code creating and waiting on promises, runs in a single thread by default. This reduces the need for locks or other synchronization primitives. Code can be run in parallel on an opt-in basis.

Published: 24 Dec 2017

README

Lwt   

Lwt is OCaml's concurrent programming library. It provides a single data type: the promise, which is a value that will become determined in the future. Creating a promise spawns a computation. When that computation is I/O, Lwt runs it in parallel with your OCaml code.

OCaml code, including creating and waiting on promises, is run in a single thread by default, so you don't have to worry about locking or preemption. You can detach code to be run in separate threads on an opt-in basis.

Here is a simplistic Lwt program which requests the Google front page, and fails if the request is not completed in five seconds:

let () =
  let request =
    let%lwt addresses = Lwt_unix.getaddrinfo "google.com" "80" [] in
    let google = Lwt_unix.((List.hd addresses).ai_addr) in

    Lwt_io.(with_connection google (fun (incoming, outgoing) ->
      let%lwt () = write outgoing "GET / HTTP/1.1\r\n" in
      let%lwt () = write outgoing "Connection: close\r\n\r\n" in
      let%lwt response = read incoming in
      Lwt.return (Some response)))
  in

  let timeout =
    let%lwt () = Lwt_unix.sleep 5. in
    Lwt.return None
  in

  match Lwt_main.run (Lwt.pick [request; timeout]) with
  | Some response -> print_string response
  | None -> prerr_endline "Request timed out"; exit 1

(* ocamlfind opt -package lwt.unix -package lwt.ppx -linkpkg -o request example.ml
   ./request *)

In the program, functions such as Lwt_io.write create promises. The let%lwt ... in construct is used to wait for a promise to become determined; the code after in is scheduled to run in a "callback." Lwt.pick races promises against each other, and behaves as the first one to complete. Lwt_main.run forces the whole promise-computation network to be executed. All the visible OCaml code is run in a single thread, but Lwt internally uses a combination of worker threads and non-blocking file descriptors to resolve in parallel the promises that do I/O.


Overview

Lwt compiles to native code on Linux, macOS, Windows, and other systems. It's also routinely compiled to JavaScript for the front end and Node, by js_of_ocaml and BuckleScript.

In Lwt,

  • The core library Lwt provides promises...

  • ...and a few pure-OCaml helpers, such as promise-friendly mutexes, condition variables, and mvars.

  • There is a big Unix binding, Lwt_unix that binds almost every Unix system call. A higher-level module Lwt_io provides nice I/O channels.

  • Lwt_process is for subprocess handling.

  • Lwt_preemptive spawns system threads.

  • The PPX syntax allows using all of the above without going crazy!

  • There are also some other helpers, such as Lwt_react for reactive programming, and Lwt_ssl for SSL sockets. See the table of contents on the linked manual pages!


Installing

  1. Use your system package manager to install a development libev package. It is often called libev-dev or libev-devel.

  2. opam install conf-libev lwt


Documentation

We are currently working on improving the Lwt documentation (drastically; we are rewriting the manual). In the meantime:

  • The current manual can be found here.

  • Mirage has a nicely-written Lwt tutorial.

  • An example of a simple server written in Lwt.

  • Concurrent Programming with Lwt is a nice source of Lwt examples. They are translations of code from the excellent Real World OCaml, but are just as useful if you are not reading the book.

  • Some examples are also available in Lwt's doc/examples.

Note: much of the current manual refers to 'a Lwt.t as "lightweight threads" or just "threads." This will be fixed in the new manual. 'a Lwt.t is a promise, and has nothing to do with system or preemptive threads.


Contact

Open an issue, visit Gitter chat, ask in #ocaml, on discuss.ocaml.org, or on Stack Overflow. Please do ask! Even apparently simple questions often end up educating other users, not to mention enlightening the maintainers!

Subscribe to the announcements issue to get news about Lwt releases. It is less noisy than watching the whole repository. Announcements are also made in /r/ocaml, on the OCaml mailing list, and on discuss.ocaml.org.


Contributing

  • We maintain easy starter issues. These are thoroughly explained and hyperlinked. We hope that this makes working on Lwt accessible even to relative OCaml beginners :)

  • CONTRIBUTING.md contains tips for working on the code, such as how to check the code out, how review works, etc. There is also a high-level outline of the code base.

  • The overall development plan can be found in the roadmap.

  • Ask us anything, whether it's about working on Lwt, or any question at all about it :)

  • The documentation always needs proofreading and fixes.

  • Despite a lot of progress, Lwt still needs more tests.

  • You are welcome to pick up any other issue, review a PR, add your opinion, etc.

  • Any feedback is welcome, including how to make contributing easier!


License

Lwt is released under the LGPL, with an OpenSSL linking exception. See COPYING.

Dependencies (7)

  1. result
  2. ppx_tools_versioned >= "5.0.1"
  3. ocaml-migrate-parsetree < "2.0.0"
  4. ocamlfind build & >= "1.7.3-1"
  5. jbuilder >= "1.0+beta14"
  6. cppo build & >= "1.1.0"
  7. ocaml >= "4.02.0" & < "4.08.0"

Dev Dependencies

None

  1. 0install >= "2.14"
  2. albatross
  3. alcotest-lwt
  4. alcotest-mirage
  5. ambient-context-lwt
  6. amqp-client >= "0.9.0" & < "1.0.2" | >= "1.1.0"
  7. amqp-client-lwt
  8. angstrom-lwt-unix
  9. anthill
  10. anycache-lwt
  11. arakoon < "1.8.6" | >= "1.8.8"
  12. archi-lwt
  13. arp >= "2.3.1"
  14. arp-mirage
  15. awa-lwt
  16. awa-mirage < "0.2.0"
  17. aws < "1.0.0"
  18. aws-s3-lwt
  19. awsm-lwt
  20. azure-cosmos-db
  21. baardskeerder
  22. balancer
  23. bap < "1.0.0"
  24. bap-server < "0.3.0"
  25. bimage-lwt
  26. biocaml = "0.4.0"
  27. bistro
  28. brotli < "1.2.0"
  29. brozip
  30. builder
  31. bun >= "0.3.3"
  32. c3
  33. calculon
  34. camltc
  35. canary
  36. capnp-rpc-lwt < "1.2.3"
  37. capnp-rpc-unix >= "0.9.0" & < "1.2.3"
  38. caqti-lwt < "2.0.1"
  39. carton-git < "0.7.2"
  40. carton-lwt
  41. cf-lwt
  42. channel
  43. charrua-client-lwt < "1.2.0"
  44. charrua-client-mirage < "1.2.0"
  45. charrua-core < "0.3"
  46. charrua-unix >= "0.3" & < "0.11.0" | >= "0.11.2"
  47. cmdtui-lambda-term
  48. coclobas
  49. cohttp-lwt < "6.0.0~alpha2"
  50. cohttp-lwt-jsoo
  51. cohttp-lwt-unix
  52. cohttp-lwt-unix-nossl
  53. cohttp-lwt-unix-ssl
  54. cohttp-mirage
  55. comby
  56. comby-semantic
  57. conan-lwt
  58. conduit-lwt < "7.0.0"
  59. conduit-lwt-unix < "7.0.0"
  60. core-lwt = "0.2.0"
  61. cowabloga >= "0.2.2"
  62. crunch >= "2.0.0"
  63. cstruct-lwt
  64. csv-lwt
  65. csvprovider
  66. ctypes >= "0.6.0" & < "0.21.1"
  67. ctypes-foreign >= "0.21.1"
  68. curly < "0.2.0"
  69. current_docker < "0.6.4"
  70. current_examples < "0.6.4"
  71. current_git < "0.6.4"
  72. current_github < "0.6.4"
  73. current_gitlab < "0.6.4"
  74. current_ocluster < "0.2"
  75. current_slack < "0.6.4"
  76. current_web < "0.6.4"
  77. DkSDKFFIOCaml_Std
  78. dap
  79. data-encoding < "0.1.1"
  80. datakit
  81. datakit-bridge-github
  82. datakit-bridge-local-git
  83. datakit-ci
  84. datakit-client >= "0.11.0"
  85. datakit-github
  86. datakit-server
  87. devkit
  88. dht < "0.2.0"
  89. distributed = "0.4.0"
  90. distributed-lwt
  91. dkim-mirage
  92. dns >= "0.19.1" & < "1.0.0"
  93. dns-forward >= "0.9.0"
  94. dns-forward-lwt-unix
  95. dns-lwt
  96. dnssd
  97. docker_hub
  98. dream
  99. dream-httpaf
  100. dream-pure
  101. dropbox
  102. dune_watch
  103. earlybird < "1.0.0"
  104. elasticsearch-cli
  105. eliom = "6.3.0"
  106. eris-lwt
  107. ethernet
  108. ezcurl-lwt
  109. ezirmin
  110. ezjsonm >= "0.4.2" & < "0.5.0"
  111. ezjsonm-lwt
  112. ezresto
  113. ezresto-directory
  114. faraday-lwt
  115. faraday-lwt-unix
  116. fat-filesystem >= "0.12.0"
  117. fiber-lwt
  118. flowtype >= "0.62.0" & < "0.72.0"
  119. frenetic < "2.0.0"
  120. fswatch_lwt
  121. fuseau-lwt
  122. gamepad
  123. gdb
  124. gdbprofiler
  125. git != "1.4.3" & != "1.7.2"
  126. git-paf
  127. git-unix = "1.11.1" | >= "3.0.0" & < "3.10.0"
  128. github
  129. github-hooks
  130. github-unix >= "4.4.0"
  131. gitlab-unix
  132. gluten-lwt < "0.4.0"
  133. gluten-lwt-unix < "0.4.0"
  134. gluten-mirage < "0.4.0"
  135. graphql-lwt
  136. gufo
  137. h1
  138. h1-lwt-unix
  139. h2-lwt < "0.10.0"
  140. h2-lwt-unix < "0.10.0"
  141. h2-mirage
  142. happy-eyeballs-lwt
  143. happy-eyeballs-mirage
  144. hardcaml < "1.1.0"
  145. hardcaml-examples >= "0.3.0"
  146. hardcaml-framework
  147. hardcaml-waveterm
  148. hiredis < "0.6"
  149. hl_yaml
  150. horned_worm < "0.3.1"
  151. http-lwt-client
  152. http-multipart-formdata >= "2.0.0" & < "3.0.0"
  153. http2https
  154. httpaf-lwt-unix
  155. httpun-lwt
  156. httpun-mirage
  157. httpun-ws-lwt
  158. hvsock
  159. i3ipc
  160. imaplet-lwt
  161. influxdb-lwt
  162. inotify >= "2.4"
  163. inquire < "0.3.0"
  164. iocaml < "0.4.6"
  165. iocaml-kernel >= "0.4.3"
  166. iocamljs-kernel
  167. ip2location
  168. ip2locationio
  169. ip2whois
  170. ipv6-multicast < "0.9"
  171. ipv6-multicast-lwt
  172. irc-client-lwt
  173. irc-client-lwt-ssl
  174. irc-client-tls
  175. irmin < "0.9.6" | = "0.9.10" | >= "0.11.0" & < "2.7.0"
  176. irmin-bench < "2.7.0"
  177. irmin-chunk < "2.7.0"
  178. irmin-containers < "2.7.0"
  179. irmin-fs >= "2.3.0" & < "2.7.0"
  180. irmin-git >= "2.3.0" & < "2.7.0"
  181. irmin-graphql >= "2.3.0" & < "2.7.0"
  182. irmin-http >= "2.3.0" & < "2.7.0"
  183. irmin-indexeddb
  184. irmin-layers < "2.7.0"
  185. irmin-mem >= "2.3.0"
  186. irmin-mirage-git >= "2.3.0" & < "2.7.0"
  187. irmin-mirage-graphql >= "2.3.0" & < "2.7.0"
  188. irmin-pack < "2.7.0"
  189. irmin-test >= "2.3.0" & < "2.7.0"
  190. irmin-unix >= "2.3.0" & < "2.7.0"
  191. irmin-watcher
  192. jitsu
  193. joolog
  194. jose < "0.9.0"
  195. js_of_ocaml < "3.0"
  196. js_of_ocaml-lwt
  197. jsoo_broadcastchannel
  198. jsoo_router
  199. jsoo_storage
  200. jupyter < "2.3.0"
  201. jupyter-archimedes < "2.3.2"
  202. jupyter-kernel
  203. KaSim >= "4.0.0"
  204. kafka >= "0.3" & < "0.5"
  205. kafka_lwt
  206. ke >= "0.5"
  207. ketrew >= "3.2.0"
  208. kinetic-client != "0.0.9"
  209. lablqml < "0.6"
  210. lambda-runtime
  211. lambda-term >= "1.11" & < "1.13"
  212. launchd
  213. learn-ocaml < "0.13.0"
  214. learn-ocaml-client < "0.13.0"
  215. letsencrypt
  216. letsencrypt-app
  217. letsencrypt-dns
  218. libres3
  219. links < "0.9.5"
  220. lru_cache < "v0.16.0"
  221. lwt-binio
  222. lwt-canceler
  223. lwt-dllist
  224. lwt-exit
  225. lwt-parallel >= "0.1.2"
  226. lwt-pipe
  227. lwt-pipeline
  228. lwt-watcher
  229. lwt-zmq
  230. lwt_camlp4
  231. lwt_domain < "0.3.0"
  232. lwt_eio < "0.4"
  233. lwt_glib >= "1.0.1"
  234. lwt_log < "1.1.0"
  235. lwt_named_threads
  236. lwt_ppx
  237. lwt_ppx_let
  238. lwt_react >= "1.0.1"
  239. lwt_ssl >= "1.0.1"
  240. macaque_lwt
  241. maki
  242. mariadb < "0.5.1"
  243. markup = "0.7.6"
  244. markup-lwt
  245. mdx
  246. mechaml
  247. metrics-influx
  248. metrics-lwt
  249. metrics-mirage
  250. metrics-unix
  251. mindstorm-lwt
  252. mirage < "0.9.1" | >= "0.10.0" & < "2.7.0"
  253. mirage-block < "1.0.0"
  254. mirage-block-ccm
  255. mirage-block-lwt
  256. mirage-block-ramdisk
  257. mirage-block-solo5
  258. mirage-block-unix < "2.8.3"
  259. mirage-block-xen
  260. mirage-bootvar-solo5 >= "0.2.0"
  261. mirage-bootvar-unix
  262. mirage-bootvar-xen >= "0.4.0"
  263. mirage-channel-lwt
  264. mirage-clock-freestanding < "3.0.0"
  265. mirage-clock-lwt
  266. mirage-clock-unix >= "1.2.0" & < "3.0.0"
  267. mirage-console >= "2.1.1" & < "2.2.0"
  268. mirage-console-lwt
  269. mirage-console-solo5 >= "0.2.0"
  270. mirage-console-unix >= "2.2.0" & < "3.0.0"
  271. mirage-console-xen >= "5.0.0"
  272. mirage-console-xen-backend < "3.0.1"
  273. mirage-console-xen-cli
  274. mirage-dns < "3.0.0"
  275. mirage-entropy < "0.5.0"
  276. mirage-entropy-xen < "0.2.0"
  277. mirage-flow >= "1.0.3" & < "1.2.0"
  278. mirage-flow-lwt
  279. mirage-flow-rawlink
  280. mirage-flow-unix < "2.0.0"
  281. mirage-fs-lwt
  282. mirage-fs-unix != "1.2.1"
  283. mirage-http
  284. mirage-http-unix
  285. mirage-http-xen
  286. mirage-kv-lwt
  287. mirage-kv-unix < "3.0.0"
  288. mirage-logs
  289. mirage-nat < "3.0.0"
  290. mirage-net-fd
  291. mirage-net-lwt
  292. mirage-net-macosx
  293. mirage-net-solo5
  294. mirage-net-unix
  295. mirage-net-xen
  296. mirage-os-shim >= "3.0.0"
  297. mirage-profile
  298. mirage-protocols-lwt
  299. mirage-qubes < "0.9.4"
  300. mirage-qubes-ipv4 < "0.9.4"
  301. mirage-random-stdlib >= "0.1.0"
  302. mirage-solo5
  303. mirage-stack-lwt
  304. mirage-time-lwt
  305. mirage-time-unix < "2.0.0"
  306. mirage-types-lwt < "3.7.1"
  307. mirage-unix
  308. mirage-vnetif
  309. mirage-vnetif-stack
  310. mirage-www >= "1.1.0"
  311. mirage-xen
  312. mirror
  313. moonpool-lwt
  314. mpris = "0.1.1"
  315. mqtt = "0.0.2"
  316. mrmime >= "0.5.0"
  317. multipart-form-data
  318. multipart_form >= "0.2.0" & < "0.4.0"
  319. multipart_form-lwt < "0.6.0"
  320. mwt
  321. named-pipe
  322. nanomsg
  323. nbd = "2.1.1" | >= "3.0.0"
  324. nbd-tool
  325. nbd-unix
  326. netchannel
  327. nocrypto >= "0.5.4"
  328. noise
  329. nottui-lwt
  330. nproc
  331. nsq
  332. obrowser
  333. obuilder < "0.4"
  334. obus >= "1.1.8" & < "1.2.1"
  335. ocaml-variants >= "4.00.1+mirage-unix" & < "4.00.1+open-types"
  336. ocluster < "0.2"
  337. ocluster-api < "0.2"
  338. ocplib-concur
  339. ocplib-resto
  340. ocsigen-start = "1.1.0" | >= "4.1.0" & < "4.7.0"
  341. ocsigen-toolkit = "1.1.0"
  342. ocsigenserver >= "2.9"
  343. odoc >= "2.0.0" & < "2.1.0"
  344. ojquery
  345. ojs-base < "0.6.0"
  346. opam-compiler < "0.2.0"
  347. opam-publish = "0.3.5"
  348. opam-sync-github-prs
  349. openflow < "0.2.0"
  350. opium >= "0.11.0" & < "0.19.0"
  351. opium_kernel
  352. order-i3-xfce
  353. ordma
  354. osc-lwt
  355. oskel >= "0.3.0"
  356. otetris
  357. ounit-lwt < "2.2.0"
  358. ounit2-lwt
  359. ox < "1.1.0"
  360. paf
  361. paf-cohttp
  362. passage
  363. pcap-format >= "0.3.3" & < "0.5.0"
  364. pgx_lwt
  365. pgx_lwt_mirage
  366. pgx_lwt_unix < "2.0"
  367. plotkicadsch
  368. ppx_defer >= "0.4.0"
  369. ppx_deriving_rpc
  370. ppx_json_types
  371. ppx_netblob
  372. ppx_rapper_lwt
  373. ppx_sqlexpr
  374. prof_spacetime
  375. prometheus
  376. prometheus-app
  377. promise_jsoo_lwt
  378. protocol-9p >= "0.10.0"
  379. protocol-9p-unix
  380. pvem_lwt_unix >= "0.0.2"
  381. qcow < "0.11.0"
  382. qcow-format
  383. qcow-tool
  384. qfs >= "0.5" & < "0.7"
  385. quests
  386. rawlink < "2.1"
  387. rawlink-lwt
  388. redis-lwt
  389. resource-pooling
  390. resp >= "0.10.0"
  391. resp-mirage >= "0.10.0"
  392. resp-unix >= "0.10.0"
  393. resto
  394. resto-cohttp-client
  395. resto-cohttp-self-serving-client
  396. resto-cohttp-server
  397. resto-directory
  398. riak
  399. ringo-lwt
  400. river
  401. rpc >= "1.5.1" & < "7.1.0"
  402. rpclib-js
  403. rpclib-lwt
  404. sanddb >= "0.3.0"
  405. scgi
  406. sendmail-lwt
  407. session-cohttp-lwt
  408. session-cookie-lwt
  409. session-postgresql-lwt
  410. sessions
  411. shared-block-ring
  412. shared-memory-ring < "2.0.0"
  413. shared-memory-ring-lwt
  414. skkserv-lite
  415. slacko
  416. slipshow
  417. socket-daemon
  418. speed
  419. spin < "0.6.0"
  420. spotify-web-api < "0.2.1"
  421. sqlexpr
  422. statsd-client
  423. stog >= "0.16.0" & < "0.19.0"
  424. syndic >= "1.4" & < "1.6.0"
  425. tar-format >= "0.4.1"
  426. tar-mirage < "2.2.0"
  427. tar-unix < "3.0.0"
  428. tcpip >= "3.1.1" & < "4.0.0"
  429. telegraml
  430. testrunner
  431. tezos-p2p >= "11.0" & < "13.0"
  432. tezos-stdlib < "9.0"
  433. tezos-stdlib-unix < "9.0"
  434. tftp
  435. themoviedb
  436. tls >= "0.10.1" & < "0.16.0"
  437. tls-lwt < "0.17.4"
  438. tls-mirage
  439. tlstunnel >= "0.2.0"
  440. transmission-rpc
  441. tube
  442. tuntap >= "1.0.0" & < "2.0.0"
  443. twirp_cohttp_lwt_unix
  444. typerex-lldb
  445. u2f
  446. usb
  447. uspf
  448. uspf-lwt
  449. utop >= "1.4.0"
  450. uwt >= "0.0.2"
  451. vchan >= "0.9.6" & < "2.0.0" | >= "2.0.3"
  452. vchan-unix
  453. vchan-xen
  454. vercel
  455. vhd-format >= "0.6.0" & < "0.9.1"
  456. vhd-format-lwt >= "0.12.0"
  457. vhd-tool < "0.12.0"
  458. vmnet
  459. vpnkit >= "0.1.1"
  460. vue-jsoo < "0.3"
  461. webauthn
  462. websocket < "2.3"
  463. websocket-lwt = "2.11"
  464. xe-unikernel-upload
  465. xen-api-client < "0.9.14"
  466. xen-block-driver
  467. xen-evtchn
  468. xen-evtchn-unix
  469. xen-gnt
  470. xen-gnt-unix >= "4.0.2"
  471. xenctrl
  472. xenstore
  473. xenstore_transport
  474. xentropyd
  475. yurt != "0.3" & < "0.5"
  476. zarr-lwt
  477. zbar
  478. zmq-lwt

Conflicts (2)

  1. dune >= "1.7.0"
  2. ocaml-variants = "4.02.1+BER"
OCaml

Innovation. Community. Security.