Inspector, a better way to debug Elixir Code
Marcio Lopes de Faria
Posted on September 17, 2021
EDIT: Since Elixir 1.14, there is a new macro dbg/2
that substitute the Inspector package.
I have been tinkering with better ways to improve my Elixir workflow and during this journey I realized that I am, somehow, trying to bring things which I'm used with from other environments, the same way a foreign citizen does when living in a different country.
Elixir prizes highly the Developer Experience, so that we have the astounding tools to generate documentation, first quality package management, and an excellent and mature build tool, and a REPL, iex
that allows fast experiments, but I think that may I have pushed a lot the expected usage of it, in a not intended way as it was planned by the creators.
We can feel it during a IEx.pry/0
usage, it's a pretty limited tool, if you are accustomed to use Ruby pry for example, but given that Elixir doesn't hold mutable state, maybe it isn't necessary at all, so I started to think about the root cause of my dissatisfaction and I found it.
Debugging
Elixir is blaze fast, and we can notice it clearly when running a test suite with a lot of tests, they run really fast and the maintainers are working hard to make it even faster, so the so called Puts debugging is more than enough.
But what really hurts is to type always and everyplace the same think, IO.inspect/2
, passing ad-hoc variables. It's not uncommon to make several calls to IO.inspect/2
during a debugging session, so if we improve it, enhancing the IO.inspect/2
?
This is how Inspector was born, a library that makes debugging less annoying. You need only to place it in the calling site, like this:
# If this code is on lib/my_module.ex
defmodule MyModule do
def my_function(args) do
awesome_var = :foo
amazing_var = :bar
require Inspector; Inspector.i
end
end
MyModule.my_function(:hey)
And you will see in the stdout
:
inspector: %{
bindings: [
args: :hey,
awesome_var: :foo,
amazing_var: :bar
],
file: "lib/my_module.ex:5",
location: "MyModule.my_function/1"
}
If you uses Vim or Neovim, like me, you can even make it better with a key-map:
nnoremap <Leader>i orequire Inspector; Inspector.i<esc>
I hight recommend use it running this simple command:
Or with mix test.watch
found here
That is it folks. Happy debugging!
Posted on September 17, 2021
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.