Installation View Source
NOTE: Check out the geometrics_example directory to see an example Phoenix application that has everything configured from this guide.
Running the OpenTelemetry collector
There are two ways to report data to tracing services:
- Use an opentelemetry-collector service that runs as a sidecar to your application
Pros:
- allows for exporting trace data to multiple APIs and keeps your app vendor-agnostic
- metric processing features like throttling / buffering data.
- allows for connecting distributed traces between your front end and back end
Cons:
- requires you to figure out how to deploy it in production
- requires use of docker compose locally
- may be too many features for a simple use case
- Directly export metric / trace data from your running Elixir app
Pros:
- Simple to set up
- No need to run docker locally to host the collector
Cons:
- Does not allow you to connect traces between frontend and backend code
- App remains coupled to whatever 3rd party metrics service you use
This guide walks you through setting up the opentelemetry-collector with Honeycomb, but later mentions how to set up geometrics without the collector (ie going straight to Honeycomb) as well.
1. Install Geometrics
Add geometrics to your mix.exs.
def deps do
[
{:geometrics, "~> 1.0.3-rc.3"}
]
end$ mix deps.get
2. Install the sidecar collector (skip if you do not want to run a collector)
We've made it easy to get set up a collector locally. The following command will copy a docker-compose.yml file
used to run the collector into your projects top level directory. It will also copy over a configuration file,
otel-collector-config.yml, used to configure the collector Docker process:
$ mix geometrics.install
(You will need to set HONEYCOMB_DATASET and HONEYCOMB_WRITE_KEY in your environment before running this command)
To run the collector, simply run:
$ docker compose up
After wiring up your Phoenix app to send data to it locally, you should see metrics data appear in
Honeycomb under the dataset configured by HONEYCOMB_DATASET. You can also feel free to
configure additional exporters in the otel-collector-config.yml file via the spec
Now, on to configuring your Phoenix app...
3. config.exs
Configure Geometrics in config.exs:
# Necessary to tell OpenTelemetry what repository to report traces for
config :geometrics, :ecto_prefix, [:my_app, :repo]
# Configuring a custom logger Geometrics.OpenTelemetry.Logger to help export process crashes to OpenTelemetry, which aren't reported by default
config :logger,
backends: [
:console,
Geometrics.OpenTelemetry.Logger
]
# The service name will show up in each span in your metrics service (i.e. Honeycomb)
config :opentelemetry, :resource,
service: [
name: "<app name> backend"
]3. runtime.exs
Configure opentelemetry with an exporter / collector. If running otel-collector as a sidecar
in k8s, with an otel receiver on port 55821, the following will work.
config :opentelemetry,
processors: [
otel_batch_processor: %{
exporter: {
:opentelemetry_exporter,
%{endpoints: [{:http, '0.0.0.0', 55_681, []}]}
}
}
]Despite being somewhat redundant, for now you must also specify the collector_endpoint so that the Geometrics javascript will know where to send its trace data.
config :geometrics, :collector_endpoint, "http://localhost:55681/v1/traces"In this example we export all trace data to an opentelemetry-collector agent that will be running on localhost:55681 according to the docker compose file you copied over previously.
If you'd prefer to run without using the opentelemetry-collector sidecar, and to send directly to a metrics service like Honeycomb instead, you should instead configure opentelemetry like so:
dataset = System.fetch_env!("HONEYCOMB_DATASET")
key = System.fetch_env!("HONEYCOMB_WRITE_KEY")
config :opentelemetry, :processors,
otel_batch_processor: %{
exporter: {
:opentelemetry_exporter,
%{
endpoints: ["https://api.honeycomb.io:443"],
headers: [
{"x-honeycomb-dataset", dataset},
{"x-honeycomb-team", key}
]
}
}
}NOTE: with this configuration you will not get any frontend trace reporting unless you separately configure opentelemetry-js to export to Honeycomb as well. (this is something Geometrics does for you, so long as you are using the opentelemetry-collector sidecar as outlined above).
application.ex
Add the handler to the Application's supervision tree:
defmodule MyApp.Application do
use Application
def start(_type, _args) do
children = [
Geometrics.OpenTelemetry.Handler, ## <------------
MyApp.Repo,
{Phoenix.PubSub, name: MyApp.PubSub},
MyAppWeb.Endpoint
]
opts = [strategy: :one_for_one, name: MyApp.Supervisor]
Supervisor.start_link(children, opts)
end
endPhoenix router.ex
Add our plug to the router:
defmodule MyAppWeb.Router do
use MyAppWeb, :router
pipeline :browser do
# .....
plug Geometrics.Plug.OpenTelemetry
end
# ...
endRoot layout
Add meta tags to the root layout that will enable front-end/back-end tracing
doctype html
html lang="en"
head
= csrf_meta_tag()
= Geometrics.Phoenix.View.meta_tags(@conn)
/ ....
body
= @inner_contentGetting frontend event traces
To get javascript traces to show up within LiveView traces, check out the javascript guide.