In this tutorial, you will learn how to initialize an OCaml project that can be developed using dune
.
Initialize a new project
Section titled “Initialize a new project”Make
dune
executable available:Terminal window nix shell nixpkgs#dune_3Scaffold a new project using
dune
:Terminal window dune init proj 'package_name' 'your-new-project'Enter the project directory:
Terminal window cd 'your-new-project'
Add flake.nix to the project
Section titled “Add flake.nix to the project”Initialize the template from the root directory of the project:
Terminal window nix flake init github:akirak/flake-templates#ocaml-duneOpen
flake.nix
and set thepname
andversion
of the package to be built, e.g.:default = ocamlPackages.buildDunePackage {pname = throw "Name your OCaml package";pname = "hello";version = throw "Version your OCaml package";version = "0.1";duneVersion = "3";src = self.outPath;Add
.envrc
:Terminal window use flakeAllow direnv:
Terminal window direnv allow
Developing
Section titled “Developing”Once the Nix shell is enabled, you can use dune
inside the project directory, as you would do in a normal OCaml project.
Adding OCaml dependencies
Section titled “Adding OCaml dependencies”To add library dependencies to your OCaml project, follow this instruction. In this example, we will be adding cmdliner
as a new dependency.
Add the libraries to
propagatedBuildInputs
(orcheckInputs
if it's a test dependency) attribute to your package:default = ocamlPackages.buildDunePackage {...src = self.outPath;propagatedBuildInputs = with ocamlPackages; [basecorecore_unixcmdliner];};Add them to
depends
field of yourpackage
in thedune-project
file:(package(name hello)(allow_empty)(depends(ocaml (>= 4.08.0))(dune (>= 3.16))(cmdliner (>= 1.3.0))(alcotest :with-test)))Also add them to
libraries
field of a suitable stanza in the relevantdune
file.(library(public_name hello)(name hello)(libraries unix)(libraries unix cmdliner))
Adding OCaml dependencies for testing
Section titled “Adding OCaml dependencies for testing”To add dependencies for testing that are not required for production, follow this example. We will be adding alcotest
and qcheck
as test dependencies.
In
flake.nix
, setdoCheck
totrue
in the arguments tobuildDunePackage
:default = ocamlPackages.buildDunePackage {...doCheck = true;};Also in the arguments, add
checkInputs
field which should be a list of test-only dependencies:default = ocamlPackages.buildDunePackage {...doCheck = true;checkInputs = with ocamlPackages; [alcotestqcheck-core];};If your
dune-project
file contains one or morepackage
entries, add the dependencies todepends
field of relevant package. The dependencies should have:with-test
option:(package(name hello)(allow_empty)(depends(ocaml (>= 4.08.0))(dune (>= 3.16))(cmdliner (>= 1.3.0)); test-only dependency(alcotest :with-test); test-only dependency with a version constraint(qcheck-core (and :with-test (>= 0.19)))...))Also add the dependencies to the
dune
file for testing (typicallytest/dune
):(test(name test_hello)(librariesalcotestqcheck-core))
Generating documentation for the dependencies
Section titled “Generating documentation for the dependencies”To generate documentation of the dependencies, use odig
.
To generate a documentation, use a
justfile
recipe bundled in the template:Terminal window just odig-odocTo search through the documentation, you can run a local instance of sherlodoc or open a generated HTML file directly.
Running sherlodoc
Section titled “Running sherlodoc”To run sherlodoc, follow this instruction.
Enable
sherlodoc
in theflake.nix
:devShells = eachSystem ({ pkgs, ocamlPackages, ... }:{default = pkgs.mkShell {inputsFrom = [ self.packages.${pkgs.system}.default ];buildInputs = (with ocamlPackages;[ocaml-lspocamlformatocp-indent...# (sherlodoc.override { enableServe = true; })(sherlodoc.override { enableServe = true; })])# ++ lib.optional pkgs.stdenv.isLinux pkgs.inotify-tools;};});Run
sherlodoc index
on*.odocl
files. The template contains ajustfile
recipe, so you can just run:Terminal window just sherlodoc-indexTo browse the documentation, use a justfile recipe:
Terminal window just sherlodoc-serve
For a detailed description, consult the documentation of sherlodoc.