errplane 0.6.10 → 1.0.0
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.
- data/lib/errplane.rb +40 -22
- data/lib/errplane/api.rb +22 -4
- data/lib/errplane/configuration.rb +4 -0
- data/lib/errplane/exception_presenter.rb +12 -24
- data/lib/errplane/version.rb +1 -1
- data/lib/errplane/worker.rb +11 -15
- metadata +66 -21
data/lib/errplane.rb
CHANGED
@@ -40,19 +40,37 @@ module Errplane
|
|
40
40
|
@queue ||= MaxQueue.new(configuration.queue_maximum_depth)
|
41
41
|
end
|
42
42
|
|
43
|
-
def report(name, params = {},
|
43
|
+
def report(name, params = {}, udp = false)
|
44
44
|
unless configuration.ignored_reports.find{ |msg| /#{msg}/ =~ name }
|
45
|
-
data =
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
45
|
+
data = generate_data(name, params)
|
46
|
+
udp ? Errplane.api.send(data) : Errplane.queue.push(data)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
def rollup(name, params = {})
|
51
|
+
Errplane.api.send generate_data(name, params), "t"
|
52
|
+
end
|
53
|
+
|
54
|
+
def count(name, params = {})
|
55
|
+
Errplane.api.send generate_data(name, params), "c"
|
56
|
+
end
|
57
|
+
|
58
|
+
def generate_data(name, params)
|
59
|
+
point = {:v => params[:value] || 1}
|
60
|
+
point[:t] = params[:timestamp] unless params[:timestamp].nil?
|
61
|
+
|
62
|
+
if context = params[:context]
|
63
|
+
point[:c] = params[:context].is_a?(String) ? params[:context] : params[:context].to_json
|
64
|
+
end
|
65
|
+
|
66
|
+
if dimensions = params[:dimensions]
|
67
|
+
point[:d] = Hash[params[:dimensions].map {|k,v| [k.to_s, v.to_s]}]
|
55
68
|
end
|
69
|
+
|
70
|
+
{
|
71
|
+
:n => name.gsub(/\s+/, "_"),
|
72
|
+
:p => [point]
|
73
|
+
}
|
56
74
|
end
|
57
75
|
|
58
76
|
def report_deployment(context = nil, async = false)
|
@@ -84,35 +102,35 @@ module Errplane
|
|
84
102
|
yield_value
|
85
103
|
end
|
86
104
|
|
87
|
-
def
|
88
|
-
|
105
|
+
def report_exception_unless_ignorable(e, env = {})
|
106
|
+
report_exception(e, env) unless ignorable_exception?(e)
|
89
107
|
end
|
108
|
+
alias_method :transmit_unless_ignorable, :report_exception_unless_ignorable
|
90
109
|
|
91
|
-
def
|
110
|
+
def report_exception(e, env = {})
|
92
111
|
begin
|
93
112
|
env = errplane_request_data if env.empty? && defined? errplane_request_data
|
94
113
|
exception_presenter = ExceptionPresenter.new(e, env)
|
95
114
|
log :info, "Exception: #{exception_presenter.to_json[0..512]}..."
|
96
115
|
|
97
116
|
Errplane.queue.push({
|
98
|
-
:
|
99
|
-
:
|
117
|
+
:n => "exceptions",
|
118
|
+
:p => [{
|
119
|
+
:v => 1,
|
120
|
+
:c => exception_presenter.context.to_json,
|
121
|
+
:d => exception_presenter.dimensions
|
122
|
+
}]
|
100
123
|
})
|
101
124
|
rescue => e
|
102
125
|
log :info, "[Errplane] Something went terribly wrong. Exception failed to take off! #{e.class}: #{e.message}"
|
103
126
|
end
|
104
127
|
end
|
128
|
+
alias_method :transmit, :report_exception
|
105
129
|
|
106
130
|
def current_timestamp
|
107
131
|
Time.now.utc.to_i
|
108
132
|
end
|
109
133
|
|
110
|
-
def process_line(line)
|
111
|
-
data = "#{line[:name]} #{line[:value] || 1} #{line[:timestamp] || "now"}"
|
112
|
-
data = "#{data} #{Base64.strict_encode64(line[:context].to_json)}" if line[:context]
|
113
|
-
data
|
114
|
-
end
|
115
|
-
|
116
134
|
def ignorable_exception?(e)
|
117
135
|
configuration.ignore_current_environment? ||
|
118
136
|
!!configuration.ignored_exception_messages.find{ |msg| /.*#{msg}.*/ =~ e.message } ||
|
data/lib/errplane/api.rb
CHANGED
@@ -4,6 +4,10 @@ module Errplane
|
|
4
4
|
|
5
5
|
attr_reader :last_response
|
6
6
|
|
7
|
+
HTTPS_HOST = "w.apiv3.errplane.com"
|
8
|
+
UDP_HOST = "udp.apiv3.errplane.com"
|
9
|
+
UDP_PORT = 8126
|
10
|
+
|
7
11
|
POST_RETRIES = 5
|
8
12
|
READ_TIMEOUT = 3
|
9
13
|
OPEN_TIMEOUT = 3
|
@@ -23,7 +27,7 @@ module Errplane
|
|
23
27
|
log :debug, "POSTing to #{url}"
|
24
28
|
|
25
29
|
response = begin
|
26
|
-
https.post(url, data)
|
30
|
+
https.post(url, data.to_json)
|
27
31
|
rescue *HTTP_ERRORS => e
|
28
32
|
log :error, "HTTP error contacting API! #{e.class}: #{e.message}"
|
29
33
|
retry_count -= 1
|
@@ -44,17 +48,31 @@ module Errplane
|
|
44
48
|
@last_response = response
|
45
49
|
end
|
46
50
|
|
51
|
+
def send(data, operator="r")
|
52
|
+
udp = UDPSocket.new
|
53
|
+
|
54
|
+
packet = {
|
55
|
+
:d => Errplane.configuration.database_name,
|
56
|
+
:a => Errplane.configuration.api_key.to_s,
|
57
|
+
:o => operator,
|
58
|
+
:w => [data]
|
59
|
+
}
|
60
|
+
|
61
|
+
log :debug, "Sending UDP Packet: #{packet.to_json}"
|
62
|
+
|
63
|
+
udp.send packet.to_json, 0, UDP_HOST, UDP_PORT
|
64
|
+
end
|
65
|
+
|
47
66
|
private
|
48
67
|
def url
|
49
68
|
"/databases/" \
|
50
|
-
+ Errplane.configuration.
|
51
|
-
+ Errplane.configuration.environment.to_s \
|
69
|
+
+ Errplane.configuration.database_name \
|
52
70
|
+ "/points?api_key=" \
|
53
71
|
+ Errplane.configuration.api_key.to_s
|
54
72
|
end
|
55
73
|
|
56
74
|
def initialize_secure_connection
|
57
|
-
connection = Net::HTTP.new(
|
75
|
+
connection = Net::HTTP.new(HTTPS_HOST, 443)
|
58
76
|
connection.use_ssl = true
|
59
77
|
connection.verify_mode = OpenSSL::SSL::VERIFY_NONE
|
60
78
|
connection.read_timeout = READ_TIMEOUT
|
@@ -112,6 +112,10 @@ module Errplane
|
|
112
112
|
@custom_exception_data_handler.call(black_box) if @custom_exception_data_handler
|
113
113
|
end
|
114
114
|
|
115
|
+
def database_name
|
116
|
+
@application_id.to_s + @environment.to_s
|
117
|
+
end
|
118
|
+
|
115
119
|
private
|
116
120
|
def initialize_http_connection
|
117
121
|
Net::HTTP.new(@app_host, "80")
|
@@ -31,8 +31,8 @@ module Errplane
|
|
31
31
|
@environment_variables = ENV.to_hash || {}
|
32
32
|
end
|
33
33
|
|
34
|
-
def
|
35
|
-
|
34
|
+
def context
|
35
|
+
c = {
|
36
36
|
:time => Time.now.utc.to_i,
|
37
37
|
:application_name => Errplane.configuration.application_name,
|
38
38
|
:application_root => Errplane.configuration.application_root,
|
@@ -40,41 +40,29 @@ module Errplane
|
|
40
40
|
:framework_version => Errplane.configuration.framework_version,
|
41
41
|
:message => @exception.message,
|
42
42
|
:backtrace => @backtrace,
|
43
|
-
:exception_class => @exception.class.to_s,
|
44
43
|
:language => "Ruby",
|
45
44
|
:language_version => "#{RUBY_VERSION}-p#{RUBY_PATCHLEVEL}",
|
46
45
|
:reporter => reporter,
|
47
|
-
:hostname => Socket.gethostname,
|
48
46
|
:custom_data => @custom_data
|
49
47
|
}
|
50
48
|
|
51
|
-
|
49
|
+
c[:environment_variables] = @environment_variables.reject do |k,v|
|
52
50
|
Errplane.configuration.environment_variable_filters.any? { |filter| k =~ filter }
|
53
51
|
end
|
54
52
|
|
55
53
|
Errplane.configuration.add_custom_exception_data(self)
|
56
54
|
|
57
|
-
|
58
|
-
|
59
|
-
payload.to_json
|
60
|
-
end
|
61
|
-
|
62
|
-
def calculate_hash
|
63
|
-
if hash
|
64
|
-
hash
|
65
|
-
elsif Errplane.configuration.aggregated_exception_classes.include?(@exception.class.to_s)
|
66
|
-
Digest::SHA1.hexdigest(@exception.class.to_s)
|
67
|
-
else
|
68
|
-
Digest::SHA1.hexdigest(@exception.class.to_s + @backtrace.first.to_s)
|
69
|
-
end
|
70
|
-
end
|
71
|
-
|
72
|
-
def time_series_name
|
73
|
-
"exceptions/" + calculate_hash
|
55
|
+
c[:request_data] = request_data if @controller || @action || !@params.blank?
|
56
|
+
c
|
74
57
|
end
|
75
58
|
|
76
|
-
def
|
77
|
-
|
59
|
+
def dimensions
|
60
|
+
d = {
|
61
|
+
:Class => @exception.class.to_s,
|
62
|
+
:class => @exception.class.to_s,
|
63
|
+
:method => "#{@controller}##{@action}",
|
64
|
+
:server => Socket.gethostname
|
65
|
+
}
|
78
66
|
end
|
79
67
|
|
80
68
|
def reporter
|
data/lib/errplane/version.rb
CHANGED
data/lib/errplane/worker.rb
CHANGED
@@ -5,22 +5,18 @@ require "base64"
|
|
5
5
|
|
6
6
|
module Errplane
|
7
7
|
class Worker
|
8
|
-
|
8
|
+
MAX_POST_POINTS = 200
|
9
9
|
MAX_TIME_SERIES_NAME_LENGTH = 255
|
10
10
|
|
11
11
|
class << self
|
12
12
|
include Errplane::Logger
|
13
13
|
|
14
|
-
def indent_lines(lines, num)
|
15
|
-
lines.split("\n").map {|line| (" " * num) + line[0..64]}.join("\n")
|
16
|
-
end
|
17
|
-
|
18
14
|
def post_data(data)
|
19
15
|
if Errplane.configuration.ignore_current_environment?
|
20
16
|
log :debug, "Current environment is ignored, skipping POST."
|
21
17
|
return false
|
22
18
|
else
|
23
|
-
log :debug, "POSTing data:\n#{
|
19
|
+
log :debug, "POSTing data:\n#{data}"
|
24
20
|
begin
|
25
21
|
Errplane.api.post(data)
|
26
22
|
rescue => e
|
@@ -63,23 +59,23 @@ module Errplane
|
|
63
59
|
begin
|
64
60
|
data = []
|
65
61
|
|
66
|
-
while data.size <
|
67
|
-
|
68
|
-
log :debug, "Found data in the queue! (#{
|
62
|
+
while data.size < MAX_POST_POINTS && !Errplane.queue.empty?
|
63
|
+
p = Errplane.queue.pop(true) rescue next;
|
64
|
+
log :debug, "Found data in the queue! (#{p[:n]})"
|
69
65
|
|
70
66
|
begin
|
71
|
-
if
|
72
|
-
log :error, "Time series name too long! Discarding data for: #{
|
67
|
+
if p[:n].size > MAX_TIME_SERIES_NAME_LENGTH
|
68
|
+
log :error, "Time series name too long! Discarding data for: #{p[:n]}"
|
73
69
|
else
|
74
|
-
data
|
70
|
+
data.push p
|
75
71
|
end
|
76
72
|
rescue => e
|
77
|
-
log :info, "Instrumentation Error! #{e.inspect}"
|
73
|
+
log :info, "Instrumentation Error! #{e.inspect} #{e.backtrace.first}"
|
78
74
|
end
|
79
75
|
end
|
80
76
|
|
81
|
-
post_data(data
|
82
|
-
end while Errplane.queue.length >
|
77
|
+
post_data(data) unless data.empty?
|
78
|
+
end while Errplane.queue.length > MAX_POST_POINTS
|
83
79
|
end
|
84
80
|
end
|
85
81
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: errplane
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 1.0.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,11 +9,11 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-
|
12
|
+
date: 2013-07-03 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: json
|
16
|
-
requirement:
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ! '>='
|
@@ -21,10 +21,15 @@ dependencies:
|
|
21
21
|
version: '0'
|
22
22
|
type: :runtime
|
23
23
|
prerelease: false
|
24
|
-
version_requirements:
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ! '>='
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: '0'
|
25
30
|
- !ruby/object:Gem::Dependency
|
26
31
|
name: bundler
|
27
|
-
requirement:
|
32
|
+
requirement: !ruby/object:Gem::Requirement
|
28
33
|
none: false
|
29
34
|
requirements:
|
30
35
|
- - ! '>='
|
@@ -32,10 +37,15 @@ dependencies:
|
|
32
37
|
version: 1.0.0
|
33
38
|
type: :development
|
34
39
|
prerelease: false
|
35
|
-
version_requirements:
|
40
|
+
version_requirements: !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
42
|
+
requirements:
|
43
|
+
- - ! '>='
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
version: 1.0.0
|
36
46
|
- !ruby/object:Gem::Dependency
|
37
47
|
name: fakeweb
|
38
|
-
requirement:
|
48
|
+
requirement: !ruby/object:Gem::Requirement
|
39
49
|
none: false
|
40
50
|
requirements:
|
41
51
|
- - ! '>='
|
@@ -43,10 +53,15 @@ dependencies:
|
|
43
53
|
version: '0'
|
44
54
|
type: :development
|
45
55
|
prerelease: false
|
46
|
-
version_requirements:
|
56
|
+
version_requirements: !ruby/object:Gem::Requirement
|
57
|
+
none: false
|
58
|
+
requirements:
|
59
|
+
- - ! '>='
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
47
62
|
- !ruby/object:Gem::Dependency
|
48
63
|
name: guard
|
49
|
-
requirement:
|
64
|
+
requirement: !ruby/object:Gem::Requirement
|
50
65
|
none: false
|
51
66
|
requirements:
|
52
67
|
- - ! '>='
|
@@ -54,10 +69,15 @@ dependencies:
|
|
54
69
|
version: '0'
|
55
70
|
type: :development
|
56
71
|
prerelease: false
|
57
|
-
version_requirements:
|
72
|
+
version_requirements: !ruby/object:Gem::Requirement
|
73
|
+
none: false
|
74
|
+
requirements:
|
75
|
+
- - ! '>='
|
76
|
+
- !ruby/object:Gem::Version
|
77
|
+
version: '0'
|
58
78
|
- !ruby/object:Gem::Dependency
|
59
79
|
name: guard-rspec
|
60
|
-
requirement:
|
80
|
+
requirement: !ruby/object:Gem::Requirement
|
61
81
|
none: false
|
62
82
|
requirements:
|
63
83
|
- - ! '>='
|
@@ -65,10 +85,15 @@ dependencies:
|
|
65
85
|
version: '0'
|
66
86
|
type: :development
|
67
87
|
prerelease: false
|
68
|
-
version_requirements:
|
88
|
+
version_requirements: !ruby/object:Gem::Requirement
|
89
|
+
none: false
|
90
|
+
requirements:
|
91
|
+
- - ! '>='
|
92
|
+
- !ruby/object:Gem::Version
|
93
|
+
version: '0'
|
69
94
|
- !ruby/object:Gem::Dependency
|
70
95
|
name: rake
|
71
|
-
requirement:
|
96
|
+
requirement: !ruby/object:Gem::Requirement
|
72
97
|
none: false
|
73
98
|
requirements:
|
74
99
|
- - ! '>='
|
@@ -76,10 +101,15 @@ dependencies:
|
|
76
101
|
version: '0'
|
77
102
|
type: :development
|
78
103
|
prerelease: false
|
79
|
-
version_requirements:
|
104
|
+
version_requirements: !ruby/object:Gem::Requirement
|
105
|
+
none: false
|
106
|
+
requirements:
|
107
|
+
- - ! '>='
|
108
|
+
- !ruby/object:Gem::Version
|
109
|
+
version: '0'
|
80
110
|
- !ruby/object:Gem::Dependency
|
81
111
|
name: rdoc
|
82
|
-
requirement:
|
112
|
+
requirement: !ruby/object:Gem::Requirement
|
83
113
|
none: false
|
84
114
|
requirements:
|
85
115
|
- - ! '>='
|
@@ -87,10 +117,15 @@ dependencies:
|
|
87
117
|
version: '0'
|
88
118
|
type: :development
|
89
119
|
prerelease: false
|
90
|
-
version_requirements:
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
none: false
|
122
|
+
requirements:
|
123
|
+
- - ! '>='
|
124
|
+
- !ruby/object:Gem::Version
|
125
|
+
version: '0'
|
91
126
|
- !ruby/object:Gem::Dependency
|
92
127
|
name: rspec
|
93
|
-
requirement:
|
128
|
+
requirement: !ruby/object:Gem::Requirement
|
94
129
|
none: false
|
95
130
|
requirements:
|
96
131
|
- - ! '>='
|
@@ -98,10 +133,15 @@ dependencies:
|
|
98
133
|
version: '0'
|
99
134
|
type: :development
|
100
135
|
prerelease: false
|
101
|
-
version_requirements:
|
136
|
+
version_requirements: !ruby/object:Gem::Requirement
|
137
|
+
none: false
|
138
|
+
requirements:
|
139
|
+
- - ! '>='
|
140
|
+
- !ruby/object:Gem::Version
|
141
|
+
version: '0'
|
102
142
|
- !ruby/object:Gem::Dependency
|
103
143
|
name: tzinfo
|
104
|
-
requirement:
|
144
|
+
requirement: !ruby/object:Gem::Requirement
|
105
145
|
none: false
|
106
146
|
requirements:
|
107
147
|
- - ! '>='
|
@@ -109,7 +149,12 @@ dependencies:
|
|
109
149
|
version: '0'
|
110
150
|
type: :development
|
111
151
|
prerelease: false
|
112
|
-
version_requirements:
|
152
|
+
version_requirements: !ruby/object:Gem::Requirement
|
153
|
+
none: false
|
154
|
+
requirements:
|
155
|
+
- - ! '>='
|
156
|
+
- !ruby/object:Gem::Version
|
157
|
+
version: '0'
|
113
158
|
description: This gem provides implements instrumentation with Errplane for Rails
|
114
159
|
2.3.x and 3.x applications.
|
115
160
|
email:
|
@@ -204,7 +249,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
204
249
|
version: '0'
|
205
250
|
requirements: []
|
206
251
|
rubyforge_project: errplane
|
207
|
-
rubygems_version: 1.8.
|
252
|
+
rubygems_version: 1.8.24
|
208
253
|
signing_key:
|
209
254
|
specification_version: 3
|
210
255
|
summary: Rails-based instrumentation library for Errplane.
|