scout_apm 1.0.0 → 1.1.0.pre1
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/lib/scout_apm.rb +3 -0
- data/lib/scout_apm/agent/reporting.rb +7 -1
- data/lib/scout_apm/attribute_arranger.rb +17 -0
- data/lib/scout_apm/bucket_name_splitter.rb +27 -0
- data/lib/scout_apm/context.rb +1 -1
- data/lib/scout_apm/metric_meta.rb +8 -0
- data/lib/scout_apm/metric_stats.rb +6 -0
- data/lib/scout_apm/serializers/payload_serializer.rb +5 -1
- data/lib/scout_apm/serializers/payload_serializer_to_json.rb +67 -0
- data/lib/scout_apm/slow_transaction.rb +11 -0
- data/lib/scout_apm/store.rb +1 -1
- data/lib/scout_apm/tracer.rb +0 -2
- data/lib/scout_apm/version.rb +1 -1
- data/test/unit/serializers/payload_serializer_test.rb +212 -0
- metadata +9 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6241efa65950ed1d898ba3d688c0d0e442ed4871
|
4
|
+
data.tar.gz: 166976b4a15c5e4481bb171abba5dcf2f155e70f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: d0f7893d4df03ff5216bac6334ffa04e7e0bfa0e50e9eb14be6cb8a3d8e58b40afe140ed0691b3e324b311349119917f686f152e885dfbebbe20376c0d66c571
|
7
|
+
data.tar.gz: 4f6c3c86c84349989dfb406711a35791bd7d9f550b9139d67432fd7e37f512a9d879cfd7f08bbca6f8c30d9eb730fe8c469e7b7790138d87f02d0a25ce697993
|
data/lib/scout_apm.rb
CHANGED
@@ -74,6 +74,7 @@ require 'scout_apm/layaway'
|
|
74
74
|
require 'scout_apm/layaway_file'
|
75
75
|
require 'scout_apm/reporter'
|
76
76
|
require 'scout_apm/background_worker'
|
77
|
+
require 'scout_apm/bucket_name_splitter'
|
77
78
|
require 'scout_apm/metric_meta'
|
78
79
|
require 'scout_apm/metric_stats'
|
79
80
|
require 'scout_apm/stack_item'
|
@@ -83,8 +84,10 @@ require 'scout_apm/context'
|
|
83
84
|
require 'scout_apm/stackprof_tree_collapser'
|
84
85
|
require 'scout_apm/slow_transaction'
|
85
86
|
require 'scout_apm/capacity'
|
87
|
+
require 'scout_apm/attribute_arranger'
|
86
88
|
|
87
89
|
require 'scout_apm/serializers/payload_serializer'
|
90
|
+
require 'scout_apm/serializers/payload_serializer_to_json'
|
88
91
|
require 'scout_apm/serializers/directive_serializer'
|
89
92
|
require 'scout_apm/serializers/app_server_load_serializer'
|
90
93
|
require 'scout_apm/serializers/deploy_serializer'
|
@@ -49,7 +49,13 @@ module ScoutApm
|
|
49
49
|
|
50
50
|
logger.debug "Total payload [#{payload.size/1024} KB] for #{total_request_count} requests and Slow Transactions [#{slow_transactions_kb} KB] for #{slow_transactions.size} transactions of durations: #{slow_transactions.map(&:total_call_time).join(',')}."
|
51
51
|
|
52
|
-
|
52
|
+
if ScoutApm::Agent.instance.config.value("report_format") == 'json'
|
53
|
+
headers = {'Content-Type' => 'application/json'}
|
54
|
+
else
|
55
|
+
headers = {}
|
56
|
+
end
|
57
|
+
|
58
|
+
response = reporter.report(payload, headers)
|
53
59
|
|
54
60
|
if response and response.is_a?(Net::HTTPSuccess)
|
55
61
|
directives = ScoutApm::Serializers::DirectiveSerializer.deserialize(response.body)
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module ScoutApm
|
2
|
+
module AttributeArranger
|
3
|
+
# pass in an array of symbols to return as hash keys
|
4
|
+
# if the symbol doesn't match the name of the method, pass an array: [:key, :method_name]
|
5
|
+
def self.call(subject, attributes_list)
|
6
|
+
attributes_list.inject({}) do |attribute_hash, attribute|
|
7
|
+
case attribute
|
8
|
+
when Array
|
9
|
+
attribute_hash[attribute[0]] = subject.send(attribute[1])
|
10
|
+
when Symbol
|
11
|
+
attribute_hash[attribute] = subject.send(attribute)
|
12
|
+
end
|
13
|
+
attribute_hash
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module ScoutApm
|
2
|
+
module BucketNameSplitter
|
3
|
+
def bucket
|
4
|
+
split_metric_name(metric_name).first
|
5
|
+
end
|
6
|
+
|
7
|
+
def name
|
8
|
+
split_metric_name(metric_name).last
|
9
|
+
end
|
10
|
+
|
11
|
+
def key
|
12
|
+
{:bucket => bucket, :name => name}
|
13
|
+
end
|
14
|
+
|
15
|
+
private
|
16
|
+
def split_metric_name(name)
|
17
|
+
name.to_s.split(/\//, 2)
|
18
|
+
end
|
19
|
+
|
20
|
+
def scope_hash
|
21
|
+
if scope
|
22
|
+
scope_bucket, scope_name = split_metric_name(scope)
|
23
|
+
{:bucket => scope_bucket, :name => scope_name}
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
data/lib/scout_apm/context.rb
CHANGED
@@ -81,7 +81,7 @@ module ScoutApm
|
|
81
81
|
value = key_value.values.last
|
82
82
|
if !valid_type?([String, Symbol, Numeric, Time, Date, TrueClass, FalseClass],value)
|
83
83
|
ScoutApm::Agent.instance.logger.warn "The value for [#{key_value.keys.first}] is not a valid type [#{value.class}]."
|
84
|
-
|
84
|
+
false
|
85
85
|
else
|
86
86
|
true
|
87
87
|
end
|
@@ -1,5 +1,7 @@
|
|
1
1
|
# Contains the meta information associated with a metric. Used to lookup Metrics in to Store's metric_hash.
|
2
2
|
class ScoutApm::MetricMeta
|
3
|
+
include ScoutApm::BucketNameSplitter
|
4
|
+
|
3
5
|
def initialize(metric_name, options = {})
|
4
6
|
@metric_name = metric_name
|
5
7
|
@metric_id = nil
|
@@ -31,4 +33,10 @@ class ScoutApm::MetricMeta
|
|
31
33
|
def eql?(o)
|
32
34
|
self.class == o.class && metric_name.downcase.eql?(o.metric_name.downcase) && scope == o.scope && client_id == o.client_id && desc == o.desc
|
33
35
|
end
|
36
|
+
|
37
|
+
def as_json
|
38
|
+
json_attributes = [:bucket, :name, :desc, :extra, [:scope, :scope_hash]]
|
39
|
+
# query, stack_trace
|
40
|
+
ScoutApm::AttributeArranger.call(self, json_attributes)
|
41
|
+
end
|
34
42
|
end # class MetricMeta
|
@@ -46,4 +46,10 @@ class ScoutApm::MetricStats
|
|
46
46
|
def to_json(*a)
|
47
47
|
%Q[{"total_exclusive_time":#{total_exclusive_time*1000},"min_call_time":#{min_call_time*1000},"call_count":#{call_count},"sum_of_squares":#{sum_of_squares*1000},"total_call_time":#{total_call_time*1000},"max_call_time":#{max_call_time*1000}}]
|
48
48
|
end
|
49
|
+
|
50
|
+
def as_json
|
51
|
+
json_attributes = [:call_count, :total_call_time, :total_exclusive_time, :min_call_time, :max_call_time]
|
52
|
+
# uri, context
|
53
|
+
ScoutApm::AttributeArranger.call(self, json_attributes)
|
54
|
+
end
|
49
55
|
end # class MetricStats
|
@@ -3,7 +3,11 @@ module ScoutApm
|
|
3
3
|
module Serializers
|
4
4
|
class PayloadSerializer
|
5
5
|
def self.serialize(metadata, metrics, slow_transactions)
|
6
|
-
|
6
|
+
if ScoutApm::Agent.instance.config.value("report_format") == 'json'
|
7
|
+
ScoutApm::Serializers::PayloadSerializerToJson.serialize(metadata, metrics, slow_transactions)
|
8
|
+
else
|
9
|
+
Marshal.dump(:metadata => metadata, :metrics => metrics, :slow_transactions => slow_transactions)
|
10
|
+
end
|
7
11
|
end
|
8
12
|
|
9
13
|
def self.deserialize(data)
|
@@ -0,0 +1,67 @@
|
|
1
|
+
module ScoutApm
|
2
|
+
module Serializers
|
3
|
+
module PayloadSerializerToJson
|
4
|
+
class << self
|
5
|
+
def serialize(metadata, metrics, slow_transactions)
|
6
|
+
rearranged_metrics = rearrange_the_metrics(metrics)
|
7
|
+
rearranged_slow_transactions = rearrange_the_slow_transactions(slow_transactions)
|
8
|
+
jsonify_hash({:metadata => metadata, :metrics => rearranged_metrics, :slow_transactions => rearranged_slow_transactions})
|
9
|
+
end
|
10
|
+
|
11
|
+
def rearrange_the_metrics(metrics)
|
12
|
+
metrics.to_a.map do |meta, stats|
|
13
|
+
stats.as_json.merge(key: meta.as_json)
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def rearrange_the_slow_transactions(slow_transactions)
|
18
|
+
slow_transactions.to_a.map do |slow_t|
|
19
|
+
slow_t.as_json.merge(metrics: rearrange_the_metrics(slow_t.metrics))
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def jsonify_hash(hash)
|
24
|
+
str_parts = []
|
25
|
+
hash.each do |key, value|
|
26
|
+
formatted_key = format_by_type(key)
|
27
|
+
formatted_value = format_by_type(value)
|
28
|
+
str_parts << "#{formatted_key}:#{formatted_value}"
|
29
|
+
end
|
30
|
+
"{#{str_parts.join(",")}}"
|
31
|
+
end
|
32
|
+
|
33
|
+
def escape(string)
|
34
|
+
string = string.to_s
|
35
|
+
escapers = {
|
36
|
+
'\b' => '\\b',
|
37
|
+
'\t' => '\\t',
|
38
|
+
'\n' => '\\n',
|
39
|
+
'\f' => '\\f',
|
40
|
+
'\r' => '\\r',
|
41
|
+
'"' => '\\"',
|
42
|
+
'\\' => '\\\\'
|
43
|
+
}
|
44
|
+
# TODO escape control chars
|
45
|
+
escapers.each {|bad, good| string = string.gsub(bad, good)}
|
46
|
+
string
|
47
|
+
end
|
48
|
+
|
49
|
+
def format_by_type(formatee)
|
50
|
+
case formatee
|
51
|
+
when Hash
|
52
|
+
jsonify_hash(formatee)
|
53
|
+
when Array
|
54
|
+
all_the_elements = formatee.map {|value_guy| format_by_type(value_guy)}
|
55
|
+
"[#{all_the_elements.join(",")}]"
|
56
|
+
when Numeric
|
57
|
+
formatee
|
58
|
+
when nil
|
59
|
+
"null"
|
60
|
+
else # strings and everything
|
61
|
+
%Q["#{escape(formatee)}"]
|
62
|
+
end
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
67
|
+
end
|
@@ -1,5 +1,7 @@
|
|
1
1
|
module ScoutApm
|
2
2
|
class SlowTransaction
|
3
|
+
include ScoutApm::BucketNameSplitter
|
4
|
+
|
3
5
|
BACKTRACE_THRESHOLD = 0.5 # the minimum threshold to record the backtrace for a metric.
|
4
6
|
BACKTRACE_LIMIT = 5 # Max length of callers to display
|
5
7
|
MAX_SIZE = 100 # Limits the size of the metric hash to prevent a metric explosion.
|
@@ -45,5 +47,14 @@ module ScoutApm
|
|
45
47
|
@metrics = nil
|
46
48
|
self
|
47
49
|
end
|
50
|
+
|
51
|
+
def as_json
|
52
|
+
json_attributes = [:key, :time, :total_call_time, :uri, [:context, :context_hash], :prof]
|
53
|
+
ScoutApm::AttributeArranger.call(self, json_attributes)
|
54
|
+
end
|
55
|
+
|
56
|
+
def context_hash
|
57
|
+
context.to_hash
|
58
|
+
end
|
48
59
|
end
|
49
60
|
end
|
data/lib/scout_apm/store.rb
CHANGED
@@ -150,7 +150,7 @@ module ScoutApm
|
|
150
150
|
parent_stat.total_call_time,
|
151
151
|
transaction_hash.dup,
|
152
152
|
ScoutApm::Context.current,
|
153
|
-
|
153
|
+
Time.now,
|
154
154
|
Thread::current[:scout_apm_prof])
|
155
155
|
@slow_transactions.push(slow_transaction)
|
156
156
|
ScoutApm::Agent.instance.logger.debug "Slow transaction sample added. [URI: #{uri}] [Context: #{ScoutApm::Context.current.to_hash}] Array Size: #{@slow_transactions.size}"
|
data/lib/scout_apm/tracer.rb
CHANGED
@@ -22,7 +22,6 @@ module ScoutApm
|
|
22
22
|
# TODO - wrap a lot of this into a Trace class, store that as a Thread var.
|
23
23
|
ScoutApm::Agent.instance.store.reset_transaction!
|
24
24
|
ScoutApm::Context.current.add_user(:ip => options[:ip]) if options[:ip]
|
25
|
-
Thread::current[:scout_apm_trace_time] = Time.now.utc
|
26
25
|
ScoutApm::Agent.instance.capacity.start_transaction!
|
27
26
|
e = nil
|
28
27
|
instrument(metric_name, options) do
|
@@ -34,7 +33,6 @@ module ScoutApm
|
|
34
33
|
end
|
35
34
|
Thread::current[:scout_apm_scope_name] = nil
|
36
35
|
end
|
37
|
-
Thread::current[:scout_apm_trace_time] = nil
|
38
36
|
ScoutApm::Agent.instance.capacity.finish_transaction!
|
39
37
|
# The context is cleared after instrumentation (rather than before) as tracing controller-actions doesn't occur until the controller-action is called.
|
40
38
|
# It does not trace before filters, which is a likely spot to add context. This means that any context applied during before_filters would be cleared.
|
data/lib/scout_apm/version.rb
CHANGED
@@ -0,0 +1,212 @@
|
|
1
|
+
require 'test_helper'
|
2
|
+
require 'scout_apm/attribute_arranger'
|
3
|
+
require 'scout_apm/bucket_name_splitter'
|
4
|
+
require 'scout_apm/serializers/payload_serializer'
|
5
|
+
require 'scout_apm/serializers/payload_serializer_to_json'
|
6
|
+
require 'scout_apm/slow_transaction'
|
7
|
+
require 'scout_apm/metric_meta'
|
8
|
+
require 'scout_apm/metric_stats'
|
9
|
+
require 'scout_apm/stackprof_tree_collapser'
|
10
|
+
require 'scout_apm/utils/fake_stack_prof'
|
11
|
+
require 'scout_apm/context'
|
12
|
+
require 'ostruct'
|
13
|
+
require 'json' # to deserialize what has been manually serialized by the production code
|
14
|
+
|
15
|
+
# stub the report_format value
|
16
|
+
class ScoutApm::Agent
|
17
|
+
module Config
|
18
|
+
def self.value(key)
|
19
|
+
'json'
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def self.instance
|
24
|
+
OpenStruct.new(:config => Config)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
class PayloadSerializerTest < Minitest::Test
|
29
|
+
|
30
|
+
def test_serializes_metadata_as_json
|
31
|
+
metadata = {
|
32
|
+
:app_root => "/srv/app/rootz",
|
33
|
+
:unique_id => "unique_idz",
|
34
|
+
:agent_version => 123
|
35
|
+
}
|
36
|
+
payload = ScoutApm::Serializers::PayloadSerializer.serialize(metadata, {}, {})
|
37
|
+
|
38
|
+
# symbol keys turn to strings
|
39
|
+
formatted_metadata = {
|
40
|
+
"app_root" => "/srv/app/rootz",
|
41
|
+
"unique_id" => "unique_idz",
|
42
|
+
"agent_version" => 123
|
43
|
+
}
|
44
|
+
assert_equal formatted_metadata, JSON.parse(payload)["metadata"]
|
45
|
+
end
|
46
|
+
|
47
|
+
def test_serializes_metrics_as_json
|
48
|
+
metrics = {
|
49
|
+
ScoutApm::MetricMeta.new('ActiveRecord/all').tap { |meta|
|
50
|
+
meta.desc = "SELECT * from users where filter=?"
|
51
|
+
meta.extra = {user: 'cooluser'}
|
52
|
+
meta.metric_id = nil
|
53
|
+
meta.scope = "Controller/apps/checkin"
|
54
|
+
} => ScoutApm::MetricStats.new.tap { |stats|
|
55
|
+
stats.call_count = 16
|
56
|
+
stats.max_call_time = 0.005338062
|
57
|
+
stats.min_call_time = 0.000613518
|
58
|
+
stats.sum_of_squares = 9.8040860751126e-05
|
59
|
+
stats.total_call_time = 0.033245704
|
60
|
+
stats.total_exclusive_time = 0.033245704
|
61
|
+
},
|
62
|
+
ScoutApm::MetricMeta.new("Controller/apps/checkin").tap { |meta|
|
63
|
+
meta.desc = nil
|
64
|
+
meta.extra = {}
|
65
|
+
meta.metric_id = nil
|
66
|
+
meta.scope = nil
|
67
|
+
} => ScoutApm::MetricStats.new.tap { |stats|
|
68
|
+
stats.call_count = 2
|
69
|
+
stats.max_call_time = 0.078521419
|
70
|
+
stats.min_call_time = 0.034881757
|
71
|
+
stats.sum_of_squares = 0.007382350213180609
|
72
|
+
stats.total_call_time = 0.113403176
|
73
|
+
stats.total_exclusive_time = 0.07813208899999999
|
74
|
+
}
|
75
|
+
}
|
76
|
+
payload = ScoutApm::Serializers::PayloadSerializer.serialize({}, metrics, {})
|
77
|
+
formatted_metrics = [
|
78
|
+
{
|
79
|
+
"key" => {
|
80
|
+
"bucket" => "ActiveRecord",
|
81
|
+
"name" => "all",
|
82
|
+
"desc" => "SELECT * from users where filter=?",
|
83
|
+
"extra" => {
|
84
|
+
"user" => "cooluser",
|
85
|
+
},
|
86
|
+
"scope" => {
|
87
|
+
"bucket" => "Controller",
|
88
|
+
"name" => "apps/checkin",
|
89
|
+
},
|
90
|
+
},
|
91
|
+
"call_count" => 16,
|
92
|
+
"max_call_time" => 0.005338062,
|
93
|
+
"min_call_time" => 0.000613518,
|
94
|
+
"total_call_time" => 0.033245704,
|
95
|
+
"total_exclusive_time" => 0.033245704,
|
96
|
+
},
|
97
|
+
{
|
98
|
+
"key" => {
|
99
|
+
"bucket" => "Controller",
|
100
|
+
"name" => "apps/checkin",
|
101
|
+
"desc" => nil,
|
102
|
+
"extra" => {},
|
103
|
+
"scope" => nil,
|
104
|
+
},
|
105
|
+
"call_count" => 2,
|
106
|
+
"max_call_time" => 0.078521419,
|
107
|
+
"min_call_time" => 0.034881757,
|
108
|
+
"total_call_time" => 0.113403176,
|
109
|
+
"total_exclusive_time" => 0.07813208899999999,
|
110
|
+
}
|
111
|
+
]
|
112
|
+
assert_equal formatted_metrics, JSON.parse(payload)["metrics"]
|
113
|
+
end
|
114
|
+
|
115
|
+
def test_serializes_slow_transactions_as_json
|
116
|
+
slow_transaction_metrics = {
|
117
|
+
ScoutApm::MetricMeta.new('ActiveRecord/all').tap { |meta|
|
118
|
+
meta.desc = "SELECT * from users where filter=?"
|
119
|
+
meta.extra = {user: 'cooluser'}
|
120
|
+
meta.metric_id = nil
|
121
|
+
meta.scope = "Controller/apps/checkin"
|
122
|
+
} => ScoutApm::MetricStats.new.tap { |stats|
|
123
|
+
stats.call_count = 16
|
124
|
+
stats.max_call_time = 0.005338062
|
125
|
+
stats.min_call_time = 0.000613518
|
126
|
+
stats.sum_of_squares = 9.8040860751126e-05
|
127
|
+
stats.total_call_time = 0.033245704
|
128
|
+
stats.total_exclusive_time = 0.033245704
|
129
|
+
},
|
130
|
+
ScoutApm::MetricMeta.new("Controller/apps/checkin").tap { |meta|
|
131
|
+
meta.desc = nil
|
132
|
+
meta.extra = {}
|
133
|
+
meta.metric_id = nil
|
134
|
+
meta.scope = nil
|
135
|
+
} => ScoutApm::MetricStats.new.tap { |stats|
|
136
|
+
stats.call_count = 2
|
137
|
+
stats.max_call_time = 0.078521419
|
138
|
+
stats.min_call_time = 0.034881757
|
139
|
+
stats.sum_of_squares = 0.007382350213180609
|
140
|
+
stats.total_call_time = 0.113403176
|
141
|
+
stats.total_exclusive_time = 0.07813208899999999
|
142
|
+
}
|
143
|
+
}
|
144
|
+
context = ScoutApm::Context.new
|
145
|
+
context.add({"this" => "that"})
|
146
|
+
context.add_user({"hello" => "goodbye"})
|
147
|
+
slow_t = ScoutApm::SlowTransaction.new("http://example.com/blabla", "Buckethead/something/else", 1.23, slow_transaction_metrics, context, Time.at(1448198788), StackProf.new)
|
148
|
+
payload = ScoutApm::Serializers::PayloadSerializer.serialize({}, {}, [slow_t])
|
149
|
+
formatted_slow_transactions = [
|
150
|
+
{
|
151
|
+
"key" => {
|
152
|
+
"bucket" => "Buckethead",
|
153
|
+
"name" => "something/else"
|
154
|
+
},
|
155
|
+
"time" => "2015-11-22 06:26:28 -0700",
|
156
|
+
"total_call_time" => 1.23,
|
157
|
+
"uri" => "http://example.com/blabla",
|
158
|
+
"context" => {"this"=>"that", "user"=>{"hello"=>"goodbye"}},
|
159
|
+
"prof" => [],
|
160
|
+
"metrics" => [
|
161
|
+
{
|
162
|
+
"key" => {
|
163
|
+
"bucket" => "ActiveRecord",
|
164
|
+
"name" => "all",
|
165
|
+
"desc" => "SELECT * from users where filter=?",
|
166
|
+
"extra" => {
|
167
|
+
"user" => "cooluser",
|
168
|
+
},
|
169
|
+
"scope" => {
|
170
|
+
"bucket" => "Controller",
|
171
|
+
"name" => "apps/checkin",
|
172
|
+
},
|
173
|
+
},
|
174
|
+
"call_count" => 16,
|
175
|
+
"max_call_time" => 0.005338062,
|
176
|
+
"min_call_time" => 0.000613518,
|
177
|
+
"total_call_time" => 0.033245704,
|
178
|
+
"total_exclusive_time" => 0.033245704,
|
179
|
+
},
|
180
|
+
{
|
181
|
+
"key" => {
|
182
|
+
"bucket" => "Controller",
|
183
|
+
"name" => "apps/checkin",
|
184
|
+
"desc" => nil,
|
185
|
+
"extra" => {},
|
186
|
+
"scope" => nil,
|
187
|
+
},
|
188
|
+
"call_count" => 2,
|
189
|
+
"max_call_time" => 0.078521419,
|
190
|
+
"min_call_time" => 0.034881757,
|
191
|
+
"total_call_time" => 0.113403176,
|
192
|
+
"total_exclusive_time" => 0.07813208899999999,
|
193
|
+
}
|
194
|
+
]
|
195
|
+
}
|
196
|
+
]
|
197
|
+
assert_equal formatted_slow_transactions, JSON.parse(payload)["slow_transactions"]
|
198
|
+
end
|
199
|
+
|
200
|
+
def test_escapes_json_quotes
|
201
|
+
metadata = {
|
202
|
+
:quotie => "here are some \"quotes\"",
|
203
|
+
}
|
204
|
+
payload = ScoutApm::Serializers::PayloadSerializer.serialize(metadata, {}, {})
|
205
|
+
|
206
|
+
# symbol keys turn to strings
|
207
|
+
formatted_metadata = {
|
208
|
+
"quotie" => "here are some \"quotes\""
|
209
|
+
}
|
210
|
+
assert_equal formatted_metadata, JSON.parse(payload)["metadata"]
|
211
|
+
end
|
212
|
+
end
|
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: 1.0.
|
4
|
+
version: 1.1.0.pre1
|
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: 2015-
|
12
|
+
date: 2015-12-02 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: minitest
|
@@ -71,7 +71,9 @@ files:
|
|
71
71
|
- lib/scout_apm/agent/logging.rb
|
72
72
|
- lib/scout_apm/agent/reporting.rb
|
73
73
|
- lib/scout_apm/app_server_load.rb
|
74
|
+
- lib/scout_apm/attribute_arranger.rb
|
74
75
|
- lib/scout_apm/background_worker.rb
|
76
|
+
- lib/scout_apm/bucket_name_splitter.rb
|
75
77
|
- lib/scout_apm/capacity.rb
|
76
78
|
- lib/scout_apm/config.rb
|
77
79
|
- lib/scout_apm/context.rb
|
@@ -106,6 +108,7 @@ files:
|
|
106
108
|
- lib/scout_apm/serializers/deploy_serializer.rb
|
107
109
|
- lib/scout_apm/serializers/directive_serializer.rb
|
108
110
|
- lib/scout_apm/serializers/payload_serializer.rb
|
111
|
+
- lib/scout_apm/serializers/payload_serializer_to_json.rb
|
109
112
|
- lib/scout_apm/server_integrations/null.rb
|
110
113
|
- lib/scout_apm/server_integrations/passenger.rb
|
111
114
|
- lib/scout_apm/server_integrations/puma.rb
|
@@ -133,6 +136,7 @@ files:
|
|
133
136
|
- test/unit/config_test.rb
|
134
137
|
- test/unit/environment_test.rb
|
135
138
|
- test/unit/instruments/active_record_instruments_test.rb
|
139
|
+
- test/unit/serializers/payload_serializer_test.rb
|
136
140
|
- test/unit/sql_sanitizer_test.rb
|
137
141
|
homepage: https://github.com/scoutapp/scout_apm_ruby
|
138
142
|
licenses: []
|
@@ -149,9 +153,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
149
153
|
version: '0'
|
150
154
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
151
155
|
requirements:
|
152
|
-
- - "
|
156
|
+
- - ">"
|
153
157
|
- !ruby/object:Gem::Version
|
154
|
-
version:
|
158
|
+
version: 1.3.1
|
155
159
|
requirements: []
|
156
160
|
rubyforge_project: scout_apm
|
157
161
|
rubygems_version: 2.2.2
|
@@ -164,4 +168,5 @@ test_files:
|
|
164
168
|
- test/unit/config_test.rb
|
165
169
|
- test/unit/environment_test.rb
|
166
170
|
- test/unit/instruments/active_record_instruments_test.rb
|
171
|
+
- test/unit/serializers/payload_serializer_test.rb
|
167
172
|
- test/unit/sql_sanitizer_test.rb
|