solarwinds_apm 5.1.9 → 6.0.0.preV1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/LICENSE +0 -1
- data/ext/oboe_metal/extconf.rb +19 -23
- data/ext/oboe_metal/lib/liboboe-1.0-aarch64.so.sha256 +1 -1
- data/ext/oboe_metal/lib/liboboe-1.0-alpine-aarch64.so.sha256 +1 -1
- data/ext/oboe_metal/lib/liboboe-1.0-alpine-x86_64.so.sha256 +1 -1
- data/ext/oboe_metal/lib/liboboe-1.0-x86_64.so.sha256 +1 -1
- data/ext/oboe_metal/src/VERSION +1 -1
- data/ext/oboe_metal/src/oboe_debug.h +1 -0
- data/lib/oboe_metal.rb +116 -80
- data/lib/rails/generators/solarwinds_apm/install_generator.rb +1 -2
- data/lib/rails/generators/solarwinds_apm/templates/solarwinds_apm_initializer.rb +44 -260
- data/lib/solarwinds_apm/api/current_trace_info.rb +148 -0
- data/lib/solarwinds_apm/api/tracing.rb +30 -0
- data/lib/solarwinds_apm/api/transaction_name.rb +57 -0
- data/lib/solarwinds_apm/api.rb +8 -15
- data/lib/solarwinds_apm/base.rb +4 -131
- data/lib/solarwinds_apm/config.rb +128 -175
- data/lib/solarwinds_apm/constants.rb +32 -0
- data/lib/solarwinds_apm/logger.rb +1 -1
- data/lib/solarwinds_apm/noop/context.rb +2 -5
- data/lib/solarwinds_apm/noop/metadata.rb +1 -2
- data/lib/solarwinds_apm/noop/profiling.rb +3 -7
- data/lib/solarwinds_apm/oboe_init_options.rb +71 -33
- data/lib/solarwinds_apm/opentelemetry/solarwinds_exporter.rb +204 -0
- data/lib/solarwinds_apm/opentelemetry/solarwinds_processor.rb +163 -0
- data/lib/solarwinds_apm/opentelemetry/solarwinds_propagator.rb +92 -0
- data/lib/solarwinds_apm/opentelemetry/solarwinds_response_propagator.rb +72 -0
- data/lib/solarwinds_apm/opentelemetry/solarwinds_sampler.rb +330 -0
- data/lib/solarwinds_apm/opentelemetry.rb +8 -0
- data/lib/solarwinds_apm/otel_config.rb +161 -0
- data/lib/solarwinds_apm/{inst → support}/logger_formatter.rb +5 -6
- data/lib/solarwinds_apm/{inst → support}/logging_log_event.rb +3 -6
- data/lib/solarwinds_apm/{inst → support}/lumberjack_formatter.rb +1 -4
- data/lib/solarwinds_apm/support/oboe_tracing_mode.rb +27 -0
- data/lib/solarwinds_apm/support/swomarginalia/LICENSE +20 -0
- data/lib/solarwinds_apm/support/swomarginalia/README.md +41 -0
- data/lib/solarwinds_apm/support/swomarginalia/comment.rb +205 -0
- data/lib/solarwinds_apm/support/swomarginalia/load_swomarginalia.rb +48 -0
- data/lib/solarwinds_apm/support/swomarginalia/railtie.rb +22 -0
- data/lib/solarwinds_apm/support/swomarginalia/swomarginalia.rb +86 -0
- data/lib/solarwinds_apm/support/transaction_cache.rb +24 -0
- data/lib/solarwinds_apm/support/transaction_settings.rb +26 -209
- data/lib/solarwinds_apm/support/transformer.rb +56 -0
- data/lib/solarwinds_apm/support/txn_name_manager.rb +25 -0
- data/lib/solarwinds_apm/support/x_trace_options.rb +42 -26
- data/lib/solarwinds_apm/support.rb +33 -10
- data/lib/solarwinds_apm/support_report.rb +10 -32
- data/lib/solarwinds_apm/thread_local.rb +1 -1
- data/lib/solarwinds_apm/version.rb +4 -4
- data/lib/solarwinds_apm.rb +31 -26
- metadata +76 -121
- data/.dockerignore +0 -5
- data/.gitignore +0 -58
- data/.rubocop.yml +0 -29
- data/.whitesource +0 -22
- data/.yardopts +0 -7
- data/CHANGELOG-appoptics.md +0 -766
- data/CHANGELOG.md +0 -82
- data/CONFIG.md +0 -31
- data/Gemfile +0 -15
- data/README.md +0 -385
- data/bin/solarwinds_apm_config +0 -15
- data/examples/prepend.rb +0 -13
- data/examples/sdk_examples.rb +0 -158
- data/ext/oboe_metal/README.md +0 -69
- data/ext/oboe_metal/extconf_local.rb +0 -75
- data/ext/oboe_metal/lib/.keep +0 -0
- data/ext/oboe_metal/noop/noop.c +0 -8
- data/ext/oboe_metal/src/README.md +0 -6
- data/ext/oboe_metal/src/frames.cc +0 -247
- data/ext/oboe_metal/src/frames.h +0 -40
- data/ext/oboe_metal/src/logging.cc +0 -97
- data/ext/oboe_metal/src/logging.h +0 -34
- data/ext/oboe_metal/src/profiling.cc +0 -435
- data/ext/oboe_metal/src/profiling.h +0 -78
- data/ext/oboe_metal/test/CMakeLists.txt +0 -53
- data/ext/oboe_metal/test/FindGMock.cmake +0 -43
- data/ext/oboe_metal/test/README.md +0 -56
- data/ext/oboe_metal/test/frames_test.cc +0 -164
- data/ext/oboe_metal/test/profiling_test.cc +0 -93
- data/ext/oboe_metal/test/ruby_inc_dir.rb +0 -8
- data/ext/oboe_metal/test/ruby_prefix.rb +0 -8
- data/ext/oboe_metal/test/ruby_test_helper.rb +0 -67
- data/ext/oboe_metal/test/test.h +0 -11
- data/ext/oboe_metal/test/test_main.cc +0 -32
- data/init.rb +0 -4
- data/lib/solarwinds_apm/api/layerinit.rb +0 -41
- data/lib/solarwinds_apm/api/logging.rb +0 -356
- data/lib/solarwinds_apm/api/memcache.rb +0 -37
- data/lib/solarwinds_apm/api/metrics.rb +0 -63
- data/lib/solarwinds_apm/api/util.rb +0 -98
- data/lib/solarwinds_apm/frameworks/grape.rb +0 -96
- data/lib/solarwinds_apm/frameworks/padrino.rb +0 -78
- data/lib/solarwinds_apm/frameworks/rails/inst/action_controller.rb +0 -100
- data/lib/solarwinds_apm/frameworks/rails/inst/action_controller5.rb +0 -50
- data/lib/solarwinds_apm/frameworks/rails/inst/action_controller_api.rb +0 -50
- data/lib/solarwinds_apm/frameworks/rails/inst/action_view.rb +0 -88
- data/lib/solarwinds_apm/frameworks/rails/inst/active_record.rb +0 -26
- data/lib/solarwinds_apm/frameworks/rails/inst/connection_adapters/mysql2.rb +0 -29
- data/lib/solarwinds_apm/frameworks/rails/inst/connection_adapters/postgresql.rb +0 -22
- data/lib/solarwinds_apm/frameworks/rails/inst/connection_adapters/utils5x.rb +0 -103
- data/lib/solarwinds_apm/frameworks/rails/inst/logger_formatters.rb +0 -14
- data/lib/solarwinds_apm/frameworks/rails.rb +0 -100
- data/lib/solarwinds_apm/frameworks/sinatra.rb +0 -96
- data/lib/solarwinds_apm/inst/bunny-client.rb +0 -157
- data/lib/solarwinds_apm/inst/bunny-consumer.rb +0 -102
- data/lib/solarwinds_apm/inst/curb.rb +0 -289
- data/lib/solarwinds_apm/inst/dalli.rb +0 -89
- data/lib/solarwinds_apm/inst/delayed_job.rb +0 -100
- data/lib/solarwinds_apm/inst/excon.rb +0 -113
- data/lib/solarwinds_apm/inst/faraday.rb +0 -96
- data/lib/solarwinds_apm/inst/graphql.rb +0 -206
- data/lib/solarwinds_apm/inst/grpc_client.rb +0 -147
- data/lib/solarwinds_apm/inst/grpc_server.rb +0 -119
- data/lib/solarwinds_apm/inst/httpclient.rb +0 -182
- data/lib/solarwinds_apm/inst/memcached.rb +0 -86
- data/lib/solarwinds_apm/inst/mongo.rb +0 -246
- data/lib/solarwinds_apm/inst/mongo2.rb +0 -225
- data/lib/solarwinds_apm/inst/moped.rb +0 -466
- data/lib/solarwinds_apm/inst/net_http.rb +0 -60
- data/lib/solarwinds_apm/inst/rack.rb +0 -223
- data/lib/solarwinds_apm/inst/rack_cache.rb +0 -35
- data/lib/solarwinds_apm/inst/redis.rb +0 -280
- data/lib/solarwinds_apm/inst/redis_v4.rb +0 -273
- data/lib/solarwinds_apm/inst/resque.rb +0 -129
- data/lib/solarwinds_apm/inst/rest-client.rb +0 -43
- data/lib/solarwinds_apm/inst/sequel.rb +0 -241
- data/lib/solarwinds_apm/inst/sidekiq-client.rb +0 -63
- data/lib/solarwinds_apm/inst/sidekiq-worker.rb +0 -64
- data/lib/solarwinds_apm/inst/typhoeus.rb +0 -90
- data/lib/solarwinds_apm/instrumentation.rb +0 -22
- data/lib/solarwinds_apm/loading.rb +0 -65
- data/lib/solarwinds_apm/ruby.rb +0 -35
- data/lib/solarwinds_apm/sdk/current_trace_info.rb +0 -123
- data/lib/solarwinds_apm/sdk/custom_metrics.rb +0 -94
- data/lib/solarwinds_apm/sdk/logging.rb +0 -37
- data/lib/solarwinds_apm/sdk/trace_context_headers.rb +0 -69
- data/lib/solarwinds_apm/sdk/tracing.rb +0 -432
- data/lib/solarwinds_apm/support/profiling.rb +0 -25
- data/lib/solarwinds_apm/support/trace_context.rb +0 -53
- data/lib/solarwinds_apm/support/trace_state.rb +0 -69
- data/lib/solarwinds_apm/support/trace_string.rb +0 -89
- data/lib/solarwinds_apm/support/transaction_metrics.rb +0 -67
- data/lib/solarwinds_apm/test.rb +0 -165
- data/lib/solarwinds_apm/util.rb +0 -426
- data/log/.keep +0 -0
- data/log/postgresql/.keep +0 -0
- data/solarwinds_apm.gemspec +0 -55
- data/yardoc_frontpage.md +0 -24
@@ -1,233 +1,50 @@
|
|
1
1
|
# Copyright (c) 2018 SolarWinds, LLC.
|
2
2
|
# All rights reserved.
|
3
3
|
#
|
4
|
-
|
5
|
-
AO_TRACING_ENABLED = 1
|
6
|
-
AO_TRACING_DISABLED = 0
|
7
|
-
AO_TRACING_UNSET = -1
|
8
|
-
|
9
|
-
AO_TRACING_DECISIONS_OK = 0
|
10
|
-
|
11
|
-
OBOE_SETTINGS_UNSET = -1
|
12
|
-
|
13
4
|
module SolarWindsAPM
|
14
5
|
##
|
15
6
|
# This module helps with setting up the transaction filters and applying them
|
16
7
|
#
|
17
8
|
class TransactionSettings
|
9
|
+
SWO_TRACING_ENABLED = 1
|
10
|
+
SWO_TRACING_DISABLED = 0
|
18
11
|
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
@do_metrics = false
|
24
|
-
@do_sample = false
|
25
|
-
@do_propagate = true
|
26
|
-
|
27
|
-
SolarWindsAPM.trace_context = SolarWindsAPM::TraceContext.new(headers)
|
28
|
-
@tracestring = SolarWindsAPM.trace_context.tracestring
|
29
|
-
@sw_member_value = SolarWindsAPM.trace_context.sw_member_value
|
30
|
-
tracing_mode = AO_TRACING_ENABLED
|
31
|
-
|
32
|
-
# TODO
|
33
|
-
# NH-11132 will address this
|
34
|
-
# incoming tracing info has priority over existing context
|
35
|
-
# if SolarWindsAPM::Context.isValid && !@sw_member_value
|
36
|
-
# @do_sample = SolarWindsAPM.tracing?
|
37
|
-
# return
|
38
|
-
# end
|
39
|
-
|
40
|
-
if url && asset?(url)
|
41
|
-
@do_propagate = false
|
42
|
-
return
|
43
|
-
end
|
44
|
-
|
45
|
-
if tracing_mode_disabled? && !tracing_enabled?(url) ||
|
46
|
-
tracing_disabled?(url)
|
47
|
-
|
48
|
-
tracing_mode = AO_TRACING_DISABLED
|
49
|
-
end
|
50
|
-
|
51
|
-
# args (all optional)
|
52
|
-
# 0 char const *in_xtrace
|
53
|
-
# 1 char const *tracestate
|
54
|
-
# 2 int custom_tracing_mode
|
55
|
-
# 3 int custom_sample_rate
|
56
|
-
# 4 int request_type
|
57
|
-
# 5 int custom_trigger_mode
|
58
|
-
# 6 char const *header_options
|
59
|
-
# 7 char const *header_signature
|
60
|
-
# 8 long header_timestamp
|
61
|
-
args = [@tracestring, @sw_member_value] #0,1
|
62
|
-
args << tracing_mode #2
|
63
|
-
args << (SolarWindsAPM::Config[:sample_rate] || OBOE_SETTINGS_UNSET) #3
|
64
|
-
|
65
|
-
if options && (options.options || options.signature)
|
66
|
-
args << (options.trigger_trace ? 1 : 0) #4
|
67
|
-
args << (trigger_tracing_mode_disabled? ? 0 : 1) #5
|
68
|
-
args << options.options #6
|
69
|
-
args << options.signature #7
|
70
|
-
args << options.timestamp #8
|
71
|
-
end
|
72
|
-
|
73
|
-
metrics, sample, @rate, @source, @bucket_rate, @bucket_cap, @type, @auth, @status_msg, @auth_msg, @status =
|
74
|
-
SolarWindsAPM::Context.getDecisions(*args)
|
75
|
-
|
76
|
-
if @status > AO_TRACING_DECISIONS_OK
|
77
|
-
SolarWindsAPM.logger.warn "[solarwinds_apm/sample] Problem getting the sampling decisions: #{@status_msg} code: #{@status}"
|
78
|
-
end
|
79
|
-
|
80
|
-
@do_metrics = metrics > 0
|
81
|
-
@do_sample = sample > 0
|
82
|
-
end
|
83
|
-
|
84
|
-
def to_s
|
85
|
-
"do_propagate: #{do_propagate}, do_sample: #{do_sample}, do_metrics: #{do_metrics} rate: #{rate}, source: #{source}"
|
86
|
-
end
|
87
|
-
|
88
|
-
def add_kvs(kvs)
|
89
|
-
kvs[:SampleRate] = @rate
|
90
|
-
kvs[:SampleSource] = @source
|
91
|
-
end
|
92
|
-
|
93
|
-
def triggered_trace?
|
94
|
-
@type == 1
|
12
|
+
def initialize(url: '', name: '', kind: '')
|
13
|
+
@url = url
|
14
|
+
@name = name
|
15
|
+
@kind = kind
|
95
16
|
end
|
96
17
|
|
97
|
-
|
98
|
-
|
99
|
-
|
18
|
+
# calculate trace mode to set either 1 or 0 based on url and name+kind
|
19
|
+
# first check if url match, if not match, then match the name+kind
|
20
|
+
def calculate_trace_mode
|
21
|
+
tracing_mode_enabled? && tracing_enabled? ? SWO_TRACING_ENABLED : SWO_TRACING_DISABLED
|
100
22
|
end
|
101
23
|
|
102
24
|
private
|
103
25
|
|
104
|
-
|
105
|
-
|
106
|
-
def tracing_mode_disabled?
|
107
|
-
SolarWindsAPM::Config[:tracing_mode] &&
|
108
|
-
[:disabled, :never].include?(SolarWindsAPM::Config[:tracing_mode])
|
26
|
+
def tracing_mode_enabled?
|
27
|
+
SolarWindsAPM::Config[:tracing_mode] && ![:disabled, :never].include?(SolarWindsAPM::Config[:tracing_mode])
|
109
28
|
end
|
110
29
|
|
111
|
-
|
112
|
-
|
113
|
-
#
|
114
|
-
# Given a path, this method determines whether it matches any of the
|
115
|
-
# regexps to exclude it from metrics and traces
|
116
|
-
#
|
117
|
-
def tracing_enabled?(url)
|
118
|
-
return false unless SolarWindsAPM::Config[:url_enabled_regexps].is_a? Array
|
119
|
-
# once we only support Ruby >= 2.4.0 use `match?` instead of `=~`
|
120
|
-
return SolarWindsAPM::Config[:url_enabled_regexps].any? { |regex| regex =~ url }
|
121
|
-
rescue => e
|
122
|
-
SolarWindsAPM.logger.warn "[SolarWindsAPM/filter] Could not apply :enabled filter to path. #{e.inspect}"
|
123
|
-
true
|
124
|
-
end
|
125
|
-
|
126
|
-
##
|
127
|
-
# tracing_disabled?
|
128
|
-
#
|
129
|
-
# Given a path, this method determines whether it matches any of the
|
130
|
-
# regexps to exclude it from metrics and traces
|
131
|
-
#
|
132
|
-
def tracing_disabled?(url)
|
133
|
-
return false unless SolarWindsAPM::Config[:url_disabled_regexps].is_a? Array
|
134
|
-
# once we only support Ruby >= 2.4.0 use `match?` instead of `=~`
|
135
|
-
return SolarWindsAPM::Config[:url_disabled_regexps].any? { |regex| regex =~ url }
|
136
|
-
rescue => e
|
137
|
-
SolarWindsAPM.logger.warn "[SolarWindsAPM/filter] Could not apply :disabled filter to path. #{e.inspect}"
|
138
|
-
false
|
139
|
-
end
|
140
|
-
|
141
|
-
def trigger_tracing_mode_disabled?
|
142
|
-
SolarWindsAPM::Config[:trigger_tracing_mode] &&
|
143
|
-
SolarWindsAPM::Config[:trigger_tracing_mode] == :disabled
|
144
|
-
end
|
145
|
-
|
146
|
-
##
|
147
|
-
# asset?
|
148
|
-
#
|
149
|
-
# Given a path, this method determines whether it is a static asset
|
150
|
-
#
|
151
|
-
def asset?(path)
|
152
|
-
return false unless SolarWindsAPM::Config[:dnt_compiled]
|
153
|
-
# once we only support Ruby >= 2.4.0 use `match?` instead of `=~`
|
154
|
-
return SolarWindsAPM::Config[:dnt_compiled] =~ path
|
155
|
-
rescue => e
|
156
|
-
SolarWindsAPM.logger.warn "[SolarWindsAPM/filter] Could not apply do-not-trace filter to path. #{e.inspect}"
|
157
|
-
false
|
158
|
-
end
|
159
|
-
|
160
|
-
public
|
161
|
-
|
162
|
-
class << self
|
30
|
+
def tracing_enabled?
|
31
|
+
span_layer = "#{@name}:#{@kind}"
|
163
32
|
|
164
|
-
|
165
|
-
|
166
|
-
# once we only support Ruby >= 2.4.0 use `match?` instead of `=~`
|
167
|
-
return SolarWindsAPM::Config[:dnt_compiled] =~ path
|
168
|
-
rescue => e
|
169
|
-
SolarWindsAPM.logger.warn "[SolarWindsAPM/filter] Could not apply do-not-trace filter to path. #{e.inspect}"
|
170
|
-
false
|
171
|
-
end
|
33
|
+
enabled_regexps = SolarWindsAPM::Config[:enabled_regexps]
|
34
|
+
disabled_regexps = SolarWindsAPM::Config[:disabled_regexps]
|
172
35
|
|
173
|
-
|
174
|
-
|
175
|
-
reset_url_regexps
|
176
|
-
return
|
177
|
-
end
|
36
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] enabled_regexps: #{enabled_regexps&.inspect}"}
|
37
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] disabled_regexps: #{disabled_regexps&.inspect}"}
|
178
38
|
|
179
|
-
|
180
|
-
|
181
|
-
|
39
|
+
return false if disabled_regexps.is_a?(Array) && disabled_regexps.any? { |regex| regex.match?(@url) }
|
40
|
+
return true if enabled_regexps.is_a?(Array) && enabled_regexps.any? { |regex| regex.match?(@url) }
|
41
|
+
return false if disabled_regexps.is_a?(Array) && disabled_regexps.any? { |regex| regex.match?(span_layer) }
|
42
|
+
return true if enabled_regexps.is_a?(Array) && enabled_regexps.any? { |regex| regex.match?(span_layer) }
|
182
43
|
|
183
|
-
|
184
|
-
|
185
|
-
|
186
|
-
|
187
|
-
def compile_regexp(settings)
|
188
|
-
regexp_regexp = compile_url_settings_regexp(settings)
|
189
|
-
extensions_regexp = compile_url_settings_extensions(settings)
|
190
|
-
|
191
|
-
regexps = [regexp_regexp, extensions_regexp].flatten.compact
|
192
|
-
|
193
|
-
regexps.empty? ? nil : regexps
|
194
|
-
end
|
195
|
-
|
196
|
-
def compile_url_settings_regexp(value)
|
197
|
-
regexps = value.select do |v|
|
198
|
-
v.key?(:regexp) &&
|
199
|
-
!(v[:regexp].is_a?(String) && v[:regexp].empty?) &&
|
200
|
-
!(v[:regexp].is_a?(Regexp) && v[:regexp].inspect == '//')
|
201
|
-
end
|
202
|
-
|
203
|
-
regexps.map! do |v|
|
204
|
-
begin
|
205
|
-
v[:regexp].is_a?(String) ? Regexp.new(v[:regexp], v[:opts]) : Regexp.new(v[:regexp])
|
206
|
-
rescue
|
207
|
-
SolarWindsAPM.logger.warn "[solarwinds_apm/config] Problem compiling transaction_settings item #{v}, will ignore."
|
208
|
-
nil
|
209
|
-
end
|
210
|
-
end
|
211
|
-
regexps.keep_if { |v| !v.nil? }
|
212
|
-
regexps.empty? ? nil : regexps
|
213
|
-
end
|
214
|
-
|
215
|
-
def compile_url_settings_extensions(value)
|
216
|
-
extensions = value.select do |v|
|
217
|
-
v.key?(:extensions) &&
|
218
|
-
v[:extensions].is_a?(Array) &&
|
219
|
-
!v[:extensions].empty?
|
220
|
-
end
|
221
|
-
extensions = extensions.map { |v| v[:extensions] }.flatten
|
222
|
-
extensions.keep_if { |v| v.is_a?(String) }
|
223
|
-
|
224
|
-
extensions.empty? ? nil : Regexp.new("(#{Regexp.union(extensions).source})(\\?.+){0,1}$")
|
225
|
-
end
|
226
|
-
|
227
|
-
def reset_url_regexps
|
228
|
-
SolarWindsAPM::Config[:url_enabled_regexps] = nil
|
229
|
-
SolarWindsAPM::Config[:url_disabled_regexps] = nil
|
230
|
-
end
|
44
|
+
true
|
45
|
+
rescue StandardError => e
|
46
|
+
SolarWindsAPM.logger.warn {"[#{self.class}/#{__method__}] Could not determine tracing status for #{kind}. #{e.inspect}. transaction_settings regexps/extensions igonred/unfiltered."}
|
47
|
+
true
|
231
48
|
end
|
232
49
|
end
|
233
50
|
end
|
@@ -0,0 +1,56 @@
|
|
1
|
+
module SolarWindsAPM
|
2
|
+
module OpenTelemetry
|
3
|
+
# Transformer
|
4
|
+
class Transformer
|
5
|
+
VERSION = '00'.freeze
|
6
|
+
|
7
|
+
def self.sw_from_context(span_context)
|
8
|
+
flag = span_context.trace_flags.sampled?? 1 : 0
|
9
|
+
"#{span_context.hex_span_id}-0#{flag}"
|
10
|
+
end
|
11
|
+
|
12
|
+
def self.trace_state_header(trace_state)
|
13
|
+
arr = []
|
14
|
+
trace_state.to_h.each do |key, value|
|
15
|
+
arr << "#{key}=#{value}"
|
16
|
+
end
|
17
|
+
arr.join(",")
|
18
|
+
end
|
19
|
+
|
20
|
+
# Generates a liboboe W3C compatible trace_context from provided OTel span context.
|
21
|
+
def self.traceparent_from_context(span_context)
|
22
|
+
flag = span_context.trace_flags.sampled?? 1 : 0
|
23
|
+
xtr = "#{VERSION}-#{span_context.hex_trace_id}-#{span_context.hex_span_id}-0#{flag}"
|
24
|
+
SolarWindsAPM.logger.debug("Generated traceparent #{xtr} from #{span_context.inspect}")
|
25
|
+
xtr
|
26
|
+
end
|
27
|
+
|
28
|
+
# Formats tracestate sw value from span_id and liboboe decision as 16-byte span_id with 8-bit trace_flags
|
29
|
+
# e.g. 1a2b3c4d5e6f7g8h-01
|
30
|
+
def self.sw_from_span_and_decision(span_id, decision)
|
31
|
+
[span_id, decision].join("-")
|
32
|
+
end
|
33
|
+
|
34
|
+
# trace_flags [Integer]
|
35
|
+
def self.trace_flags_from_int(trace_flags)
|
36
|
+
"0#{trace_flags}"
|
37
|
+
end
|
38
|
+
|
39
|
+
def self.trace_flags_from_boolean(trace_flags)
|
40
|
+
trace_flags == true ? "01" : "00"
|
41
|
+
end
|
42
|
+
|
43
|
+
def self.sampled?(decision)
|
44
|
+
decision == ::OpenTelemetry::SDK::Trace::Samplers::Decision::RECORD_AND_SAMPLE
|
45
|
+
end
|
46
|
+
|
47
|
+
def self.span_id_from_sw(sw_value)
|
48
|
+
sw_value.split("-")[0]
|
49
|
+
end
|
50
|
+
|
51
|
+
def self.create_key(name_)
|
52
|
+
::OpenTelemetry::Context.create_key(name_)
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
module SolarWindsAPM
|
2
|
+
module OpenTelemetry
|
3
|
+
# SolarWindsTxnNameManager
|
4
|
+
class TxnNameManager
|
5
|
+
def initialize
|
6
|
+
@cache = {}
|
7
|
+
end
|
8
|
+
|
9
|
+
def get(key)
|
10
|
+
@cache[key]
|
11
|
+
end
|
12
|
+
|
13
|
+
def del(key)
|
14
|
+
@cache.delete(key)
|
15
|
+
end
|
16
|
+
|
17
|
+
def set(key, value)
|
18
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] current cache #{@cache.inspect}"}
|
19
|
+
@cache[key] = value
|
20
|
+
end
|
21
|
+
|
22
|
+
alias []= set
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
@@ -2,10 +2,10 @@
|
|
2
2
|
# All rights reserved.
|
3
3
|
|
4
4
|
module SolarWindsAPM
|
5
|
+
# XTraceOptions
|
5
6
|
class XTraceOptions
|
6
|
-
|
7
|
-
|
8
|
-
attr_reader :sw_keys, :custom_kvs, :ignored # used in tests
|
7
|
+
attr_reader :options, :signature, :trigger_trace, :timestamp,
|
8
|
+
:sw_keys, :custom_kvs, :ignored
|
9
9
|
|
10
10
|
##
|
11
11
|
# use by Trigger Tracing
|
@@ -33,16 +33,20 @@ module SolarWindsAPM
|
|
33
33
|
# - ts (unix timestamp)
|
34
34
|
# - other keys will be reported in the response options as ignored
|
35
35
|
|
36
|
-
|
37
|
-
|
38
|
-
|
36
|
+
SW_XTRACEOPTIONS_RESPONSE_KEY = 'xtrace_options_response'.freeze
|
37
|
+
|
38
|
+
def initialize(context)
|
39
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] x_trace_options context: #{context.inspect}"}
|
40
|
+
@context = context.dup
|
39
41
|
@trigger_trace = false
|
40
42
|
@custom_kvs = {}
|
41
43
|
@sw_keys = nil
|
42
44
|
@ignored = []
|
43
45
|
@timestamp = 0
|
46
|
+
@options = options_header
|
47
|
+
@signature = obtain_signature
|
44
48
|
|
45
|
-
options&.split(/;+/)&.each do |val|
|
49
|
+
@options&.split(/;+/)&.each do |val|
|
46
50
|
k = val.split('=', 2)
|
47
51
|
|
48
52
|
next unless k[0] # it can be nil, eg when the header starts with ';'
|
@@ -57,19 +61,19 @@ module SolarWindsAPM
|
|
57
61
|
end
|
58
62
|
when 'sw-keys'
|
59
63
|
if @sw_keys
|
60
|
-
SolarWindsAPM.logger.info "[
|
64
|
+
SolarWindsAPM.logger.info {"[#{self.class}/#{__method__}] Duplicate key: #{k[0]}"}
|
61
65
|
else
|
62
66
|
@sw_keys = k[1].strip
|
63
67
|
end
|
64
68
|
when /^custom-[^\s]*$/
|
65
69
|
if @custom_kvs[k[0]]
|
66
|
-
SolarWindsAPM.logger.info "[
|
70
|
+
SolarWindsAPM.logger.info {"[#{self.class}/#{__method__}] Duplicate key: #{k[0]}"}
|
67
71
|
else
|
68
72
|
@custom_kvs[k[0]] = k[1].strip
|
69
73
|
end
|
70
74
|
when 'ts'
|
71
75
|
if @timestamp > 0
|
72
|
-
SolarWindsAPM.logger.info "[
|
76
|
+
SolarWindsAPM.logger.info {"[#{self.class}/#{__method__}] Duplicate key: #{k[0]}"}
|
73
77
|
else
|
74
78
|
@timestamp = k[1].to_i
|
75
79
|
end
|
@@ -77,10 +81,7 @@ module SolarWindsAPM
|
|
77
81
|
@ignored << k[0]
|
78
82
|
end
|
79
83
|
end
|
80
|
-
unless @ignored.empty?
|
81
|
-
msg = "[solarwinds_apm/x-trace-options] Some keys were ignored: #{@ignored.join(',')}"
|
82
|
-
SolarWindsAPM.logger.info(msg)
|
83
|
-
end
|
84
|
+
SolarWindsAPM.logger.info("[#{self.class}/#{__method__}] Some keys were ignored: #{@ignored.join(',')}") unless @ignored.empty?
|
84
85
|
end
|
85
86
|
|
86
87
|
def add_kvs(kvs, settings)
|
@@ -91,23 +92,38 @@ module SolarWindsAPM
|
|
91
92
|
kvs['TriggeredTrace'] = true if settings.triggered_trace?
|
92
93
|
end
|
93
94
|
|
94
|
-
def
|
95
|
-
|
95
|
+
def obtain_signature
|
96
|
+
# INTL_SWO_SIGNATURE_KEY = sw_signature
|
97
|
+
signature = obtain_sw_value(SolarWindsAPM::Constants::INTL_SWO_SIGNATURE_KEY)
|
98
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] x_trace_options option_signature: #{signature}"}
|
99
|
+
signature
|
100
|
+
end
|
96
101
|
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
102
|
+
def options_header
|
103
|
+
# INTL_SWO_X_OPTIONS_KEY = sw_xtraceoptions
|
104
|
+
header = obtain_sw_value(SolarWindsAPM::Constants::INTL_SWO_X_OPTIONS_KEY)
|
105
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] x_trace_options option_header: #{header}"}
|
106
|
+
header
|
107
|
+
end
|
108
|
+
|
109
|
+
def obtain_sw_value(type)
|
110
|
+
sw_value = nil
|
111
|
+
instance_variable = @context&.instance_variable_get("@entries")
|
112
|
+
instance_variable&.each do |key, value|
|
113
|
+
if key.instance_of?(::String)
|
114
|
+
sw_value = value if key == type
|
115
|
+
SolarWindsAPM.logger.debug {"[#{self.class}/#{__method__}] obtained sw value: #{type} #{key}: #{value.inspect}"}
|
104
116
|
end
|
105
|
-
response << "trigger-trace=#{trigger_msg}"
|
106
|
-
response << "ignored=#{@ignored.join(',')}" unless @ignored.empty?
|
107
117
|
end
|
118
|
+
sw_value
|
119
|
+
end
|
108
120
|
|
109
|
-
|
121
|
+
def intify_trigger_trace
|
122
|
+
@trigger_trace ? 1 : 0
|
110
123
|
end
|
111
124
|
|
125
|
+
def self.sw_xtraceoptions_response_key
|
126
|
+
SW_XTRACEOPTIONS_RESPONSE_KEY
|
127
|
+
end
|
112
128
|
end
|
113
129
|
end
|
@@ -1,13 +1,36 @@
|
|
1
|
-
# Copyright (c) SolarWinds, LLC.
|
2
|
-
# All rights reserved
|
1
|
+
# Copyright (c) 2023 SolarWinds, LLC.
|
2
|
+
# All rights reserved.
|
3
|
+
#
|
4
|
+
# This file is for loading support library
|
5
|
+
#
|
3
6
|
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
7
|
+
require_relative './support/logger_formatter'
|
8
|
+
require_relative './support/logging_log_event'
|
9
|
+
require_relative './support/lumberjack_formatter'
|
10
|
+
require_relative './support/transaction_cache'
|
11
|
+
require_relative './support/transaction_settings'
|
12
|
+
require_relative './support/oboe_tracing_mode'
|
13
|
+
require_relative './support/txn_name_manager'
|
14
|
+
require_relative './support/transformer'
|
15
|
+
require_relative './support/x_trace_options'
|
16
|
+
|
17
|
+
if SolarWindsAPM::Config[:tag_sql]
|
18
|
+
if defined?(::Rails)
|
19
|
+
if ::Rails.version < '7'
|
20
|
+
require_relative './support/swomarginalia/railtie'
|
21
|
+
elsif ::Rails.version >= '7'
|
22
|
+
# User has to define in their config/environments:
|
23
|
+
# config.active_record.query_log_tags = [
|
24
|
+
# {
|
25
|
+
# tracecontext: -> {
|
26
|
+
# SolarWindsAPM::SWOMarginalia::Comment.traceparent
|
27
|
+
# }
|
28
|
+
# }
|
29
|
+
# ]
|
30
|
+
require_relative './support/swomarginalia/comment'
|
31
|
+
end
|
32
|
+
else
|
33
|
+
require_relative './support/swomarginalia/load_swomarginalia'
|
34
|
+
SolarWindsAPM::SWOMarginalia::LoadSWOMarginalia.insert
|
12
35
|
end
|
13
36
|
end
|
@@ -14,33 +14,23 @@ module SolarWindsAPM
|
|
14
14
|
# yesno
|
15
15
|
#
|
16
16
|
# Utility method to translate value/nil to "yes"/"no" strings
|
17
|
-
def self.yesno(
|
18
|
-
|
17
|
+
def self.yesno(condition)
|
18
|
+
condition ? 'yes' : 'no'
|
19
19
|
end
|
20
20
|
|
21
|
-
# rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity, Metrics/AbcSize
|
22
21
|
def self.support_report
|
23
22
|
@logger_level = SolarWindsAPM.logger.level
|
24
23
|
SolarWindsAPM.logger.level = ::Logger::DEBUG
|
25
24
|
|
26
25
|
SolarWindsAPM.logger.warn '********************************************************'
|
27
26
|
SolarWindsAPM.logger.warn '* BEGIN SolarWindsAPM Support Report'
|
28
|
-
SolarWindsAPM.logger.warn '* Please email the output of this report to
|
27
|
+
SolarWindsAPM.logger.warn '* Please email the output of this report to SWO-support@solarwinds.com'
|
29
28
|
SolarWindsAPM.logger.warn '********************************************************'
|
30
29
|
SolarWindsAPM.logger.warn "Ruby: #{RUBY_DESCRIPTION}"
|
31
|
-
SolarWindsAPM.logger.warn "
|
32
|
-
SolarWindsAPM.logger.warn "
|
33
|
-
SolarWindsAPM.logger.warn "$2: #{$2}" unless $2.nil?
|
34
|
-
SolarWindsAPM.logger.warn "$3: #{$3}" unless $3.nil?
|
35
|
-
SolarWindsAPM.logger.warn "$4: #{$4}" unless $4.nil?
|
30
|
+
SolarWindsAPM.logger.warn "PROGRAM_NAME: #{$PROGRAM_NAME}" # replace $0 to get executing script
|
31
|
+
SolarWindsAPM.logger.warn "ARGV: #{ARGV.inspect}"
|
36
32
|
SolarWindsAPM.logger.warn "SolarWindsAPM.loaded == #{SolarWindsAPM.loaded}"
|
37
33
|
|
38
|
-
on_heroku = SolarWindsAPM.heroku?
|
39
|
-
SolarWindsAPM.logger.warn "On Heroku?: #{yesno(on_heroku)}"
|
40
|
-
if on_heroku
|
41
|
-
SolarWindsAPM.logger.warn "SW_APM_URL: #{ENV['SW_APM_URL']}"
|
42
|
-
end
|
43
|
-
|
44
34
|
SolarWindsAPM.logger.warn "SolarWindsAPM::Ruby defined?: #{yesno(defined?(SolarWindsAPM::Ruby))}"
|
45
35
|
SolarWindsAPM.logger.warn "SolarWindsAPM.reporter: #{SolarWindsAPM.reporter}"
|
46
36
|
|
@@ -52,9 +42,7 @@ module SolarWindsAPM
|
|
52
42
|
SolarWindsAPM.logger.warn "Using Rails?: #{yesno(using_rails)}"
|
53
43
|
if using_rails
|
54
44
|
SolarWindsAPM.logger.warn "SolarWindsAPM::Rails loaded?: #{yesno(defined?(SolarWindsAPM::Rails))}"
|
55
|
-
if defined?(SolarWindsAPM::Rack)
|
56
|
-
SolarWindsAPM.logger.warn "SolarWindsAPM::Rack middleware loaded?: #{yesno(::Rails.configuration.middleware.include? SolarWindsAPM::Rack)}"
|
57
|
-
end
|
45
|
+
SolarWindsAPM.logger.warn "SolarWindsAPM::Rack middleware loaded?: #{yesno(::Rails.configuration.middleware.include?(SolarWindsAPM::Rack))}" if defined?(SolarWindsAPM::Rack)
|
58
46
|
end
|
59
47
|
|
60
48
|
using_sinatra = defined?(::Sinatra)
|
@@ -80,34 +68,24 @@ module SolarWindsAPM
|
|
80
68
|
SolarWindsAPM.logger.warn '********************************************************'
|
81
69
|
SolarWindsAPM.logger.warn '* SolarWindsAPM::Config Values'
|
82
70
|
SolarWindsAPM.logger.warn '********************************************************'
|
83
|
-
SolarWindsAPM::Config.print_config
|
84
71
|
|
85
72
|
SolarWindsAPM.logger.warn '********************************************************'
|
86
73
|
SolarWindsAPM.logger.warn '* OS, Platform + Env'
|
87
74
|
SolarWindsAPM.logger.warn '********************************************************'
|
88
|
-
SolarWindsAPM.logger.warn "host_os:
|
89
|
-
SolarWindsAPM.logger.warn "sitearch:
|
90
|
-
SolarWindsAPM.logger.warn "arch:
|
75
|
+
SolarWindsAPM.logger.warn "host_os: #{RbConfig::CONFIG['host_os']}"
|
76
|
+
SolarWindsAPM.logger.warn "sitearch: #{RbConfig::CONFIG['sitearch']}"
|
77
|
+
SolarWindsAPM.logger.warn "arch: #{RbConfig::CONFIG['arch']}"
|
91
78
|
SolarWindsAPM.logger.warn RUBY_PLATFORM
|
92
79
|
SolarWindsAPM.logger.warn "RACK_ENV: #{ENV['RACK_ENV']}"
|
93
80
|
SolarWindsAPM.logger.warn "RAILS_ENV: #{ENV['RAILS_ENV']}" if using_rails
|
94
81
|
|
95
|
-
SolarWindsAPM.logger.warn '********************************************************'
|
96
|
-
SolarWindsAPM.logger.warn '* Raw __Init KVs'
|
97
|
-
SolarWindsAPM.logger.warn '********************************************************'
|
98
|
-
platform_info = SolarWindsAPM::Util.build_init_report
|
99
|
-
platform_info.each { |k,v|
|
100
|
-
SolarWindsAPM.logger.warn "#{k}: #{v}"
|
101
|
-
}
|
102
|
-
|
103
82
|
SolarWindsAPM.logger.warn '********************************************************'
|
104
83
|
SolarWindsAPM.logger.warn '* END SolarWindsAPM Support Report'
|
105
84
|
SolarWindsAPM.logger.warn '* Support Email: technicalsupport@solarwinds.com'
|
106
|
-
SolarWindsAPM.logger.warn '* Github: https://github.com/
|
85
|
+
SolarWindsAPM.logger.warn '* Github: https://github.com/solarwindscloud/swotel-ruby'
|
107
86
|
SolarWindsAPM.logger.warn '********************************************************'
|
108
87
|
|
109
88
|
SolarWindsAPM.logger.level = @logger_level
|
110
89
|
nil
|
111
90
|
end
|
112
|
-
# rubocop:enable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity, Metrics/AbcSize
|
113
91
|
end
|
@@ -6,10 +6,10 @@ module SolarWindsAPM
|
|
6
6
|
# The current version of the gem. Used mainly by
|
7
7
|
# solarwinds_apm.gemspec during gem build process
|
8
8
|
module Version
|
9
|
-
MAJOR =
|
10
|
-
MINOR =
|
11
|
-
PATCH =
|
12
|
-
PRE =
|
9
|
+
MAJOR = 6 # breaking,
|
10
|
+
MINOR = 0 # feature,
|
11
|
+
PATCH = 0 # fix => BFF
|
12
|
+
PRE = 'preV1' # for pre-releases into packagecloud, set to nil for production releases into rubygems
|
13
13
|
|
14
14
|
STRING = [MAJOR, MINOR, PATCH, PRE].compact.join('.')
|
15
15
|
end
|