diff --git a/CHANGELOG.md b/CHANGELOG.md index 54d02e8f4..b344c13dd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,9 @@ +## Unreleased + +### Bug Fixes + +- Skip including `sentry.message.template` in the log event attributes if there are no interpolation parameters provided ([#2700](https://github.com/getsentry/sentry-ruby/pull/2700)) + ## 5.27.0 ### Feature diff --git a/sentry-ruby/lib/sentry/log_event.rb b/sentry-ruby/lib/sentry/log_event.rb index a30a2f59c..31eb20374 100644 --- a/sentry-ruby/lib/sentry/log_event.rb +++ b/sentry-ruby/lib/sentry/log_event.rb @@ -32,6 +32,8 @@ class LogEvent "sentry.message.template" => :template } + PARAMETER_PREFIX = "sentry.message.parameter" + USER_ATTRIBUTES = { "user.id" => :user_id, "user.name" => :user_username, @@ -51,6 +53,7 @@ class LogEvent parent_span_id sdk_name sdk_version + template timestamp trace_id user_id @@ -146,6 +149,10 @@ def serialize_user_email user[:email] end + def serialize_template + template if has_parameters? + end + def serialize_attributes hash = {} @@ -185,11 +192,11 @@ def parameters if parameters.is_a?(Hash) parameters.each do |key, value| - attributes["sentry.message.parameter.#{key}"] = value + attributes["#{PARAMETER_PREFIX}.#{key}"] = value end else parameters.each_with_index do |param, index| - attributes["sentry.message.parameter.#{index}"] = param + attributes["#{PARAMETER_PREFIX}.#{index}"] = param end end end @@ -202,5 +209,9 @@ def template_tokens def is_template? body.include?("%s") || TOKEN_REGEXP.match?(body) end + + def has_parameters? + attributes.keys.any? { |key| key.start_with?(PARAMETER_PREFIX) } + end end end diff --git a/sentry-ruby/spec/sentry/log_event_spec.rb b/sentry-ruby/spec/sentry/log_event_spec.rb index 4d9fc3664..73b46096e 100644 --- a/sentry-ruby/spec/sentry/log_event_spec.rb +++ b/sentry-ruby/spec/sentry/log_event_spec.rb @@ -96,6 +96,39 @@ expect(hash[:attributes]).not_to have_key("sentry.message.template") end + it "doesn't set message.template when template has no parameters" do + event = described_class.new( + configuration: configuration, + level: :info, + body: "Hello %{name}, today is %{day}" + ) + + hash = event.to_hash + + expect(hash[:attributes]).not_to have_key("sentry.message.template") + expect(hash[:attributes]).not_to have_key("sentry.message.parameter.name") + expect(hash[:attributes]).not_to have_key("sentry.message.parameter.day") + end + + it "sets message.template only when parameters are present" do + attributes = { + "sentry.message.parameter.0" => "John" + } + + event = described_class.new( + configuration: configuration, + level: :info, + body: "User %s has logged in!", + attributes: attributes + ) + + hash = event.to_hash + + expect(hash[:attributes]).to have_key("sentry.message.template") + expect(hash[:attributes]["sentry.message.template"]).to eq({ value: "User %s has logged in!", type: "string" }) + expect(hash[:attributes]["sentry.message.parameter.0"]).to eq({ value: "John", type: "string" }) + end + it "serializes different attribute types correctly" do attributes = { "string_attr" => "string value",