{"id":13680760,"url":"https://github.com/mirage/alcotest","last_synced_at":"2025-05-15T11:07:10.045Z","repository":{"id":12474500,"uuid":"15141922","full_name":"mirage/alcotest","owner":"mirage","description":"A lightweight and colourful test framework","archived":false,"fork":false,"pushed_at":"2025-03-18T00:56:36.000Z","size":3964,"stargazers_count":477,"open_issues_count":50,"forks_count":82,"subscribers_count":25,"default_branch":"main","last_synced_at":"2025-05-08T08:49:17.119Z","etag":null,"topics":["ocaml","unit-testing"],"latest_commit_sha":null,"homepage":null,"language":"OCaml","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"isc","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mirage.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGES.md","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2013-12-12T16:58:41.000Z","updated_at":"2025-05-03T12:08:39.000Z","dependencies_parsed_at":"2023-02-09T21:01:08.156Z","dependency_job_id":"995ef471-d61b-4320-8e53-f4ac50161a7b","html_url":"https://github.com/mirage/alcotest","commit_stats":{"total_commits":616,"total_committers":56,"mean_commits":11.0,"dds":0.6103896103896104,"last_synced_commit":"c9089302e22424cb5256af0088bf370e9c0244e9"},"previous_names":[],"tags_count":44,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirage%2Falcotest","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirage%2Falcotest/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirage%2Falcotest/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirage%2Falcotest/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mirage","download_url":"https://codeload.github.com/mirage/alcotest/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":254328384,"owners_count":22052632,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["ocaml","unit-testing"],"created_at":"2024-08-02T13:01:21.634Z","updated_at":"2025-05-15T11:07:09.995Z","avatar_url":"https://github.com/mirage.png","language":"OCaml","readme":"\u003cp align=\"center\"\u003e\u003cimg src=\"./.meta/alcotest-logo.png\"/\u003e\u003c/p\u003e\n\u003cp align=\"center\"\u003e\u003cb\u003eA lightweight and colourful test framework.\u003c/b\u003e\u003c/p\u003e\n\u003cbr/\u003e\n\nAlcotest exposes a simple interface to perform unit tests. It exposes\na simple `TESTABLE` module type, a `check` function to assert test\npredicates and a `run` function to perform a list of `unit -\u003e unit`\ntest callbacks.\n\nAlcotest provides a quiet and colorful output where only faulty runs\nare fully displayed at the end of the run (with the full logs ready to\ninspect), with a simple (yet expressive) query language to select the\ntests to run. See [the manpage](./alcotest-help.txt) for details.\n\nThe API documentation can be found [here][docs]. For information on\ncontributing to Alcotest, see [CONTRIBUTING.md](./CONTRIBUTING.md).\n\n[![OCaml-CI Build Status](https://img.shields.io/endpoint?url=https://ci.ocamllabs.io/badge/mirage/alcotest/main\u0026logo=ocaml)](https://ci.ocamllabs.io/github/mirage/alcotest)\n[![Alcotest Documentation](https://img.shields.io/badge/doc-online-blue.svg)][docs]\n\n[docs]: https://mirage.github.io/alcotest/alcotest/Alcotest/index.html\n\n\u003chr/\u003e\n\n### Examples\n\nA simple example (taken from `examples/simple.ml`):\n\n\u003cp align=\"center\"\u003e\u003cimg src=\"./.meta/ok.png\" width=\"65%\"\u003e\u003c/p\u003e\n\nGenerated by the following test suite specification:\n\n```ocaml\n(* Build with `ocamlbuild -pkg alcotest simple.byte` *)\n\n(* A module with functions to test *)\nmodule To_test = struct\n  let lowercase = String.lowercase_ascii\n  let capitalize = String.capitalize_ascii\n  let str_concat = String.concat \"\"\n  let list_concat = List.append\nend\n\n(* The tests *)\nlet test_lowercase () =\n  Alcotest.(check string) \"same string\" \"hello!\" (To_test.lowercase \"hELLO!\")\n\nlet test_capitalize () =\n  Alcotest.(check string) \"same string\" \"World.\" (To_test.capitalize \"world.\")\n\nlet test_str_concat () =\n  Alcotest.(check string) \"same string\" \"foobar\" (To_test.str_concat [\"foo\"; \"bar\"])\n\nlet test_list_concat () =\n  Alcotest.(check (list int)) \"same lists\" [1; 2; 3] (To_test.list_concat [1] [2; 3])\n\n(* Run it *)\nlet () =\n  let open Alcotest in\n  run \"Utils\" [\n      \"string-case\", [\n          test_case \"Lower case\"     `Quick test_lowercase;\n          test_case \"Capitalization\" `Quick test_capitalize;\n        ];\n      \"string-concat\", [ test_case \"String mashing\" `Quick test_str_concat  ];\n      \"list-concat\",   [ test_case \"List mashing\"   `Slow  test_list_concat ];\n    ]\n```\n\nThe result is a self-contained binary which displays the test\nresults. Use `dune exec examples/simple.exe -- --help` to see the\nruntime options.\n\nHere's an example of a of failing test suite:\n\n\u003cp align=\"center\"\u003e\u003cimg src=\"./.meta/error.png\" width=\"85%\"\u003e\u003c/p\u003e\n\nBy default, only the first failing test log is printed to the console\n(and all test logs are captured on disk). Pass `--show-errors` to\nprint all error messages.\n\n### Using Alcotest with opam and Dune\n\nAdd `(alcotest :with-test)` to the `depends` stanza of your\n`dune-project` file, or `\"alcotest\" {with-test}` to your opam file.\nUse the `with-test` [package variable][with-test] to declare your\ntests opam dependencies. Call opam to install them:\n\n```sh-session\n$ opam install --deps-only --with-test .\n```\n\nYou can then [declare your test][tests] and link with Alcotest: `(test\n(libraries alcotest …) …)`, and run your tests:\n\n```sh-session\n$ dune runtest\n```\n\n[with-test]: https://opam.ocaml.org/doc/Manual.html#pkgvar-with-test\n[tests]: https://dune.readthedocs.io/en/stable/tests.html#custom-tests\n\n### Selecting tests to execute\n\nYou can filter which tests to run by supplying a regular expression\nmatching the names of the tests to execute, or by passing a regular\nexpression _and_ a comma-separated list of test numbers (or ranges of\ntest numbers, e.g. `2,4..9`):\n\n```sh-session\n$ ./simple.native test '.*concat*'\nTesting Utils.\n[SKIP]     string-case            0   Lower case.\n[SKIP]     string-case            1   Capitalization.\n[OK]       string-concat          0   String mashing.\n[OK]       list-concat            0   List mashing.\nThe full test results are available in `_build/_tests`.\nTest Successful in 0.000s. 2 tests run.\n\n$ ./simple.native test 'string-case' '1..3'\nTesting Utils.\n[SKIP]     string-case            0   Lower case.\n[OK]       string-case            1   Capitalization.\n[SKIP]     string-concat          0   String mashing.\n[SKIP]     list-concat            0   List mashing.\nThe full test results are available in `_build/_tests`.\nTest Successful in 0.000s. 1 test run.\n```\n\nNote that you cannot filter by test case name (i.e. `Lower case` or\n`Capitalization`), you must filter by test name \u0026 number instead.\n\nSee the [examples][] directory for more examples.\n\n[examples]: https://github.com/mirage/alcotest/tree/main/examples\n\n### Quick and Slow tests\n\nIn general you should use `` `Quick`` tests: tests that are ran on any\ninvocations of the test suite. You should only use `` `Slow`` tests\nfor stress tests that are ran only on occasion (typically before a\nrelease or after a major change). These slow tests can be suppressed\nby passing the `-q` flag on the command line, e.g.:\n\n```sh-session\n$ ./test.exe -q # run only the quick tests\n$ ./test.exe    # run quick and slow tests\n```\n\n### Passing custom options to the tests\n\nIn most cases, the base tests are `unit -\u003e unit` functions. However,\nit is also possible to pass an extra option to all the test functions\nby using `'a -\u003e unit`, where `'a` is the type of the extra parameter.\n\nIn order to do this, you need to specify how this extra parameter is\nread on the command-line, by providing a [Cmdliner term][] for\ncommand-line arguments which explains how to parse and serialize\nvalues of type `'a` (*note:* do not use positional arguments, only\noptional arguments are supported).\n\n[Cmdliner term]: https://erratique.ch/software/cmdliner/doc/Cmdliner/Term/index.html\n\nFor instance:\n\n```ocaml\nlet test_nice i = Alcotest.(check int) \"Is it a nice integer?\" i 42\n\nlet int =\n  let doc = \"What is your preferred number?\" in\n  Cmdliner.Arg.(required \u0026 opt (some int) None \u0026 info [\"n\"] ~doc ~docv:\"NUM\")\n\nlet () =\n  Alcotest.run_with_args \"foo\" int [\n    \"all\", [\"nice\", `Quick, test_nice]\n  ]\n```\n\nWill generate `test.exe` such that:\n\n```sh-session\n$ test.exe test\ntest.exe: required option -n is missing\n\n$ test.exe test -n 42\nTesting foo.\n[OK]                all          0   int.\n```\n\n### Lwt\n\nAlcotest provides an `Alcotest_lwt` module that you could use to wrap\nLwt test cases. The basic idea is that instead of providing a test\nfunction in the form `unit -\u003e unit`, you provide one with the type\n`unit -\u003e unit Lwt.t` and alcotest-lwt calls `Lwt_main.run` for you.\n\nHowever, there are a couple of extra features:\n\n- If an async exception occurs, it will cancel your test case for you\n  and fail it (rather than exiting the process).\n\n- You get given a switch, which will be turned off when the test case\n  finishes (or fails). You can use that to free up any resources.\n\nFor instance:\n\n```ocaml\nlet free () = print_endline \"freeing all resources\"; Lwt.return ()\n\nlet test_lwt switch () =\n  Lwt_switch.add_hook (Some switch) free;\n  Lwt.async (fun () -\u003e failwith \"All is broken\");\n  Lwt_unix.sleep 10.\n\nlet () =\n  Lwt_main.run @@ Alcotest_lwt.run \"foo\" [\n    \"all\", [\n      Alcotest_lwt.test_case \"one\" `Quick test_lwt\n    ]\n  ]\n```\n\nWill generate:\n\n```sh-session\n$ test.exe\nTesting foo.\n[ERROR]             all          0   one.\n-- all.000 [one.] Failed --\nin _build/_tests/all.000.output:\nfreeing all resources\n[failure] All is broken\n```\n\n### Comparison with other testing frameworks\n\nThe README is pretty clear about that:\n\n\u003e Alcotest is a lightweight and colourful test framework.\n\nAlcotest is the only testing framework using colors!\n\nMore seriously, Alcotest is similar to [ounit][] but it fixes a few of\nthe problems found in that library:\n\n- Alcotest has a nicer output, it is easier to see what failed and\n  what succeeded and to read the log outputs of the failed tests;\n\n- Alcotest uses combinators to define pretty-printers and comparators\n  between the things to test.\n\nOther nice tools doing different kind of testing also exist:\n\n- [qcheck][] does random generation and property testing (e.g. Quick\n  Check);\n\n- [crowbar][] and [bun][] are similar to qcheck, but use\n  compiler-directed randomness, i.e. they take advantage of the AFL\n  support the OCaml compiler;\n\n- [ppx_inline_tests][] allows to write tests in the same file as\n  your source-code; they will be run only in a special mode of\n  compilation.\n\n[ounit]: https://github.com/gildor478/ounit\n[qcheck]: https://github.com/c-cube/qcheck\n[crowbar]: https://github.com/stedolan/crowbar\n[bun]: https://github.com/yomimono/ocaml-bun\n[ppx_inline_tests]: https://github.com/janestreet/ppx_inline_test\n","funding_links":[],"categories":["\u003ca name=\"OCaml\"\u003e\u003c/a\u003eOCaml","Libraries","Testing","OCaml"],"sub_categories":["Testing"],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmirage%2Falcotest","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmirage%2Falcotest","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmirage%2Falcotest/lists"}