# Erlang/Elixir OpenTelemetry API

[![EEF Observability WG project](](
![Build Status](

This is the API portion of [OpenTelemetry]( for Erlang and Elixir Applications.

This is a library, it does not start any processes, and should be the only OpenTelemetry dependency of Erlang/Elixir Applications. 

The end user of your Application can then choose to include the [OpenTelemetry implementation]( Application. If the implementation Application is not in the final release the OpenTelemetry instrumentation will all be no-ops. This means no processes started, no ETS tables created and nothing added to the process dictionary.

This separation is done so you should feel comfortable instrumenting your Erlang/Elixir Application with OpenTelemetry and not worry that a complicated dependency is being forced on your users.

## Use

When instrumenting an Application to be used as a dependency of other projects it is best practice to register a `Tracer` with a name and a version using the Application's name and version. This should be the name and version of the Application that has the `opentelemetry` calls being written in it, not the name of the Application it might be being used to instrument. For example, an [Elli]( middleware to add tracing to the Elli HTTP server would *not* be named `elli`, it would be the name of the middleware Application, like `opentelemetry_elli`.

Registration is done through a single process and uses a [persistent_term](, so should be done only once per-Application. Updating a registration is allowed, so updating the version on a release upgrade can, and should, be done, but will involve the performance penalty of updating a [persistent_term](

Naming the `Tracers` provides additional metadata on spans and allows the user of your Application to disable the traces from the dependency if it is needed.

### Dependency in Elixir

``` elixir
def deps do
    {:opentelemetry_api, "~> 0.6.0"}

### Helper Macros for Application Tracers

There are both Erlang and Elixir macros that make use of the current module's
name to lookup a Named Tracer -- a Named Tracer is created for each Application
loaded in the system at start time -- for you and can be used for Trace and Span

``` erlang

some_fun() ->
    ?with_span(<<"some_fun/0">>, #{}, 
        fun(_SpanCtx) -> 
            ?set_attribute(<<"key">>, <<"value">>),

``` elixir
require OpenTelemetry.Tracer
require OpenTelemetry.Span
def some_fun() do
    OpenTelemetry.Tracer.with_span "some-span" do
      OpenTelemetry.Span.set_attribute("key", "value")

### Including the OpenTelemetry SDK

For traces to actually be tracked, propagated and exported, the [opentelemetry]( Application must be included as a dependency of your project, likely as part of a [Release]( and not as a dependency of an individual Application within the Release.

See the [Using section]( of the [OpenTelemetry-Erlang]( repository for details.

### Exporters

Exporters can be found as separate Applications on Github under the [OpenTelemetry Beam Organization](

- [Zipkin](
- [OpenTelemetry Collector](

### HTTP Integrations

- [Elli](

### Database Client Integration

- [Ecto](

## Contributing

See the [contributing file](