- ReasonML file is translated to OCaml using
refmt
- OCaml files are compiled to Javascript using
bsc
. The-bs-files
flag takes care of dependency ordering. - Generated
.js
files are available to other rules as inputs for further processing (such as bundling or minification).
- ReasonML file is translated to OCaml using
refmt
- OCaml files are compiled using
ocamlc
- All
.cmo
,.cmt
, and.cmi
, as well as.ml
and.mli
files are then available for linking.
- ReasonML file is translated to OCaml using
refmt
- OCaml files are directly compiled using
ocamlc
orocamlopt
All dependencies will be handled as:
- A set of external repositories, declared through repository rules specified
by the
declare_dependencies
macro in a generated Skylark file - A generated tree of BUILD files that will compile and make the dependencies accessible to the current workspace rules
This macro will evaluate the repository rules needed to download and verify the sources of the dependencies will be created, so that declaring all of these packages has a clear interface.
The macro will live in a deps.bzl
file within the package manager
depdendencies folder:
3rdparty/${package_manager}/deps.bzl
And it will be defined as:
load("//reason:def.bzl", "${package_repository_rule}")
def deps():
return []
def declare_dependencies(rule=${package_repository_rule}):
for dep in deps():
rule(dep)
Where deps
will return a list of packages in a map accepted by the rule.
To declare packages at the WORKSPACE
level, we would use it like:
load("//3rdparty/${package_manager}:deps.bzl", "declare_dependencies")
declare_dependencies()
For each package manager, a subdirectory in 3rdparty/
will be created that
will have subdirectories for each one of the declared dependencies.
The directory structure will be defined by the following rules:
3rdparty/${package_manager}/BUILD
# for each declared dependency package
3rdparty/${package_manager}/${package_name}/BUILD
Each one of the packages BUILD
file will include the appropriate rules for
exposing a target of the same name that will output the desired artifact. Using
the same name for the Bazel target and the Bazel package allows us to omit it
when specifying dependencies and building it directly.
bazel build //3rdparty/${package_manager}/${package_name}
ocaml_native_binary(
# ...
deps = [
"//3rdparty/opam/cmdliner",
],
)
bs_module(
# ...
deps = [
"//3rdparty/node_modules/reason-future",
]
)
Packages in opam
are listed in a GitHub
repository
This repository has information about the packages under the following path:
${root_url}/tree/master/packages/${pkg}/${pkg}.${version}
Sample: cmdliner
And it contains for each one of them 3 files:
descr
, a plain-text description of the packageopam
, the opam package description file, which includes dependenciesurl
, a plain-text with an archive url and an md5 checksum
This repository rule should include:
pkg_name
, the name of the package as listed inopam
pkg_version
, the version of the packagearchive
, the exact url to download the contents of this packagesha256
, the sha256 that will be used to verify the contents of the packagedepends
, a list of labels that this package depends on
Upon downloading and verifying the archive
, this rule should create a build
file that will compile the OCaml sources, listing the required dependencies:
filegroup(
visibility = ["//visibility:public"],
name = "srcs",
srcs = glob(["**/*.ml", "**/*.mli"]),
)
Packages in redex
are listed in a GitHub repository
Packages in npm
are listed in their internal API:
https://api.npms.io/v2/package/${pkg_name}
Sample: reason-future
Upon calling the retool
binary, available through
bazel run @com_github_ostera_rules_reason//:retool -- sync
The tool will inspect the dependency files 3rdparty/package.json
and
3rdparty/package.opam
, and generate a directory structure based on the
dependencies as we saw defined above:
sample_project λ tree -C -L 9 3rdparty
3rdparty
├── BUILD
├── load.bzl
├── node_modules
│ ├── BUILD
│ ├── deps.bzl
│ └── reason-future
│ └── BUILD
├── opam
│ ├── BUILD
│ ├── cmdliner
│ │ └── BUILD
│ ├── deps.bzl
│ ├── httpaf
│ │ └── BUILD
│ └── result
│ └── BUILD
├── package.json
└── package.opam