Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update span names for OpentelemetryPhoenix #433

Draft
wants to merge 3 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -163,11 +163,14 @@ defmodule OpentelemetryPhoenix do
%{socket: %{view: live_view}} = meta,
_handler_configuration
) do
start_opts = live_view_start_opts(meta)
target = target(start_opts.attributes, live_view)

OpentelemetryTelemetry.start_telemetry_span(
@tracer_id,
"#{inspect(live_view)}.mount",
"live_view.mount #{target}",
meta,
%{kind: :server}
start_opts
)
end

Expand All @@ -177,11 +180,14 @@ defmodule OpentelemetryPhoenix do
%{socket: %{view: live_view}} = meta,
_handler_configuration
) do
start_opts = live_view_start_opts(meta)
target = target(start_opts.attributes, live_view)

OpentelemetryTelemetry.start_telemetry_span(
@tracer_id,
"#{inspect(live_view)}.handle_params",
"live_view.handle_params #{target}",
meta,
%{kind: :server}
start_opts
)
end

Expand All @@ -191,11 +197,14 @@ defmodule OpentelemetryPhoenix do
%{socket: %{view: live_view}, event: event} = meta,
_handler_configuration
) do
start_opts = live_view_start_opts(meta)
target = target(start_opts.attributes, live_view)

OpentelemetryTelemetry.start_telemetry_span(
@tracer_id,
"#{inspect(live_view)}.handle_event##{event}",
"live_view.handle_event #{target} #{event}",
meta,
%{kind: :server}
live_view_start_opts(meta)
)
end

Expand All @@ -222,4 +231,26 @@ defmodule OpentelemetryPhoenix do
OpenTelemetry.Span.set_status(ctx, OpenTelemetry.status(:error, ""))
OpentelemetryTelemetry.end_telemetry_span(@tracer_id, meta)
end

defp live_view_start_opts(meta) do
%{
kind: :server,
attributes: url_attributes(meta)
}
end

defp url_attributes(%{uri: uri, socket: %{router: router}}) do
uri = URI.parse(uri)

case Phoenix.Router.route_info(router, "GET", uri.path, uri.host) do
:error -> %{}
route_info -> %{URLAttributes.url_template() => route_info.route}
end
end

defp url_attributes(_meta), do: %{}

defp target(attributes, live_view) do
attributes[URLAttributes.url_template()] || inspect(live_view)
end
end
1 change: 1 addition & 0 deletions instrumentation/opentelemetry_phoenix/mix.exs
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ defmodule OpentelemetryPhoenix.MixProject do
{:opentelemetry_cowboy, "~> 1.0.0", only: [:dev, :test]},
{:ex_doc, "~> 0.36", only: [:dev], runtime: false},
{:phoenix, "~> 1.7", only: [:dev, :test]},
{:phoenix_live_view, "~> 1.0.0", only: [:dev, :test]},
{:phoenix_html, "~> 4.1", only: [:dev, :test]},
{:plug_cowboy, "~> 2.5", only: [:dev, :test]},
{:bandit, "~> 1.5", only: [:dev, :test]},
Expand Down
1 change: 1 addition & 0 deletions instrumentation/opentelemetry_phoenix/mix.lock
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@
"otel_http": {:hex, :otel_http, "0.2.0", "b17385986c7f1b862f5d577f72614ecaa29de40392b7618869999326b9a61d8a", [:rebar3], [], "hexpm", "f2beadf922c8cfeb0965488dd736c95cc6ea8b9efce89466b3904d317d7cc717"},
"phoenix": {:hex, :phoenix, "1.7.14", "a7d0b3f1bc95987044ddada111e77bd7f75646a08518942c72a8440278ae7825", [:mix], [{:castore, ">= 0.0.0", [hex: :castore, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:phoenix_pubsub, "~> 2.1", [hex: :phoenix_pubsub, repo: "hexpm", optional: false]}, {:phoenix_template, "~> 1.0", [hex: :phoenix_template, repo: "hexpm", optional: false]}, {:phoenix_view, "~> 2.0", [hex: :phoenix_view, repo: "hexpm", optional: true]}, {:plug, "~> 1.14", [hex: :plug, repo: "hexpm", optional: false]}, {:plug_cowboy, "~> 2.7", [hex: :plug_cowboy, repo: "hexpm", optional: true]}, {:plug_crypto, "~> 1.2 or ~> 2.0", [hex: :plug_crypto, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}, {:websock_adapter, "~> 0.5.3", [hex: :websock_adapter, repo: "hexpm", optional: false]}], "hexpm", "c7859bc56cc5dfef19ecfc240775dae358cbaa530231118a9e014df392ace61a"},
"phoenix_html": {:hex, :phoenix_html, "4.1.1", "4c064fd3873d12ebb1388425a8f2a19348cef56e7289e1998e2d2fa758aa982e", [:mix], [], "hexpm", "f2f2df5a72bc9a2f510b21497fd7d2b86d932ec0598f0210fed4114adc546c6f"},
"phoenix_live_view": {:hex, :phoenix_live_view, "1.0.1", "5389a30658176c0de816636ce276567478bffd063c082515a6e8368b8fc9a0db", [:mix], [{:floki, "~> 0.36", [hex: :floki, repo: "hexpm", optional: true]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:phoenix, "~> 1.6.15 or ~> 1.7.0", [hex: :phoenix, repo: "hexpm", optional: false]}, {:phoenix_html, "~> 3.3 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: false]}, {:phoenix_template, "~> 1.0", [hex: :phoenix_template, repo: "hexpm", optional: false]}, {:phoenix_view, "~> 2.0", [hex: :phoenix_view, repo: "hexpm", optional: true]}, {:plug, "~> 1.15", [hex: :plug, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4.2 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "c0f517e6f290f10dbb94343ac22e0109437fb1fa6f0696e7c73967b789c1c285"},
"phoenix_pubsub": {:hex, :phoenix_pubsub, "2.1.3", "3168d78ba41835aecad272d5e8cd51aa87a7ac9eb836eabc42f6e57538e3731d", [:mix], [], "hexpm", "bba06bc1dcfd8cb086759f0edc94a8ba2bc8896d5331a1e2c2902bf8e36ee502"},
"phoenix_template": {:hex, :phoenix_template, "1.0.4", "e2092c132f3b5e5b2d49c96695342eb36d0ed514c5b252a77048d5969330d639", [:mix], [{:phoenix_html, "~> 2.14.2 or ~> 3.0 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}], "hexpm", "2c0c81f0e5c6753faf5cca2f229c9709919aba34fab866d3bc05060c9c444206"},
"plug": {:hex, :plug, "1.16.1", "40c74619c12f82736d2214557dedec2e9762029b2438d6d175c5074c933edc9d", [:mix], [{:mime, "~> 1.0 or ~> 2.0", [hex: :mime, repo: "hexpm", optional: false]}, {:plug_crypto, "~> 1.1.1 or ~> 1.2 or ~> 2.0", [hex: :plug_crypto, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4.3 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "a13ff6b9006b03d7e33874945b2755253841b238c34071ed85b0e86057f8cddc"},
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,19 @@
defmodule NnnnnWeb.Router do
use Phoenix.Router, helpers: false

import Phoenix.LiveView.Router

scope "/", NnnnnWeb do
scope "/resources/", ResourceLive do
live "/:resource_id", Show, :show
end
end
end

defmodule NnnnnWeb.ResourceLive.Show do
use Phoenix.LiveView, log: false
end

defmodule OpentelemetryPhoenixTest do
use ExUnit.Case, async: false
doctest OpentelemetryPhoenix
Expand All @@ -7,7 +23,64 @@ defmodule OpentelemetryPhoenixTest do
require Record

alias OpenTelemetry.SemConv.ExceptionAttributes
alias PhoenixLiveViewMeta, as: LiveViewMeta

@socket Phoenix.LiveView.Utils.configure_socket(
%Phoenix.LiveView.Socket{
endpoint: NnnnWeb.Endpoint,
router: NnnnnWeb.Router,
view: NnnnnWeb.ResourceLive.Show
},
%{
connect_params: %{},
connect_info: %{},
root_view: NnnnnWeb.ResourceLive.Show,
live_temp: %{}
},
:show,
%{},
URI.parse("https://localhost:4000/resources/123?foo=bar")
)

@telemetry_meta_base %{
socket: @socket,
params: %{"foo" => "bar"},
uri: "https://localhost:4000/resources/123?foo=bar",
session: %{},
telemetry_span_context: :dummy_ref
}

@telemetry_meta_handle_params Map.put(@telemetry_meta_base, :event, "hello")

@exception_meta %{
reason: %RuntimeError{message: "stop"},
stacktrace: [
{NnnnnWeb.ResourceLive.Show, :handle_params, 3,
[
file: ~c"lib/nnnnn_web/live/resources_live/show.ex",
line: 28,
error_info: %{module: Exception}
]}
],
kind: :error
}

@telemetry_meta %{
mount: %{
start: @telemetry_meta_base,
stop: @telemetry_meta_base,
exception: @telemetry_meta_base
},
handle_params: %{
start: @telemetry_meta_base,
stop: @telemetry_meta_base,
exception: Map.merge(@telemetry_meta_base, @exception_meta)
},
handle_event: %{
start: @telemetry_meta_handle_params,
stop: @telemetry_meta_handle_params,
exception: Map.merge(@telemetry_meta_handle_params, @exception_meta)
}
}

for {name, spec} <- Record.extract_all(from_lib: "opentelemetry/include/otel_span.hrl") do
Record.defrecord(name, spec)
Expand All @@ -34,22 +107,22 @@ defmodule OpentelemetryPhoenixTest do
:telemetry.execute(
[:phoenix, :live_view, :mount, :start],
%{system_time: System.system_time()},
LiveViewMeta.mount_start()
@telemetry_meta.mount.start
)

:telemetry.execute(
[:phoenix, :live_view, :mount, :stop],
%{system_time: System.system_time()},
LiveViewMeta.mount_stop()
%{system_time: System.system_time(), duration: 10},
@telemetry_meta.mount.stop
)

assert_receive {:span,
span(
name: "NnnnnWeb.MyTestLive.mount",
name: "live_view.mount /resources/:resource_id",
attributes: attributes
)}

assert %{} == :otel_attributes.map(attributes)
assert :otel_attributes.map(attributes) == %{:"url.template" => "/resources/:resource_id"}
end

test "records spans for Phoenix LiveView handle_params" do
Expand All @@ -58,22 +131,22 @@ defmodule OpentelemetryPhoenixTest do
:telemetry.execute(
[:phoenix, :live_view, :handle_params, :start],
%{system_time: System.system_time()},
LiveViewMeta.handle_params_start()
@telemetry_meta.handle_params.start
)

:telemetry.execute(
[:phoenix, :live_view, :handle_params, :stop],
%{system_time: System.system_time()},
LiveViewMeta.handle_params_stop()
%{system_time: System.system_time(), duration: 10},
@telemetry_meta.handle_params.stop
)

assert_receive {:span,
span(
name: "NnnnnWeb.MyTestLive.handle_params",
name: "live_view.handle_params /resources/:resource_id",
attributes: attributes
)}

assert %{} == :otel_attributes.map(attributes)
assert :otel_attributes.map(attributes) == %{:"url.template" => "/resources/:resource_id"}
end

test "records spans for Phoenix LiveView handle_event" do
Expand All @@ -82,22 +155,22 @@ defmodule OpentelemetryPhoenixTest do
:telemetry.execute(
[:phoenix, :live_view, :handle_event, :start],
%{system_time: System.system_time()},
LiveViewMeta.handle_event_start()
@telemetry_meta.handle_event.start
)

:telemetry.execute(
[:phoenix, :live_view, :handle_event, :stop],
%{system_time: System.system_time()},
LiveViewMeta.handle_event_stop()
%{system_time: System.system_time(), duration: 10},
@telemetry_meta.handle_event.stop
)

assert_receive {:span,
span(
name: "NnnnnWeb.MyTestLive.handle_event#hello",
name: "live_view.handle_event /resources/:resource_id hello",
attributes: attributes
)}

assert %{} == :otel_attributes.map(attributes)
assert :otel_attributes.map(attributes) == %{:"url.template" => "/resources/:resource_id"}
end

test "handles exception during Phoenix LiveView handle_params" do
Expand All @@ -106,43 +179,43 @@ defmodule OpentelemetryPhoenixTest do
:telemetry.execute(
[:phoenix, :live_view, :mount, :start],
%{system_time: System.system_time()},
LiveViewMeta.mount_start(:exception)
@telemetry_meta.mount.start
)

:telemetry.execute(
[:phoenix, :live_view, :mount, :stop],
%{system_time: System.system_time()},
LiveViewMeta.mount_stop(:exception)
@telemetry_meta.mount.stop
)

:telemetry.execute(
[:phoenix, :live_view, :handle_params, :start],
%{system_time: System.system_time()},
LiveViewMeta.handle_params_start(:exception)
@telemetry_meta.handle_params.start
)

:telemetry.execute(
[:phoenix, :live_view, :handle_params, :exception],
%{system_time: System.system_time()},
LiveViewMeta.handle_params_exception(:exception)
@telemetry_meta.handle_params.exception
)

assert_receive {:span,
span(
name: "NnnnnWeb.MyTestLive.mount",
name: "live_view.mount /resources/:resource_id",
attributes: attributes
)}

assert %{} == :otel_attributes.map(attributes)
assert :otel_attributes.map(attributes) == %{:"url.template" => "/resources/:resource_id"}

assert_receive {:span,
span(
name: "NnnnnWeb.MyTestLive.handle_params",
name: "live_view.handle_params /resources/:resource_id",
attributes: attributes,
events: events
)}

assert %{} == :otel_attributes.map(attributes)
assert :otel_attributes.map(attributes) == %{:"url.template" => "/resources/:resource_id"}

[
event(
Expand All @@ -165,23 +238,23 @@ defmodule OpentelemetryPhoenixTest do
:telemetry.execute(
[:phoenix, :live_view, :handle_event, :start],
%{system_time: System.system_time()},
LiveViewMeta.handle_event_start(:exception)
@telemetry_meta.handle_event.start
)

:telemetry.execute(
[:phoenix, :live_view, :handle_event, :exception],
%{system_time: System.system_time()},
LiveViewMeta.handle_event_exception(:exception)
@telemetry_meta.handle_event.exception
)

assert_receive {:span,
span(
name: "NnnnnWeb.MyTestLive.handle_event#hello",
name: "live_view.handle_event /resources/:resource_id hello",
attributes: attributes,
events: events
)}

assert %{} == :otel_attributes.map(attributes)
assert :otel_attributes.map(attributes) == %{:"url.template" => "/resources/:resource_id"}

[
event(
Expand Down
Loading
Loading