BEAM Language Update Policy

I am unsure if this is the proper category to place this thread under. Anyone with the ability, please feel free to change it to something more fitting.

I submitted a PR today that ended up sparking conversation surrounding the update policy of BEAM based languages (Erlang, Elixir, etc).

So this is the start of that conversation. I would love to hear from anyone using any BEAM language what they believe the update policy should be for any of our languages. I would also love to hear from maintainers of other languages for how and when they decide to change the default version of their languages.

3 Likes

My opinion (having about a decade of experience in Elixir, led teams doing remediation on legacy Phoenix apps, being a maintainer on a few libraries, etc.) is that for own own sanity it’d probably make the most sense to just track latest packaged OTP, and then have a clear and documented way (probably in the manual, where it currently lives) for overriding for particular Elixir/OTP combinations.

According to the manual, we track Elixir minor releases going back 5 versions, but I don’t see any similar guarantee per se for Erlang OTP. OTP also has several different flavors depending on if you want X support, ODBC support, Java support for documentation or Java nodes, and so on and so forth–I’m honestly not sure that there is a sane way of supporting OTP without explicit recompilation for the intended platform. Who amongst us has not stubbed their toe at least once on being unable to use :observer because OTP was compiled without wxWidgets?

If I had to sum up the questions/issues I’ve run into in trying to use Nix for the past couple years with the beam ecosytem, they basically are:

  • Do I use a system Erlang/Elixir, a flake Erlang/Elixir, or something else?
  • At least with flakes, do I use a project/directory specific hex/mix folder or a shared one?
  • Which OTP should I be using with my Elixir? What supporting libs are needed to make that easy to work with?
  • What parts of this tower of babel are going to be cached with Nix versus needing local compilation?
  • Why doesn’t the nixpgs search show that there’s a richer story around beam support (via the beam subtree) versus the seeming “oh yeah just grab the elixir/erlang/whatever package and you’re all set!”?
  • Why doesn’t the wiki mention this at all, really, beyond hex2nix (under the Erlang section, hilariously enough) and nix-rebar3?

Anyways, it’s just sorta a big footgun.

4 Likes

Make erlang and elixir always point to their latest versions
If we look at the code at here, we can find:

  packages = {
    erlang = self.packages.${self.latestVersion};
    erlang_27 = self.packagesWith self.interpreters.erlang_27;

The lastest version is 27 in real world, but in the code, the latestVersion points to 25, There is a contradiction here. Making latestVersion always point to the latest version would resolve this contradiction.

If we use this convention for Erlang, then Elixir should follow the same convention as well.

Additionally:

  • from the perspective of the package manager, these names without version suffixes should point to the latest version.
  • Software is always iterating, and the Nixpkgs’ default settings should follow the pace of its iteration.

What should we do for those who want to stick with the old versions?
Currently, we have the ability to specify any combination of Erlang and Elixir, like:

  • pkgs.beam.packages.erlang_27.elixir_1_17
  • pkgs.beam.packages.erlang_26.elixir_1_15
  • …

So, this wouldn’t be a big issue.

2 Likes

I use Elixir for 7 years and Nix for the past year. I think not having the latest version on pkgs.erlang is very confusing. I have settled for this approach but in my opinion you should need something like this if you want to stay on some older version of Elixir for some legacy reasons. It should be easy to stay on the latest version.

beamPackages = pkgs.beam_minimal.packages.erlang_27;
erlang = beamPackages.erlang;
elixir = beamPackages.elixir_1_17;

One of my other painpoint is that you are not able to pass Elixir version to mixRelease - it will always use the “main” version set as latest by Nix. So I am not able to install elixir_ls with latest Elixir at all. I am able to pass latest Erlang like this, but not latest Elixir:

(elixir_ls.override {
  inherit (beamPackages) fetchMixDeps mixRelease;
  inherit elixir;
})

but the mixRelease is not aware of the version of Elixir I want to use

I also find it confusing to not have Elixir and Erlang default to the latest release. Having multiple releases is great, but the default should align with what the upstream maintainers want, which is to use the latest released version.

Seems like we’re getting some consensus around Elixir following latest release, then, if I’m reading correctly. Also, I think @Sgiath might have spotted something important too with the mixRelease thing.

I would vote for updating the latest versions of beam and elixir to the new version when it’s added. This change should only be applied to unstable/master though, probably as a separate commit. NixOS releases should always stay with the defaults they had at release, but backporting the new version is fine otherwise.

mixRelease should be overridable with a different elixir already afaict.

You are right, I have outdated info :slight_smile:

Since Elixir may have compatibility issues with latest Erlang, it looks like latest Elixir release should build on top of latest compatible Erlang version, not just latest Erlang version.

1 Like

Elixir will always be compatible with the latest stable Erlang version (latest, at the time of the Elixir release).

Applications built with Elixir may have specific Erlang/OTP version requirements, but that’s an application-specific concern. If I simply install Elixir from Nixpkgs, it would be preferable to get Elixir paired with the latest stable Erlang.

3 Likes