Test fails at unexpected line

Maybe there’s something obvious, but I was expecting this test to fail on the first line, because the module doesn’t exist, but instead it fails at the assertion. Note that if the assertion is removed or it passes, then the expected error is raised.

test "why?" do
  DoNotExists.foo do
    assert 1 + 1 == 3
  end
end

Maybe for the same reason that

iex(1)> DoNotExists.foo(2 + 3)
** (UndefinedFunctionError) function DoNotExists.foo/1 is undefined (module DoNotExists is not available)
    DoNotExists.foo(5)

fails with a value of 5.

First, the inner body is evaluated (2 + 3), then the function is called with the result of that evaluation. It doesn’t exist, so an error is raised.

Then, in your case, first the inner assert is evaluated and and since it fails, nothing else in the test matters.

1 Like

Oh… it’s so clear now that you have explained it. I was under the incorrect assumption that blocks only works with macros, so I was expecting the compiler to expand it (and fail, because I didn’t write the macro yet)

Thank you!

Nope, a block executes where defined before a function call. Macro calls, on the other hand, run at compile-time, they just happen to take the block’s AST and do something with it, but the block itself is still run at whatever place the macro puts it. :slight_smile:

/me uses do blocks for a number of things with functions in their Phoenix Template helpers.