Part 5 · 1 chapters · ~8 min

Tooling and Testing

mix and project structure, Hex dependencies, ExUnit with async tests and tags, doctests, the Ecto SQL sandbox, Mox and behaviours, property-based testing with StreamData, testing processes and supervision, mix format, Credo, Dialyzer and the built-in type checker, and CI.

6

Tests that run in parallel

code
defmodule Ledger.TransferTest do
  use Ledger.DataCase, async: true            # own sandboxed transaction per test

  test "100 identical requests create one transfer" do
    key = Ecto.UUID.generate()
    results = 1..100 |> Task.async_stream(fn _ -> Ledger.create_transfer(params(), key) end, max_concurrency: 100) |> Enum.map(fn {:ok, r} -> r end)
    assert results |> Enum.map(fn {:ok, t} -> t.id end) |> Enum.uniq() |> length() == 1
  end

  property "postings always sum to zero" do
    check all amount <- positive_integer(), fee <- integer(0..5_000) do
      assert Ledger.postings_for(amount, fee) |> Enum.map(& &1.amount) |> Enum.sum() == 0
    end
  end
end

Mox.defmock(Rails.Mock, for: Rails.Behaviour)          # mocks only for behaviours
TOOLING AND TESTING
the mix toolbox
mixBuild tool: new projects, deps,compile, tasks, releases.HexThe package manager; mix deps.get.ExUnitBuilt-in tests, async: true runsmodules in parallel.Ecto SQL sandboxEach test in a transaction rolledback: parallel DB tests.MoxMocks only for behaviours youdefine: explicit contracts.format, Credo, Dialyzermix format, static analysis, typechecks in CI.
swipe the figure sideways, or tap expand for full screen
1/4
one tool
mix creates, compiles, tests and releases projects; Hex hosts packages.
mix + Hexone consistent toolbox