Add opentelemetry integration to Oban (#6)
By default a new trace is automatically started when a job is processed
by monitoring these events:
* `[:oban, :job, :start]` — at the point a job is fetched from the database and will execute
* `[:oban, :job, :stop]` — after a job succeeds and the success is recorded in the database
* `[:oban, :job, :exception]` — after a job fails and the failure is recorded in the database
To also record a span when a job is created and to link traces together
`Oban.insert/2` has to be replaced by `OpentelemetryOban.insert/2`.
Before:
```elixir
%{id: 1, in_the: "business", of_doing: "business"}
|> MyApp.Business.new()
|> Oban.insert()
```
After:
```elixir
%{id: 1, in_the: "business", of_doing: "business"}
|> MyApp.Business.new()
|> OpentelemetryOban.insert()
```
Co-authored-by: Tristan Sloughter <t@crashfast.com>
2021-12-08 15:41:36 +00:00
|
|
|
ExUnit.start()
|
|
|
|
|
|
|
|
TestRepo.start_link(
|
|
|
|
database: "opentelemetry_oban_test",
|
|
|
|
hostname: "localhost",
|
|
|
|
username: "postgres",
|
|
|
|
password: "postgres",
|
|
|
|
pool: Ecto.Adapters.SQL.Sandbox
|
|
|
|
)
|
|
|
|
|
|
|
|
Ecto.Adapters.SQL.Sandbox.mode(TestRepo, {:shared, self()})
|
|
|
|
|
|
|
|
defmodule PrepareOban do
|
|
|
|
use Ecto.Migration
|
|
|
|
def up, do: Oban.Migrations.up()
|
|
|
|
end
|
|
|
|
|
|
|
|
Ecto.Migrator.run(TestRepo, [{0, PrepareOban}], :up, all: true)
|
|
|
|
TestRepo.query("TRUNCATE oban_jobs", [])
|
|
|
|
|
|
|
|
Oban.start_link(
|
|
|
|
repo: TestRepo,
|
|
|
|
plugins: [Oban.Plugins.Pruner],
|
2022-11-16 00:48:50 +00:00
|
|
|
notifier: Oban.Notifiers.PG,
|
|
|
|
testing: :manual
|
Add opentelemetry integration to Oban (#6)
By default a new trace is automatically started when a job is processed
by monitoring these events:
* `[:oban, :job, :start]` — at the point a job is fetched from the database and will execute
* `[:oban, :job, :stop]` — after a job succeeds and the success is recorded in the database
* `[:oban, :job, :exception]` — after a job fails and the failure is recorded in the database
To also record a span when a job is created and to link traces together
`Oban.insert/2` has to be replaced by `OpentelemetryOban.insert/2`.
Before:
```elixir
%{id: 1, in_the: "business", of_doing: "business"}
|> MyApp.Business.new()
|> Oban.insert()
```
After:
```elixir
%{id: 1, in_the: "business", of_doing: "business"}
|> MyApp.Business.new()
|> OpentelemetryOban.insert()
```
Co-authored-by: Tristan Sloughter <t@crashfast.com>
2021-12-08 15:41:36 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
defmodule TestJob do
|
|
|
|
use Oban.Worker, queue: :events, max_attempts: 1
|
|
|
|
|
|
|
|
@impl Oban.Worker
|
|
|
|
def perform(_job) do
|
|
|
|
:ok
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
defmodule TestJobWithInnerSpan do
|
|
|
|
use Oban.Worker, queue: :events, max_attempts: 1
|
|
|
|
require OpenTelemetry.Tracer
|
|
|
|
|
|
|
|
@impl Oban.Worker
|
|
|
|
def perform(_job) do
|
|
|
|
OpenTelemetry.Tracer.with_span "span inside the job" do
|
|
|
|
:ok
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
defmodule TestJobThatReturnsError do
|
|
|
|
use Oban.Worker, queue: :events, max_attempts: 1
|
|
|
|
|
|
|
|
@impl Oban.Worker
|
|
|
|
def perform(_job) do
|
|
|
|
{:error, :something}
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
defmodule TestJobThatThrowsException do
|
|
|
|
use Oban.Worker, queue: :events, max_attempts: 1
|
|
|
|
|
|
|
|
@impl Oban.Worker
|
|
|
|
def perform(_job) do
|
|
|
|
raise %UndefinedFunctionError{
|
|
|
|
message: "function Some.error/0 is undefined (module Some is not available)"
|
|
|
|
}
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
defmodule TestHelpers do
|
|
|
|
def remove_oban_handlers() do
|
|
|
|
Enum.each(:telemetry.list_handlers([:oban]), fn handler ->
|
|
|
|
:telemetry.detach(handler[:id])
|
|
|
|
end)
|
|
|
|
end
|
|
|
|
end
|