This post is part of a series of four, Gleam calling Erlang, and v.v., this post, Gleam calling JS, and v.v., and Gleam in the browser.
This post looks at combining Erlang and Gleam code in one rebar3 project, as well as using a gleam package (via hex) in a rebar3 project.It's the same Project; a shortcut
When you like Gleam for some parts of your project, but prefer or need Erlang for other parts, you can work with both the languages in one project, with a few tricks.
Let's continue with our happy project from the previous post.
We will put our erlang code in a separate place, by adjusting rebar.config
.
{src_dirs, [ "erlang" ]}.
we must also compile the files generated by gleam build
,
which are located in build/dev/erlang/happy/_gleam_artefacts/
.
Two problems:
- there are dependencies that we need,
-
there is a file
gleam@@compile.erl
for happy and each of the dependencies. It's an escript file that cannot be compiled, and which I hope will not be generated in the future (gleam should be able to compile without it?).
{src_dirs, [
"erlang",
{"build/dev/erlang", [{recursive, true}]}
]}.
{pre_hooks, [
{compile, "gleam build"},
{compile, "find build -name gleam@@compile.erl | xargs rm -f"}
]}.
when you run this, not much happens. That's because rebar3 needs an app definition (catches me every time).
Edit erlang/happy.app.src
to contain something like this (or better, call rebar3 new
, and get what you need from it):
{application, happy,
[{description, "Happy"},
{vsn, "0.1.0"},
{applications, [kernel, stdlib]}
]}.
and there we go!
$ rebar3 shell
===> Verifying dependencies...
Compiling happy
Compiled in 0.04s
===> Analyzing applications...
===> Compiling happy
Erlang/OTP 25 [erts-13.1.4] [source] [64-bit] [smp:8:8] [ds:8:8:10] [async-threads:1] [jit:ns]
Eshell V13.1.4 (abort with ^G)
1> happy:reverse_and_debug([atoms, only, today]).
[Today, Only, Atoms]
[today,only,atoms]
2>
Which means that code in the erlang source directory can also use our happy function.
[Edit Apr 5] rebar3 eunit
also runs the gleeunit
tests.
It's a proper Gleam library
Remove all rebar3 and erlang files from our happy project, so we're back at what we had at the start of this post.
For use by multiple Erlang projects, you should simplygleam publish
on hex.pm.
For that, you need the description and license set in gleam/toml
.
If you provide a repository, make sure it is an https url, hex does not accept a git url.
Any rebar3 project can now depend on the package:
{deps, [{happy, "0.1.0"}]}.
Running a local Hex repository
If you do not want to publish yet on hex.pm, or are not allowed to, you can run a local hex repository.Creating the tarball
Gleam v0.27.0 contains my Pull Request, so you cangleam export hex-tarball
. You can copy the resulting tarball from the build directory to the proper dir in your hex repo.
The command
mix hex.registry build public --name=local_hex --private-key=private_key.pem
will update the repository.
Configuring rebar
In the link above, it is specified how mix can reach your local hex repository, but not rebar3. You need to define the local repository like:{ hex, [
{ repos, [
#{name => <<"local_hex">>,
repo_url => <<"http://localhost:8080">>,
repo_public_key => <<"-----BEGIN RSA PUBLIC KEY-----
MIIBCgKCAQEAuNnBXDdcAy0piIE7LL4ley1OOynsQBSNmNFn58caa0YICnq0dzfi
18VLuXtcUBQfbiRiGVwHCO8dXy4VDmrsAq7SRYAHA0aGmgUA3fqORDC40yn4uLeu
2zPbgGGTdBDtlKurQNGudmCe2G4ZR5EakRfybFT3T49ACXxQb0e8IBbtcHizn0YA
y2y0doYCVIRtugOKXpe7+IXmoVJmjelyYDHU+9EwMXpak/8wncR4NfbRYrII
yhe57VByEyTSl20qSAs6tQK68h3rroaePUqAa5Jc9HylcTTWuEa0g3n8ninw
nkvgOv+wMM7FBN0Zxak58GN+KJwDg3AKzQIDAQAB
-----END RSA PUBLIC KEY-----
">>} ] }
]}.
and then rebar3 will look there, as well as at hex.pm for dependencies.
! rebar3 needs your local web server to use the 'etag' http header for the hex repo entries! Otherwise it'll send a malformed 'if-none-match' header, which cowboy(!) refuses with a 400 response.
! Be sure you trust such a local repo, as it will override what is on hex.pm.
The round trip from Gleam to Erlang is unwieldy in early versions of a package when your API is still unstable. It should not be so bad when your API reaches 1.0 and will mostly be extended, not changed.
Enjoy!