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

add Elixir modules for baggage and context #121

Merged
merged 2 commits into from
Oct 15, 2020
Merged
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
2 changes: 1 addition & 1 deletion apps/opentelemetry/test/opentelemetry_SUITE.erl
Original file line number Diff line number Diff line change
Expand Up @@ -233,7 +233,7 @@ propagation(Config) ->
?assertEqual(undefined, ?current_span_ctx),

%% clear our baggage from the context to test extraction
otel_ctx:remove(otel_baggage:ctx_key()),
otel_baggage:clear(),
?assertEqual(#{}, otel_baggage:get_all()),

%% make header keys uppercase to validate the extractor is case insensitive
Expand Down
13 changes: 13 additions & 0 deletions apps/opentelemetry_api/lib/open_telemetry/baggage.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
defmodule OpenTelemetry.Baggage do
@moduledoc """
Baggage is used to annotate telemetry, adding context and information to
metrics, traces, and logs. It is represented by a set of name/value pairs
describing user-defined properties.
"""

defdelegate set(keyvalues), to: :otel_baggage
defdelegate set(key, values), to: :otel_baggage
defdelegate get_all(), to: :otel_baggage
defdelegate clear(), to: :otel_baggage
defdelegate get_text_map_propagators(), to: :otel_baggage
end
18 changes: 18 additions & 0 deletions apps/opentelemetry_api/lib/open_telemetry/ctx.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
defmodule OpenTelemetry.Ctx do
@moduledoc """
Ctx is responsible for propagating values within a process that are associated
with a particular Trace or set of Baggage. `OpenTelemetry.Tracer` and
`OpenTelemetry.Baggage` handle updating the Context.
"""

defdelegate new(), to: :otel_ctx
defdelegate attach(ctx), to: :otel_ctx
defdelegate detach(token), to: :otel_ctx
defdelegate set_value(key, value), to: :otel_ctx
defdelegate set_value(ctx, key, value), to: :otel_ctx
defdelegate get_value(key, default), to: :otel_ctx
defdelegate get_value(ctx, key, default), to: :otel_ctx
defdelegate clear(), to: :otel_ctx
defdelegate remove(key), to: :otel_ctx
defdelegate get_current(), to: :otel_ctx
end
19 changes: 15 additions & 4 deletions apps/opentelemetry_api/src/otel_baggage.erl
Original file line number Diff line number Diff line change
Expand Up @@ -12,14 +12,17 @@
%% See the License for the specific language governing permissions and
%% limitations under the License.
%%
%% @doc
%% @doc Baggage is used to annotate telemetry, adding context and
%% information to metrics, traces, and logs. It is represented by a set
%% of name/value pairs describing user-defined properties.
%% @end
%%%-------------------------------------------------------------------------
-module(otel_baggage).

-export([ctx_key/0,
-export([set/1,
set/2,
get_all/0,
clear/0,
get_text_map_propagators/0]).

-type key() :: string().
Expand All @@ -34,8 +37,12 @@
-define(BAGGAGE_KEY, '$__otel_baggage_ctx_key').
-define(BAGGAGE_HEADER, <<"baggage">>).

ctx_key() ->
?BAGGAGE_KEY.
-spec set(#{key() => value()} | [{key(), value()}]) -> ok.
set(KeyValues) when is_list(KeyValues) ->
set(maps:from_list(KeyValues));
set(KeyValues) when is_map(KeyValues) ->
Baggage = otel_ctx:get_value(?BAGGAGE_KEY, #{}),
otel_ctx:set_value(?BAGGAGE_KEY, maps:merge(Baggage, KeyValues)).

-spec set(key(), value()) -> ok.
set(Key, Value) ->
Expand All @@ -46,6 +53,10 @@ set(Key, Value) ->
get_all() ->
otel_ctx:get_value(?BAGGAGE_KEY, #{}).

-spec clear() -> ok.
clear() ->
otel_ctx:set_value(?BAGGAGE_KEY, #{}).

-spec get_text_map_propagators() -> {otel_propagator:text_map_extractor(), otel_propagator:text_map_injector()}.
get_text_map_propagators() ->
ToText = fun(Baggage) when is_map(Baggage) ->
Expand Down
5 changes: 4 additions & 1 deletion apps/opentelemetry_api/src/otel_ctx.erl
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,10 @@
%% See the License for the specific language governing permissions and
%% limitations under the License.
%%
%% @doc
%% @doc Ctx is responsible for propagating values within a process that
%% are associated with a particular Trace or set of Baggage.
%% `OpenTelemetry.Tracer` and `OpenTelemetry.Baggage` handle updating
%% the Context.
%% @end
%%%-------------------------------------------------------------------------
-module(otel_ctx).
Expand Down
40 changes: 40 additions & 0 deletions apps/opentelemetry_api/test/open_telemetry_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ defmodule OpenTelemetryTest do

require OpenTelemetry.Tracer, as: Tracer
require OpenTelemetry.Span, as: Span
require OpenTelemetry.Baggage, as: Baggage
require OpenTelemetry.Ctx, as: Ctx

require Record
@fields Record.extract(:span_ctx, from_lib: "opentelemetry_api/include/opentelemetry.hrl")
Expand Down Expand Up @@ -63,4 +65,42 @@ defmodule OpenTelemetryTest do
assert [] = Span.tracestate(span)
end
end

test "baggage api from elixir" do
Baggage.set(%{"a" => "b"})
assert %{"a" => "b"} = Baggage.get_all()

Baggage.set(%{"a" => "c"})
assert %{"a" => "c"} = Baggage.get_all()

Baggage.clear()
assert 0 = :erlang.map_size(Baggage.get_all())
end

test "context api from elixir" do
ctx = Ctx.new()
ctx = Ctx.set_value(ctx, :somekey, :somevalue)
assert :somevalue = Ctx.get_value(ctx, :somekey, "default")

# attach the context and get value from implicit attached context
Ctx.attach(ctx)
assert :somevalue = Ctx.get_value(:somekey, "default")
end

test "baggage across contexts" do
ctx = Ctx.get_current()

Baggage.set(%{"a" => "b"})
assert %{"a" => "b"} = Baggage.get_all()

# attach the empty context
# gets a token for the context
token = Ctx.attach(ctx)
assert 0 = :erlang.map_size(Baggage.get_all())

# return to the context in the pdict before the attach
Ctx.detach(token)
assert %{"a" => "b"} = Baggage.get_all()
end

end