jarlah
Testcontainers - A Testcontainers implementation for Elixir
Testcontainers
Testcontainers is an Elixir library that supports ExUnit tests, providing lightweight, throwaway instances of common databases, or anything else that can run in a Docker container.
It supports Testcontainers Desktop, but doesn’t need it to run. It will find and pick up a docker engine that works every time it runs.
Let me show you its features
In its basic form Testcontainers can used like this:
{:ok, _} = Testcontainers.start_link()
config = %Testcontainers.Container{image: "redis:latest"}
{:ok, container} = Testcontainers.start_container(config)
But the most interesting usage for Elixir is the Ecto module, which lets you run tests without having a postgres (or mysql) container running (see the README section for this advanced usage).
You can also spin up a throwaway container in a single ExUnit test:
container(:redis, Testcontainers.RedisContainer.new())
or shared container for multiple tests
container(:redis, Testcontainers.RedisContainer.new(), shared: true)
How it works
It has a dependency on an autogenerated elixir library for the docker engine api. The complex logic for calling out to docker is hidden inside that library.
Most Liked
jarlah
Proud to announce v1.8.0 which brings support for two new technologies, RabbitMq and Emqx.
There are a lot of new contributors in this release and this is really encouraging.
Key features that has been implemented is private registry support and proper user agent is sent to docker engine api.
![]()
jarlah
a friendly and helpful github user that previously reported podman not working, got back to me and told me that it was still not working after the release. Well i brought in the big guns, virtualbox, and installed ubuntu 24 and podman and started podman.socket service in user mode. Confirmed the issue, fixed the bug and released v1.11.5
Thanks to github user kianmeng for this helpful testing.
jarlah
jarlah
A couple of bugfixes later I can now testify that the testcontainers library is actually usable now. With the introduction of the mix task and its reuse and watch functionality, i can attest for its usefulness.
If you are using it already, do a mix deps.update testcontainers and it will update the patch version. If not, adding it to deps with {:testcontainers, "~> 1.10", only: [:dev, :test], runtime: false} and running mix deps.get will get you up and running. Dont need to add anything in the test_helper.exs.
To use the testcontainers.test task you will need to adjust the config/test.exs so it reads db environment variables. From the readme, it can look like this:
config :my_app, MyApp.Repo,
username: System.get_env("DB_USER") || "postgres",
password: System.get_env("DB_PASSWORD") || "postgres",
hostname: System.get_env("DB_HOST") || "localhost",
port: System.get_env("DB_PORT") || "5432",
database: "my_app_test#{System.get_env("MIX_TEST_PARTITION")}",
pool: Ecto.Adapters.SQL.Sandbox,
pool_size: System.schedulers_online() * 2
If you want to reuse the database container, add testcontainers.reuse.enable=true in ~/.testcontainers.properties.
Now you can run
mix testcontainers.test
It doesnt look as pretty as normal test runs, because it streams output from a System.cmd call to stdout, but its better than having to struggle with mix test.watch which have many unresolved issues. At least for me.
If you want to watch files for changes and rerun the tests when changed, run this instead:
mix testcontainers.test --watch lib --watch test
Its not a very complicated task, so if you cancel before the test run completes, it will run in the background as a separate os process. If you rerun the command above before its complete, and if you have reuse enabled in properties, you might encounter many fun issues.
I usually have another terminal open where i monitor docker:
watch docker ps
Any feedback on the mix task and the watching functionality would be wonderful
<3
jarlah
Big news
Testcontainers for Elixir now has (rootless) podman support
Read more here
I have had this nugget of a problem on my desk for quite some time now and its quite funny how easy it was to fix. The major problem was that I am not using podman myself. So had to test at work where they are using podman. And i have also added a github workflow to verify that everything works for both normal docker and podman.
Im very psyched about this because it opens for many more (security oriented) developers to start using the library ![]()
Try it out and see how/if it works for you.







