Packages

Debug utility for Elixir, inspired by Node.js debug package

Current section

Files

Jump to
ex_dbug README.md
Raw

README.md

# ExDbug
[![Hex.pm](https://img.shields.io/hexpm/v/ex_dbug.svg)](https://hex.pm/packages/ex_dbug)
[![Docs](https://img.shields.io/badge/hex-docs-blue.svg)](https://hexdocs.pm/ex_dbug)
Debug utility for Elixir applications, inspired by the Node.js 'debug' package.
Version 2.0 introduces decorator-based function tracing while maintaining compatibility with 1.x style debugging.
## Features
* 🎯 **Decorator-based function tracing** - Zero-cost, compile-time instrumentation
* πŸ”„ **1.x Compatibility Mode** - Seamless upgrade path from earlier versions
* πŸ” **Namespace-based filtering** - Filter debug output by context
* πŸ“Š **Rich metadata support** - Attach and format detailed debug information
* ⚑ **Zero runtime cost when disabled** - Compile-time optimization
* 🌍 **Environment variable-based filtering** - Easy runtime control
* πŸ“ **Automatic metadata truncation** - Smart handling of large values
* πŸ”§ **Hierarchical configuration** - Global, module, and function-level settings
* πŸ“ˆ **Value tracking** - Monitor values through pipelines
* ⏱️ **Optional timing and stack traces** - Deep insights when needed
## Installation
Add `ex_dbug` to your list of dependencies in `mix.exs`:
```elixir
def deps do
[
{:ex_dbug, "~> 2.0"}
]
end
```
## Usage (2.0 Style)
The new decorator-based approach makes debugging more elegant and maintainable:
```elixir
defmodule MyApp.Worker do
use ExDbug, enabled: true
# Simple debug trace
@decorate dbug()
def process(data) do
# Implementation
end
# Configured debug trace
@decorate dbug(context: :important)
def process_important(data) do
# Implementation
end
# Debug all functions in module
@decorate_all dbug()
def bulk_1(arg), do: arg
def bulk_2(arg), do: arg
end
```
## Compatibility Mode (1.x Style)
For existing projects or gradual migration, use compatibility mode:
```elixir
defmodule MyApp.LegacyWorker do
use ExDbug, compatibility_mode: true
def process(data) do
dbug("Processing data", size: byte_size(data))
# ... processing logic
dbug("Completed processing", status: :ok)
end
end
```
## Configuration
### Compile-Time Configuration
In your `config.exs`:
```elixir
config :ex_dbug,
enabled: true,
config: [
max_depth: 3,
include_timing: true,
include_stack: true,
truncate: 100,
levels: [:debug, :error]
]
```
### Module-Level Configuration
```elixir
use ExDbug,
enabled: true,
max_depth: 5,
include_timing: true,
include_stack: false,
levels: [:debug, :error]
```
### Function-Level Configuration (2.0)
```elixir
@decorate dbug(
context: :important,
include_timing: true,
include_stack: true
)
def critical_function(arg) do
# Implementation
end
```
### Runtime Configuration
Control debug output using the `DEBUG` environment variable:
```bash
# Enable all debug output
DEBUG="*" mix run
# Enable specific namespace
DEBUG="myapp:worker" mix run
# Enable multiple patterns
DEBUG="myapp:*,other:thing" mix run
# Enable all except specific namespace
DEBUG="*,-myapp:secret" mix run
```
## Migrating from 1.x to 2.0
### Option 1: Direct Upgrade (Recommended)
Replace debug calls with decorators:
```elixir
# Before (1.x)
def process(arg) do
dbug("Processing", value: arg)
# Implementation
end
# After (2.0)
@decorate dbug()
def process(arg) do
# Implementation
end
```
### Option 2: Compatibility Mode
For gradual migration, enable compatibility mode:
```elixir
use ExDbug, compatibility_mode: true
# All 1.x code continues to work
```
### Configuration Updates
Update your configuration to use the new hierarchical structure:
```elixir
# Before (1.x)
config :ex_dbug, enabled: true
# After (2.0)
config :ex_dbug,
enabled: true,
config: [
max_depth: 3,
include_timing: true
]
```
## Best Practices
1. Use descriptive context names matching your application structure
2. Prefer decorator-based debugging for new code
3. Use compatibility mode for gradual migration
4. Set appropriate DEBUG patterns for different environments
5. Configure hierarchically (global β†’ module β†’ function)
6. Disable in production for zero overhead
## Production Use
While ExDbug has minimal overhead when disabled, it's recommended to set
`config :ex_dbug, enabled: false` in production unless debugging is specifically
needed. This ensures zero runtime cost as debug calls are compiled out completely.
## Contributing
1. Fork it
2. Create your feature branch (`git checkout -b my-new-feature`)
3. Commit your changes (`git commit -am 'Add some feature'`)
4. Push to the branch (`git push origin my-new-feature`)
5. Create new Pull Request
## License
MIT License - see LICENSE.md for details.