# Pretty
This module addresses two surprises you'll encounter trying to dump data to the remote console
like you did during development with `iex -S mix`:
* `IO.inspect/1` _et al_ work fine at the `iex>` prompt but their output goes to the server's
logs, not your console when you call them from inside a `:telemetry` handler function or other
troubleshooting mechanism
* The syntax colors aren't working
* The inspection width is 80… just like `iex`, now that you think of it
Why? See the [explanation](EXPLAIN.md).
In case of emergency, [BREAK GLASS](#break-glass) to get what you need with some copying and
pasting.
## Usage
To get the right syntax colors and inspection width, replace your calls to `IO.inspect/1` with
calls to `Pretty.inspect/1`:
```elixir
Pretty.inspect(<<0, 1, 2>>, width: 40)
```
... and `IO.inspect/2` with `Pretty.inspect/2`:
```elixir
[1, 2, 3]
|> IO.inspect(label: "before")
|> Enum.map(&(&1 * 2))
|> IO.inspect(label: "after")
|> Enum.sum()
```
To get the right colors, width, and output device, use `Pretty.bind/1` to get an `t:inspector/1`
function, and use it instead of `IO.inspect/1` or `Pretty.inspect/1`:
```elixir
dump = Pretty.bind(label: "Ecto")
handler = fn name, m10s, m6a, nil -> dump.({name, m10s, m6a}) end
:telemetry.attach(self(), [:my_app, :repo, :query], handler, nil)
```
## Installation
If [available in Hex](https://hex.pm/docs/publish), the package can be installed by adding
`pretty` to your list of dependencies in `mix.exs`:
```elixir
def deps do
[
{:pretty, "~> 1.0.0"}
]
end
```
## Development
Dependency management:
* `mix deps.get` to get your dependencies
* `mix deps.compile` to compile them
Finding problems:
* `mix compile` to compile your code
* `mix credo` to suggest more idiomatic style for it
* `mix dialyzer` to find problems static typing might spot... *slowly*
* `mix test` to run unit tests
* `mix test.watch` to run the tests again whenever you change something
* `mix coveralls` to check test coverage
Documentation:
* `mix docs` to generate documentation for this project
* `mix help` to find out what else you can do with `mix`
## BREAK GLASS
If you're sitting at a remote console _right now_ and just need some output without taking a new
dependency and re-releasing, paste this in to get most of the functionality of `Pretty.bind/1`
right away:
```elixir
bind = fn opts ->
device = Process.group_leader()
width = with {:ok, n} <- :io.columns(device), do: n, else: (_ -> %Inspect.Opts{}.width)
opts = Keyword.merge(:rpc.call(:erlang.node(device), IEx.Config, :inspect_opts, []), opts)
opts = Keyword.merge(opts, pretty: true, width: width)
reset = Enum.find_value(Keyword.get(opts, :syntax_colors, []), [], fn _ -> IO.ANSI.reset() end)
fn term -> IO.puts(device, [Kernel.inspect(term, opts), reset]); term end
end
# I never said it'd be Pretty...
# Can you make it shorter? PR or it didn't happen.
```
... and then use that:
```elixir
dump = bind.(label: "ecto")
handler = fn name, m10s, m6a, nil -> dump.({name, m10s, m6a}) end
:telemetry.attach(self(), [:my_app, :repo, :query], handler, nil)
```