Packages
sentry
10.2.1
13.3.0
13.2.0
13.1.0
13.0.1
13.0.0
12.0.3
12.0.2
12.0.1
12.0.0
11.0.4
11.0.3
11.0.2
11.0.1
11.0.0
10.10.0
10.9.0
10.8.1
10.8.0
10.7.1
10.7.0
10.6.2
10.6.1
10.6.0
10.5.0
10.4.0
10.3.0
10.2.1
10.2.0
10.2.0-rc.2
10.2.0-rc.1
10.1.0
10.0.3
10.0.2
10.0.1
10.0.0
9.1.0
9.0.0
8.1.0
8.0.6
8.0.5
8.0.4
8.0.3
8.0.2
8.0.1
8.0.0
8.0.0-rc.2
8.0.0-rc.1
8.0.0-rc.0
retired
7.2.5
7.2.4
7.2.3
7.2.2
7.2.1
7.2.0
7.1.0
7.0.6
7.0.5
7.0.4
7.0.3
7.0.2
7.0.1
7.0.0
6.4.2
6.4.1
6.4.0
6.3.0
6.2.1
6.2.0
6.1.0
6.0.5
6.0.4
6.0.3
6.0.2
6.0.1
6.0.0
5.0.1
5.0.0
4.0.3
4.0.2
4.0.1
4.0.0
3.0.0
2.2.0
2.1.0
2.0.2
2.0.1
2.0.0
1.1.2
1.1.1
1.1.0
1.0.0
0.3.2
0.3.1
0.3.0
0.2.0
0.1.3
0.1.2
0.1.1
0.1.0
The Official Elixir client for Sentry
Current section
Files
Jump to
Current section
Files
lib/sentry/cron/quantum.ex
defmodule Sentry.Cron.Quantum do
@moduledoc false
@events [
[:quantum, :job, :start],
[:quantum, :job, :stop],
[:quantum, :job, :exception]
]
@spec attach_telemetry_handler() :: :ok
def attach_telemetry_handler do
_ = :telemetry.attach_many(__MODULE__, @events, &__MODULE__.handle_event/4, :no_config)
:ok
end
@spec handle_event([atom()], term(), term(), :no_config) :: :ok
def handle_event(event, measurements, metadata, _config)
def handle_event(
[:quantum, :job, event],
measurements,
%{job: %mod{schedule: schedule}} = metadata,
_config
)
when event in [:start, :stop, :exception] and mod == Quantum.Job and not is_nil(schedule) do
_ = handle_event(event, measurements, metadata)
:ok
end
def handle_event([:quantum, :job, event], _measurements, _metadata, _config)
when event in [:start, :stop, :exception] do
:ok
end
## Helpers
defp handle_event(:start, _measurements, metadata) do
if opts = check_in_opts(metadata) do
opts
|> Keyword.merge(status: :in_progress)
|> Sentry.capture_check_in()
end
end
defp handle_event(:stop, measurements, metadata) do
if opts = check_in_opts(metadata) do
opts
|> Keyword.merge(status: :ok, duration: duration_in_seconds(measurements))
|> Sentry.capture_check_in()
end
end
defp handle_event(:exception, measurements, metadata) do
if opts = check_in_opts(metadata) do
opts
|> Keyword.merge(status: :error, duration: duration_in_seconds(measurements))
|> Sentry.capture_check_in()
end
end
defp check_in_opts(%{job: job} = metadata) when is_struct(job, Quantum.Job) do
if schedule_opts = schedule_opts(job) do
id = metadata.telemetry_span_context |> :erlang.phash2() |> Integer.to_string()
[
check_in_id: "quantum-#{id}",
# This is already a binary.
monitor_slug: "quantum-#{inspect(job.name)}",
monitor_config: [schedule: schedule_opts]
]
else
nil
end
end
defp schedule_opts(job) when is_struct(job, Quantum.Job) do
case apply(Crontab.CronExpression.Composer, :compose, [job.schedule]) do
"@hourly" -> [type: :interval, value: 1, unit: :hour]
"@daily" -> [type: :interval, value: 1, unit: :day]
"@weekly" -> [type: :interval, value: 1, unit: :week]
"@monthly" -> [type: :interval, value: 1, unit: :month]
"@yearly" -> [type: :interval, value: 1, unit: :year]
"@annually" -> [type: :interval, value: 1, unit: :year]
"@reboot" -> nil
cron_expr when is_binary(cron_expr) -> [type: :crontab, value: cron_expr]
_other -> nil
end
end
defp duration_in_seconds(%{duration: duration} = _measurements) do
duration
|> System.convert_time_unit(:native, :millisecond)
|> Kernel./(1000)
end
end