scout_apm 2.6.4 → 2.6.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.markdown +10 -0
- data/gems/rails3.gemfile +1 -0
- data/lib/scout_apm.rb +2 -0
- data/lib/scout_apm/auto_instrument/instruction_sequence.rb +1 -1
- data/lib/scout_apm/background_job_integrations/legacy_sneakers.rb +55 -0
- data/lib/scout_apm/background_job_integrations/sneakers.rb +11 -11
- data/lib/scout_apm/job_record.rb +4 -2
- data/lib/scout_apm/layaway_file.rb +4 -0
- data/lib/scout_apm/layer_children_set.rb +9 -8
- data/lib/scout_apm/layer_converters/trace_converter.rb +3 -0
- data/lib/scout_apm/remote/message.rb +4 -0
- data/lib/scout_apm/serializers/app_server_load_serializer.rb +4 -0
- data/lib/scout_apm/serializers/directive_serializer.rb +4 -0
- data/lib/scout_apm/utils/marshal_logging.rb +90 -0
- data/lib/scout_apm/version.rb +1 -1
- data/test/test_helper.rb +1 -1
- data/test/unit/layer_children_set_test.rb +9 -0
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 41f15f4e7f91d0274a280b34d03697ff422963a39bcadc9f9056f6380b949603
|
4
|
+
data.tar.gz: c76090db49ba3f24ea685ccf61c0fbe17555affe556d947990cb584bb8f56bb5
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b33379d021bbb49e1c2c60ca0c1a72f4603539142830b92f3846e87fdf9c9d2244e73dd0be5a84fc567945ca028b62450f48dbfd6fdc0fcab81eb6d44f82bab9
|
7
|
+
data.tar.gz: 35183553754b6a56397ff10579f014abf168c1b3ef83c22318c691ba6ab2798d6a4264e7d17270b318fe43c0ea5a61ab75c025b974354b10f4f5b1395ad77bb5
|
data/CHANGELOG.markdown
CHANGED
@@ -1,3 +1,12 @@
|
|
1
|
+
# 2.6.5
|
2
|
+
|
3
|
+
* Add a tag to any requests that reach maximum number of spans (#316)
|
4
|
+
* Update testing library Mocha (#315)
|
5
|
+
* Fix case sensitivity mismatch in Job renaming (#314)
|
6
|
+
* Add support for Sneakers 2.5 (#313)
|
7
|
+
* Fix edge case with Resque instrumentation (#312)
|
8
|
+
* Fix missing source code when used with BugSnag (#308)
|
9
|
+
|
1
10
|
# 2.6.4
|
2
11
|
|
3
12
|
* Add defensive check against a nil @address in Net/HTTP instruments (#306)
|
@@ -26,6 +35,7 @@
|
|
26
35
|
# 2.5.3
|
27
36
|
|
28
37
|
* Add Que support (#265)
|
38
|
+
* Add Memcached support (#279)
|
29
39
|
|
30
40
|
# 2.5.2
|
31
41
|
|
data/gems/rails3.gemfile
CHANGED
data/lib/scout_apm.rb
CHANGED
@@ -63,6 +63,7 @@ require 'scout_apm/background_job_integrations/resque'
|
|
63
63
|
require 'scout_apm/background_job_integrations/shoryuken'
|
64
64
|
require 'scout_apm/background_job_integrations/sneakers'
|
65
65
|
require 'scout_apm/background_job_integrations/que'
|
66
|
+
require 'scout_apm/background_job_integrations/legacy_sneakers'
|
66
67
|
|
67
68
|
require 'scout_apm/framework_integrations/rails_2'
|
68
69
|
require 'scout_apm/framework_integrations/rails_3_or_4'
|
@@ -112,6 +113,7 @@ require 'scout_apm/utils/time'
|
|
112
113
|
require 'scout_apm/utils/unique_id'
|
113
114
|
require 'scout_apm/utils/numbers'
|
114
115
|
require 'scout_apm/utils/gzip_helper'
|
116
|
+
require 'scout_apm/utils/marshal_logging'
|
115
117
|
|
116
118
|
require 'scout_apm/config'
|
117
119
|
require 'scout_apm/environment'
|
@@ -8,7 +8,7 @@ module ScoutApm
|
|
8
8
|
if Rails.controller_path?(path) & !Rails.ignore?(path)
|
9
9
|
begin
|
10
10
|
new_code = Rails.rewrite(path)
|
11
|
-
return self.compile(new_code,
|
11
|
+
return self.compile(new_code, path, path)
|
12
12
|
rescue
|
13
13
|
warn "Failed to apply auto-instrumentation to #{path}: #{$!}"
|
14
14
|
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
# This is different than other BackgroundJobIntegrations and must be prepended
|
2
|
+
# manually in each job.
|
3
|
+
#
|
4
|
+
# class MyWorker
|
5
|
+
# prepend ScoutApm::BackgroundJobIntegrations::LegacySneakers
|
6
|
+
#
|
7
|
+
# def work(msg)
|
8
|
+
# ...
|
9
|
+
# end
|
10
|
+
# end
|
11
|
+
module ScoutApm
|
12
|
+
module BackgroundJobIntegrations
|
13
|
+
module LegacySneakers
|
14
|
+
UNKNOWN_QUEUE_PLACEHOLDER = 'default'.freeze
|
15
|
+
|
16
|
+
def self.prepended(base)
|
17
|
+
ScoutApm::Agent.instance.logger.info("Prepended LegacySneakers in #{base}")
|
18
|
+
end
|
19
|
+
|
20
|
+
def initialize(*args)
|
21
|
+
super
|
22
|
+
|
23
|
+
# Save off the existing value to call the correct existing work
|
24
|
+
# function in the instrumentation. But then override Sneakers to always
|
25
|
+
# use the extra-argument version, which has data Scout needs
|
26
|
+
@call_work = respond_to?(:work)
|
27
|
+
end
|
28
|
+
|
29
|
+
def work_with_params(msg, delivery_info, metadata)
|
30
|
+
queue = delivery_info[:routing_key] || UNKNOWN_QUEUE_PLACEHOLDER
|
31
|
+
job_class = self.class.name
|
32
|
+
req = ScoutApm::RequestManager.lookup
|
33
|
+
|
34
|
+
begin
|
35
|
+
req.start_layer(ScoutApm::Layer.new('Queue', queue))
|
36
|
+
started_queue = true
|
37
|
+
req.start_layer(ScoutApm::Layer.new('Job', job_class))
|
38
|
+
started_job = true
|
39
|
+
|
40
|
+
if @call_work
|
41
|
+
work(msg)
|
42
|
+
else
|
43
|
+
super
|
44
|
+
end
|
45
|
+
rescue Exception
|
46
|
+
req.error!
|
47
|
+
raise
|
48
|
+
ensure
|
49
|
+
req.stop_layer if started_job
|
50
|
+
req.stop_layer if started_queue
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
@@ -1,14 +1,22 @@
|
|
1
1
|
module ScoutApm
|
2
2
|
module BackgroundJobIntegrations
|
3
3
|
class Sneakers
|
4
|
-
attr_reader :logger
|
5
|
-
|
6
4
|
def name
|
7
5
|
:sneakers
|
8
6
|
end
|
9
7
|
|
10
8
|
def present?
|
11
|
-
defined?(::Sneakers)
|
9
|
+
defined?(::Sneakers) && supported_version?
|
10
|
+
end
|
11
|
+
|
12
|
+
# Only support Sneakers 2.7 and up
|
13
|
+
def supported_version?
|
14
|
+
result = Gem::Version.new(::Sneakers::VERSION) > Gem::Version.new("2.7.0")
|
15
|
+
ScoutApm::Agent.instance.logger.info("Skipping Sneakers instrumentation. Only versions 2.7+ are supported. See docs or contact support@scoutapm.com for instrumentation of older versions.")
|
16
|
+
result
|
17
|
+
rescue
|
18
|
+
ScoutApm::Agent.instance.logger.info("Failed comparing Sneakers Version. Skipping")
|
19
|
+
false
|
12
20
|
end
|
13
21
|
|
14
22
|
def forking?
|
@@ -69,14 +77,6 @@ module ScoutApm
|
|
69
77
|
alias_method :process_work_without_scout, :process_work
|
70
78
|
alias_method :process_work, :process_work_with_scout
|
71
79
|
end
|
72
|
-
|
73
|
-
# msg = {
|
74
|
-
# "job_class":"DummyWorker",
|
75
|
-
# "job_id":"ea23ba1c-3022-4e05-870b-c3bcb1c4f328",
|
76
|
-
# "queue_name":"default",
|
77
|
-
# "arguments":["fjdkl"],
|
78
|
-
# "locale":"en"
|
79
|
-
# }
|
80
80
|
end
|
81
81
|
|
82
82
|
ACTIVE_JOB_KLASS = 'ActiveJob::QueueAdapters::SneakersAdapter::JobWrapper'.freeze
|
data/lib/scout_apm/job_record.rb
CHANGED
@@ -32,8 +32,10 @@ module ScoutApm
|
|
32
32
|
|
33
33
|
# Modifies self and returns self, after merging in `other`.
|
34
34
|
def combine!(other)
|
35
|
-
|
36
|
-
|
35
|
+
if !self.eql?(other)
|
36
|
+
ScoutApm::Agent.instance.logger.debug("Mismatched Merge of Background Job: (Queue #{queue_name} == #{other.queue_name}) (Name #{job_name} == #{other.job_name}) (Hash #{hash} == #{other.hash})")
|
37
|
+
return self
|
38
|
+
end
|
37
39
|
|
38
40
|
@errors += other.errors
|
39
41
|
@metric_set = metric_set.combine!(other.metric_set)
|
@@ -30,6 +30,10 @@ module ScoutApm
|
|
30
30
|
|
31
31
|
def serialize(data)
|
32
32
|
Marshal.dump(data)
|
33
|
+
rescue
|
34
|
+
ScoutApm::Agent.instance.logger.info("Failed Marshalling LayawayFile")
|
35
|
+
ScoutApm::Agent.instance.logger.info(ScoutApm::Utils::MarshalLogging.new(data).dive) rescue nil
|
36
|
+
raise
|
33
37
|
end
|
34
38
|
|
35
39
|
def deserialize(data)
|
@@ -46,9 +46,15 @@ module ScoutApm
|
|
46
46
|
set = child_set(metric_type)
|
47
47
|
|
48
48
|
if set.size >= unique_cutoff
|
49
|
-
# find limited_layer
|
50
|
-
@limited_layers
|
51
|
-
@limited_layers
|
49
|
+
# find or create limited_layer
|
50
|
+
@limited_layers ||= Hash.new
|
51
|
+
layer = if @limited_layers.has_key?(metric_type)
|
52
|
+
@limited_layers[metric_type]
|
53
|
+
else
|
54
|
+
@limited_layers[metric_type] = LimitedLayer.new(metric_type)
|
55
|
+
end
|
56
|
+
|
57
|
+
layer.absorb(child)
|
52
58
|
else
|
53
59
|
# we have space just add it
|
54
60
|
set << child
|
@@ -76,10 +82,5 @@ module ScoutApm
|
|
76
82
|
def size
|
77
83
|
@children.size
|
78
84
|
end
|
79
|
-
|
80
|
-
# hold off initializing this until we know we need it
|
81
|
-
def init_limited_layers
|
82
|
-
@limited_layers ||= Hash.new { |hash, key| hash[key] = LimitedLayer.new(key) }
|
83
|
-
end
|
84
85
|
end
|
85
86
|
end
|
@@ -17,6 +17,10 @@ module ScoutApm
|
|
17
17
|
|
18
18
|
def encode
|
19
19
|
Marshal.dump(self)
|
20
|
+
rescue
|
21
|
+
ScoutApm::Agent.instance.logger.info("Failed Marshalling Remote::Message")
|
22
|
+
ScoutApm::Agent.instance.logger.info(ScoutApm::Utils::MarshalLogging.new(self).dive) rescue nil
|
23
|
+
raise
|
20
24
|
end
|
21
25
|
end
|
22
26
|
end
|
@@ -5,6 +5,10 @@ module ScoutApm
|
|
5
5
|
class AppServerLoadSerializer
|
6
6
|
def self.serialize(data)
|
7
7
|
Marshal.dump(data)
|
8
|
+
rescue
|
9
|
+
ScoutApm::Agent.instance.logger.info("Failed Marshalling AppServerLoad")
|
10
|
+
ScoutApm::Agent.instance.logger.info(ScoutApm::Utils::MarshalLogging.new(data).dive) rescue nil
|
11
|
+
raise
|
8
12
|
end
|
9
13
|
|
10
14
|
def self.deserialize(data)
|
@@ -5,6 +5,10 @@ module ScoutApm
|
|
5
5
|
class DirectiveSerializer
|
6
6
|
def self.serialize(data)
|
7
7
|
Marshal.dump(data)
|
8
|
+
rescue
|
9
|
+
ScoutApm::Agent.instance.logger.info("Failed Marshalling Directive")
|
10
|
+
ScoutApm::Agent.instance.logger.info(ScoutApm::Utils::MarshalLogging.new(data).dive) rescue nil
|
11
|
+
raise
|
8
12
|
end
|
9
13
|
|
10
14
|
def self.deserialize(data)
|
@@ -0,0 +1,90 @@
|
|
1
|
+
module ScoutApm
|
2
|
+
module Utils
|
3
|
+
class Error < StandardError; end
|
4
|
+
|
5
|
+
class InstanceVar
|
6
|
+
attr_reader :name
|
7
|
+
attr_reader :obj
|
8
|
+
|
9
|
+
def initialize(name, obj, parent)
|
10
|
+
@name = name
|
11
|
+
@obj = obj
|
12
|
+
@parent = parent
|
13
|
+
end
|
14
|
+
|
15
|
+
def to_s
|
16
|
+
"#{@name} - #{obj.class}"
|
17
|
+
end
|
18
|
+
|
19
|
+
def history
|
20
|
+
(@parent.nil? ? [] : @parent.history) + [to_s]
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
class MarshalLogging
|
25
|
+
def initialize(base_obj)
|
26
|
+
@base_obj = base_obj
|
27
|
+
end
|
28
|
+
|
29
|
+
def dive
|
30
|
+
to_investigate = [InstanceVar.new('Root', @base_obj, nil)]
|
31
|
+
max_to_check = 10000
|
32
|
+
checked = 0
|
33
|
+
|
34
|
+
while (var = to_investigate.shift)
|
35
|
+
checked += 1
|
36
|
+
if checked > max_to_check
|
37
|
+
return "Limiting Checks (max = #{max_to_check})"
|
38
|
+
end
|
39
|
+
|
40
|
+
obj = var.obj
|
41
|
+
|
42
|
+
if offending_hash?(obj)
|
43
|
+
return "Found undumpable object: #{var.history}"
|
44
|
+
end
|
45
|
+
|
46
|
+
if !dumps?(obj)
|
47
|
+
if obj.is_a? Hash
|
48
|
+
keys = obj.keys
|
49
|
+
keys.each do |key|
|
50
|
+
to_investigate.push(
|
51
|
+
InstanceVar.new(key.to_s, obj[key], var)
|
52
|
+
)
|
53
|
+
end
|
54
|
+
elsif obj.is_a? Array
|
55
|
+
obj.each_with_index do |value, idx|
|
56
|
+
to_investigate.push(
|
57
|
+
InstanceVar.new("Index #{idx}", value, var)
|
58
|
+
)
|
59
|
+
end
|
60
|
+
else
|
61
|
+
symbols = obj.instance_variables
|
62
|
+
if !symbols.any?
|
63
|
+
return "Found undumpable object: #{var.history}"
|
64
|
+
end
|
65
|
+
|
66
|
+
symbols.each do |sym|
|
67
|
+
to_investigate.push(
|
68
|
+
InstanceVar.new(sym, obj.instance_variable_get(sym), var)
|
69
|
+
)
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
true
|
76
|
+
end
|
77
|
+
|
78
|
+
def dumps?(obj)
|
79
|
+
Marshal.dump(obj)
|
80
|
+
true
|
81
|
+
rescue TypeError
|
82
|
+
false
|
83
|
+
end
|
84
|
+
|
85
|
+
def offending_hash?(obj)
|
86
|
+
obj.is_a?(Hash) && !obj.default_proc.nil?
|
87
|
+
end
|
88
|
+
end
|
89
|
+
end
|
90
|
+
end
|
data/lib/scout_apm/version.rb
CHANGED
data/test/test_helper.rb
CHANGED
@@ -71,6 +71,15 @@ class LayerChildrenSetTest < Minitest::Test
|
|
71
71
|
limited_layers.each { |ml| assert_equal 5, ml.count }
|
72
72
|
end
|
73
73
|
|
74
|
+
def test_works_with_marshal
|
75
|
+
s = SET.new(5)
|
76
|
+
10.times do
|
77
|
+
s << make_layer("LayerType", "LayerName")
|
78
|
+
end
|
79
|
+
|
80
|
+
Marshal.dump(s)
|
81
|
+
end
|
82
|
+
|
74
83
|
#############
|
75
84
|
# Helpers #
|
76
85
|
#############
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: scout_apm
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.6.
|
4
|
+
version: 2.6.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Derek Haynes
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2019-
|
12
|
+
date: 2019-12-12 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: minitest
|
@@ -250,6 +250,7 @@ files:
|
|
250
250
|
- lib/scout_apm/auto_instrument/parser.rb
|
251
251
|
- lib/scout_apm/auto_instrument/rails.rb
|
252
252
|
- lib/scout_apm/background_job_integrations/delayed_job.rb
|
253
|
+
- lib/scout_apm/background_job_integrations/legacy_sneakers.rb
|
253
254
|
- lib/scout_apm/background_job_integrations/que.rb
|
254
255
|
- lib/scout_apm/background_job_integrations/resque.rb
|
255
256
|
- lib/scout_apm/background_job_integrations/shoryuken.rb
|
@@ -376,6 +377,7 @@ files:
|
|
376
377
|
- lib/scout_apm/utils/gzip_helper.rb
|
377
378
|
- lib/scout_apm/utils/installed_gems.rb
|
378
379
|
- lib/scout_apm/utils/klass_helper.rb
|
380
|
+
- lib/scout_apm/utils/marshal_logging.rb
|
379
381
|
- lib/scout_apm/utils/numbers.rb
|
380
382
|
- lib/scout_apm/utils/scm.rb
|
381
383
|
- lib/scout_apm/utils/sql_sanitizer.rb
|