585 words, 3 min read

If you've recently run mix compile on an Elixir project that uses precompiled NIFs, such as mdex or lumis, you may have seen an error like this:

[info] Attempt 1 failed with {:error, "couldn't fetch NIF from https://github.com/...: {:error, {:header_too_long, {:max, 10240}}}"}

== Compilation error in file lib/mdex_native/native.ex ==
** (RuntimeError) Error while downloading precompiled NIF: couldn't fetch NIF from https://github.com/...

This is frustrating because mix deps.get succeeds. The problem only appears during compilation.

What's Going On?

Elixir libraries that include native code (Rust, C, etc.) often ship precompiled binaries called NIFs (Native Implemented Functions), so you don't need a native toolchain to use them. The library rustler_precompiled handles downloading the right binary for your platform at compile time.

Under the hood, rustler_precompiled uses Mint, an Elixir HTTP client, to fetch NIF archives from GitHub Releases.

Here's the problem: GitHub's CDN now returns very large response headers on release asset redirect requests—headers that exceed Mint's default maximum of 10,240 bytes (10 KB). When Mint hits that cap, it aborts the request with {:header_too_long, {:max, 10240}}, and compilation fails.

This isn't a bug in your code. It's an upstream issue involving GitHub's infrastructure and Mint's conservative defaults.

Three Ways to Fix It

Option 1 — Download the NIF Manually with curl (Fastest)

curl doesn't have the same header size restriction. You can download the NIF archive directly and let rustler_precompiled pick it up from its cache on the next compile.

First, find the download URLs in the error message in your terminal, then fetch the archive:

curl -L -o /tmp/your_nif.tar.gz "https://github.com/.../your_nif.tar.gz"

rustler_precompiled caches NIFs in ~/.cache/rustler_precompiled/ (Linux/macOS). Copy the downloaded archive there, then rerun mix compile.

Option 2 — Update the Dependency

The maintainers of these libraries are aware of the issue. A newer release may have switched away from Mint for the download step or increased Mint's header limit. Try:

mix deps.update your_nif_package
mix compile

This is the cleanest long-term fix if a patched version is available.

Option 3 — Force Build from Source

If you have the Rust toolchain installed, you can tell rustler_precompiled to compile the NIF locally instead of downloading it.

Add this to config/dev.exs (or config/config.exs):

config :rustler_precompiled, :force_build, your_nif_package: true

And add Rustler as an optional dependency in mix.exs:

{:rustler, ">= 0.0.0", optional: true}

Then run mix deps.get && mix compile. Compilation will take longer because it builds native code, but it will work regardless of GitHub's header behavior.

Which Should You Choose?

Situation Recommended fix
Just need to unblock right now Option 1 (manual curl)
A patched release is available Option 2 (update deps)
You control the environment and have Rust Option 3 (force build)
CI/CD pipeline is broken Option 1 or 3, depending on whether Rust is available

The Broader Lesson

This failure mode—a third-party infrastructure change silently breaking your build—is a good reminder to:

  • Pin your NIF dependency versions so you're not surprised by new behavior after an update.
  • Cache precompiled NIFs in CI so you're not downloading them on every build.
  • Have a fallback strategy (force build) for environments where downloading isn't reliable.

Precompiled NIFs are a major convenience for Elixir developers who don't want to manage native toolchains. But they introduce a network dependency at compile time, and as this issue shows, that dependency can break in unexpected ways.

The Proper Fix

The poeple behind rustler_precompiled are working on a proper fix. You can follow the progress with this pull request.