sentry-raven 0.7.1 → 0.8.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.
Potentially problematic release.
This version of sentry-raven might be problematic. Click here for more details.
- data/README.md +76 -13
- data/lib/raven.rb +2 -191
- data/lib/raven/backtrace.rb +5 -4
- data/lib/raven/base.rb +212 -0
- data/lib/raven/cli.rb +7 -9
- data/lib/raven/client.rb +8 -9
- data/lib/raven/configuration.rb +20 -3
- data/lib/raven/error.rb +0 -2
- data/lib/raven/event.rb +16 -19
- data/lib/raven/interfaces.rb +2 -3
- data/lib/raven/interfaces/exception.rb +0 -3
- data/lib/raven/interfaces/http.rb +10 -11
- data/lib/raven/interfaces/message.rb +0 -2
- data/lib/raven/interfaces/stack_trace.rb +7 -10
- data/lib/raven/linecache.rb +1 -3
- data/lib/raven/logger.rb +2 -4
- data/lib/raven/okjson.rb +2 -0
- data/lib/raven/processor.rb +0 -2
- data/lib/raven/processors/sanitizedata.rb +4 -3
- data/lib/raven/rack.rb +2 -4
- data/lib/raven/railtie.rb +0 -1
- data/lib/raven/sidekiq.rb +15 -10
- data/lib/raven/tasks.rb +3 -4
- data/lib/raven/transports.rb +1 -6
- data/lib/raven/transports/http.rb +1 -6
- data/lib/raven/transports/udp.rb +0 -5
- data/lib/raven/version.rb +1 -1
- data/lib/sentry-raven.rb +1 -1
- metadata +26 -14
data/lib/raven/cli.rb
CHANGED
@@ -2,7 +2,7 @@ require 'raven'
|
|
2
2
|
|
3
3
|
module Raven
|
4
4
|
class CLI
|
5
|
-
def self.test(dsn=nil)
|
5
|
+
def self.test(dsn = nil)
|
6
6
|
require 'logger'
|
7
7
|
|
8
8
|
logger = ::Logger.new(STDOUT)
|
@@ -13,26 +13,24 @@ module Raven
|
|
13
13
|
|
14
14
|
Raven.configuration.logger = logger
|
15
15
|
|
16
|
-
if dsn
|
17
|
-
Raven.configuration.dsn = dsn
|
18
|
-
end
|
16
|
+
Raven.configuration.dsn = dsn if dsn
|
19
17
|
|
20
18
|
# wipe out env settings to ensure we send the event
|
21
|
-
|
19
|
+
unless Raven.configuration.send_in_current_environment?
|
22
20
|
environments = Raven.configuration.environments
|
23
21
|
env_name = (environments && environments[0]) || 'production'
|
24
22
|
puts "Setting environment to #{env_name}"
|
25
23
|
Raven.configuration.current_environment = env_name
|
26
24
|
end
|
27
25
|
|
28
|
-
|
26
|
+
unless Raven.configuration.server
|
29
27
|
puts "Your client is not configured!"
|
30
28
|
exit 1
|
31
29
|
end
|
32
30
|
|
33
31
|
puts "Client configuration:"
|
34
32
|
['server', 'project_id', 'public_key', 'secret_key'].each do |key|
|
35
|
-
|
33
|
+
unless Raven.configuration[key]
|
36
34
|
puts "Missing configuration for #{key}"
|
37
35
|
exit 1
|
38
36
|
end
|
@@ -48,7 +46,7 @@ module Raven
|
|
48
46
|
evt = Raven.capture_exception(exception)
|
49
47
|
end
|
50
48
|
|
51
|
-
if evt
|
49
|
+
if evt
|
52
50
|
puts "-> event ID: #{evt.id}"
|
53
51
|
else
|
54
52
|
puts ""
|
@@ -60,4 +58,4 @@ module Raven
|
|
60
58
|
puts "Done!"
|
61
59
|
end
|
62
60
|
end
|
63
|
-
end
|
61
|
+
end
|
data/lib/raven/client.rb
CHANGED
@@ -22,8 +22,8 @@ module Raven
|
|
22
22
|
end
|
23
23
|
|
24
24
|
def send(event)
|
25
|
-
|
26
|
-
|
25
|
+
unless configuration.send_in_current_environment?
|
26
|
+
configuration.log_excluded_environment_message
|
27
27
|
return
|
28
28
|
end
|
29
29
|
|
@@ -34,17 +34,17 @@ module Raven
|
|
34
34
|
content_type, encoded_data = encode(event)
|
35
35
|
begin
|
36
36
|
transport.send(generate_auth_header(encoded_data), encoded_data,
|
37
|
-
|
37
|
+
:content_type => content_type)
|
38
38
|
rescue => e
|
39
39
|
Raven.logger.error "Unable to record event with remote Sentry server (#{e.class} - #{e.message})"
|
40
40
|
e.backtrace[0..10].each { |line| Raven.logger.error(line) }
|
41
41
|
return
|
42
42
|
end
|
43
43
|
|
44
|
-
|
44
|
+
event
|
45
45
|
end
|
46
46
|
|
47
|
-
|
47
|
+
private
|
48
48
|
|
49
49
|
def encode(event)
|
50
50
|
hash = event.to_hash
|
@@ -67,7 +67,8 @@ module Raven
|
|
67
67
|
end
|
68
68
|
|
69
69
|
def transport
|
70
|
-
@transport ||=
|
70
|
+
@transport ||=
|
71
|
+
case self.configuration.scheme
|
71
72
|
when 'udp'
|
72
73
|
Transports::UDP.new self.configuration
|
73
74
|
when 'http', 'https'
|
@@ -86,9 +87,7 @@ module Raven
|
|
86
87
|
'sentry_key' => self.configuration.public_key,
|
87
88
|
'sentry_secret' => self.configuration.secret_key,
|
88
89
|
}
|
89
|
-
'Sentry ' + fields.map{|key, value| "#{key}=#{value}"}.join(', ')
|
90
|
+
'Sentry ' + fields.map { |key, value| "#{key}=#{value}" }.join(', ')
|
90
91
|
end
|
91
|
-
|
92
92
|
end
|
93
|
-
|
94
93
|
end
|
data/lib/raven/configuration.rb
CHANGED
@@ -67,9 +67,15 @@ module Raven
|
|
67
67
|
# DEPRECATED: This option is now ignored as we use our own adapter.
|
68
68
|
attr_accessor :json_adapter
|
69
69
|
|
70
|
-
# Default tags for events
|
70
|
+
# Default tags for events
|
71
71
|
attr_accessor :tags
|
72
72
|
|
73
|
+
# Optional Proc to be used to send events asynchronously.
|
74
|
+
attr_reader :async
|
75
|
+
|
76
|
+
# Exceptions from these directories to be ignored
|
77
|
+
attr_accessor :app_dirs_pattern
|
78
|
+
|
73
79
|
IGNORE_DEFAULT = ['ActiveRecord::RecordNotFound',
|
74
80
|
'ActionController::RoutingError',
|
75
81
|
'ActionController::InvalidAuthenticityToken',
|
@@ -90,10 +96,11 @@ module Raven
|
|
90
96
|
self.timeout = 1
|
91
97
|
self.open_timeout = 1
|
92
98
|
self.tags = {}
|
99
|
+
self.async = false
|
93
100
|
end
|
94
101
|
|
95
102
|
def server=(value)
|
96
|
-
uri = URI
|
103
|
+
uri = URI.parse(value)
|
97
104
|
uri_path = uri.path.split('/')
|
98
105
|
|
99
106
|
if uri.user
|
@@ -110,7 +117,7 @@ module Raven
|
|
110
117
|
|
111
118
|
# For anyone who wants to read the base server string
|
112
119
|
@server = "#{@scheme}://#{@host}"
|
113
|
-
@server << ":#{@port}" unless @port == {'http'=>80,'https'=>443}[@scheme]
|
120
|
+
@server << ":#{@port}" unless @port == { 'http' => 80, 'https' => 443 }[@scheme]
|
114
121
|
@server << @path
|
115
122
|
end
|
116
123
|
|
@@ -121,6 +128,13 @@ module Raven
|
|
121
128
|
|
122
129
|
alias_method :dsn=, :server=
|
123
130
|
|
131
|
+
def async=(value)
|
132
|
+
raise ArgumentError.new("async must be callable (or false to disable)") unless (value == false || value.respond_to?(:call))
|
133
|
+
@async = value
|
134
|
+
end
|
135
|
+
|
136
|
+
alias_method :async?, :async
|
137
|
+
|
124
138
|
# Allows config options to be read like a hash
|
125
139
|
#
|
126
140
|
# @param [Symbol] option Key for a given attribute
|
@@ -140,5 +154,8 @@ module Raven
|
|
140
154
|
end
|
141
155
|
end
|
142
156
|
|
157
|
+
def log_excluded_environment_message
|
158
|
+
Raven.logger.debug "Event not sent due to excluded environment: #{current_environment}"
|
159
|
+
end
|
143
160
|
end
|
144
161
|
end
|
data/lib/raven/error.rb
CHANGED
data/lib/raven/event.rb
CHANGED
@@ -26,7 +26,7 @@ module Raven
|
|
26
26
|
attr_accessor :project, :message, :timestamp, :level
|
27
27
|
attr_accessor :logger, :culprit, :server_name, :modules, :extra, :tags
|
28
28
|
|
29
|
-
def initialize(options={}, &block)
|
29
|
+
def initialize(options = {}, &block)
|
30
30
|
@configuration = options[:configuration] || Raven.configuration
|
31
31
|
@interfaces = {}
|
32
32
|
|
@@ -41,9 +41,8 @@ module Raven
|
|
41
41
|
@culprit = options[:culprit]
|
42
42
|
@server_name = options[:server_name] || @configuration.server_name || get_hostname
|
43
43
|
|
44
|
-
if @configuration.send_modules
|
45
|
-
|
46
|
-
end
|
44
|
+
options[:modules] ||= get_modules if @configuration.send_modules
|
45
|
+
|
47
46
|
@modules = options[:modules]
|
48
47
|
|
49
48
|
@user = options[:user] || {}
|
@@ -79,11 +78,11 @@ module Raven
|
|
79
78
|
|
80
79
|
def get_modules
|
81
80
|
# Older versions of Rubygems don't support iterating over all specs
|
82
|
-
Hash[Gem::Specification.map {|spec| [spec.name, spec.version.to_s]}] if Gem::Specification.respond_to?(:map)
|
81
|
+
Hash[Gem::Specification.map { |spec| [spec.name, spec.version.to_s] }] if Gem::Specification.respond_to?(:map)
|
83
82
|
end
|
84
83
|
|
85
|
-
def interface(name, value=nil, &block)
|
86
|
-
int = Raven
|
84
|
+
def interface(name, value = nil, &block)
|
85
|
+
int = Raven.find_interface(name)
|
87
86
|
raise Error.new("Unknown interface: #{name}") unless int
|
88
87
|
@interfaces[int.name] = int.new(value, &block) if value || block
|
89
88
|
@interfaces[int.name]
|
@@ -119,7 +118,7 @@ module Raven
|
|
119
118
|
data
|
120
119
|
end
|
121
120
|
|
122
|
-
def self.from_exception(exc, options={}, &block)
|
121
|
+
def self.from_exception(exc, options = {}, &block)
|
123
122
|
notes = exc.instance_variable_get(:@__raven_context) || {}
|
124
123
|
options = notes.merge(options)
|
125
124
|
|
@@ -140,21 +139,21 @@ module Raven
|
|
140
139
|
evt.message = "#{exc.class.to_s}: #{exc.message}"
|
141
140
|
evt.level = options[:level] || :error
|
142
141
|
evt.parse_exception(exc)
|
143
|
-
if
|
142
|
+
if exc.backtrace
|
144
143
|
evt.interface :stack_trace do |int|
|
145
144
|
backtrace = Backtrace.parse(exc.backtrace)
|
146
|
-
int.frames = backtrace.lines.reverse.map
|
145
|
+
int.frames = backtrace.lines.reverse.map do |line|
|
147
146
|
int.frame do |frame|
|
148
147
|
frame.abs_path = line.file
|
149
148
|
frame.function = line.method
|
150
149
|
frame.lineno = line.number
|
151
150
|
frame.in_app = line.in_app
|
152
|
-
if context_lines
|
151
|
+
if context_lines && frame.abs_path
|
153
152
|
frame.pre_context, frame.context_line, frame.post_context = \
|
154
153
|
evt.get_file_context(frame.abs_path, frame.lineno, context_lines)
|
155
154
|
end
|
156
155
|
end
|
157
|
-
|
156
|
+
end.select { |f| f.filename }
|
158
157
|
evt.culprit = evt.get_culprit(int.frames)
|
159
158
|
end
|
160
159
|
end
|
@@ -162,7 +161,7 @@ module Raven
|
|
162
161
|
end
|
163
162
|
end
|
164
163
|
|
165
|
-
def self.from_message(message, options={})
|
164
|
+
def self.from_message(message, options = {})
|
166
165
|
new(options) do |evt|
|
167
166
|
evt.message = message
|
168
167
|
evt.level = options[:level] || :error
|
@@ -178,20 +177,20 @@ module Raven
|
|
178
177
|
|
179
178
|
def get_file_context(filename, lineno, context)
|
180
179
|
lines = (2 * context + 1).times.map do |i|
|
181
|
-
Raven::LineCache
|
180
|
+
Raven::LineCache.getline(filename, lineno - context + i)
|
182
181
|
end
|
183
|
-
[lines[0..(context-1)], lines[context], lines[(context+1)..-1]]
|
182
|
+
[lines[0..(context - 1)], lines[context], lines[(context + 1)..-1]]
|
184
183
|
end
|
185
184
|
|
186
185
|
def get_culprit(frames)
|
187
|
-
lastframe = frames.reverse.
|
186
|
+
lastframe = frames.reverse.find { |f| f.in_app } || frames.last
|
188
187
|
"#{lastframe.filename} in #{lastframe.function} at line #{lastframe.lineno}" if lastframe
|
189
188
|
end
|
190
189
|
|
191
190
|
def parse_exception(exception)
|
192
191
|
interface(:exception) do |int|
|
193
192
|
int.type = exception.class.to_s
|
194
|
-
int.value = exception.
|
193
|
+
int.value = exception.to_s
|
195
194
|
int.module = exception.class.to_s.split('::')[0...-1].join('::')
|
196
195
|
end
|
197
196
|
end
|
@@ -203,7 +202,5 @@ module Raven
|
|
203
202
|
alias :capture_exception :from_exception
|
204
203
|
alias :capture_message :from_message
|
205
204
|
end
|
206
|
-
|
207
|
-
private
|
208
205
|
end
|
209
206
|
end
|
data/lib/raven/interfaces.rb
CHANGED
@@ -5,7 +5,7 @@ module Raven
|
|
5
5
|
INTERFACES = {}
|
6
6
|
|
7
7
|
class Interface < Hashie::Dash
|
8
|
-
def initialize(attributes={}, &block)
|
8
|
+
def initialize(attributes = {}, &block)
|
9
9
|
@check_required = false
|
10
10
|
super(attributes)
|
11
11
|
block.call(self) if block
|
@@ -17,7 +17,7 @@ module Raven
|
|
17
17
|
super if @check_required
|
18
18
|
end
|
19
19
|
|
20
|
-
def self.name(value=nil)
|
20
|
+
def self.name(value = nil)
|
21
21
|
@interface_name = value if value
|
22
22
|
@interface_name
|
23
23
|
end
|
@@ -33,5 +33,4 @@ module Raven
|
|
33
33
|
def self.find_interface(name)
|
34
34
|
INTERFACES[name.to_s]
|
35
35
|
end
|
36
|
-
|
37
36
|
end
|
@@ -1,16 +1,13 @@
|
|
1
1
|
require 'raven/interfaces'
|
2
2
|
|
3
3
|
module Raven
|
4
|
-
|
5
4
|
class ExceptionInterface < Interface
|
6
5
|
|
7
6
|
name 'sentry.interfaces.Exception'
|
8
7
|
property :type, :required => true
|
9
8
|
property :value, :required => true
|
10
9
|
property :module
|
11
|
-
|
12
10
|
end
|
13
11
|
|
14
12
|
register_interface :exception => ExceptionInterface
|
15
|
-
|
16
13
|
end
|
@@ -1,7 +1,6 @@
|
|
1
1
|
require 'raven/interfaces'
|
2
2
|
|
3
3
|
module Raven
|
4
|
-
|
5
4
|
class HttpInterface < Interface
|
6
5
|
|
7
6
|
name 'sentry.interfaces.Http'
|
@@ -29,7 +28,7 @@ module Raven
|
|
29
28
|
next unless key.upcase == key # Non-upper case stuff isn't either
|
30
29
|
if key.start_with?('HTTP_')
|
31
30
|
# Header
|
32
|
-
http_key = key[5..key.length-1].split('_').map{|s| s.capitalize}.join('-')
|
31
|
+
http_key = key[5..key.length - 1].split('_').map { |s| s.capitalize }.join('-')
|
33
32
|
self.headers[http_key] = value.to_s
|
34
33
|
elsif ['CONTENT_TYPE', 'CONTENT_LENGTH'].include? key
|
35
34
|
self.headers[key.capitalize] = value.to_s
|
@@ -38,17 +37,17 @@ module Raven
|
|
38
37
|
self.env[key] = value.to_s
|
39
38
|
end
|
40
39
|
end
|
41
|
-
self.data = if req.form_data?
|
42
|
-
req.POST
|
43
|
-
elsif req.body
|
44
|
-
data = req.body.read
|
45
|
-
req.body.rewind
|
46
|
-
data
|
47
|
-
end
|
48
|
-
end
|
49
40
|
|
41
|
+
self.data =
|
42
|
+
if req.form_data?
|
43
|
+
req.POST
|
44
|
+
elsif req.body
|
45
|
+
data = req.body.read
|
46
|
+
req.body.rewind
|
47
|
+
data
|
48
|
+
end
|
49
|
+
end
|
50
50
|
end
|
51
51
|
|
52
52
|
register_interface :http => HttpInterface
|
53
|
-
|
54
53
|
end
|
@@ -3,7 +3,6 @@ require 'hashie'
|
|
3
3
|
require 'raven/interfaces'
|
4
4
|
|
5
5
|
module Raven
|
6
|
-
|
7
6
|
class StacktraceInterface < Interface
|
8
7
|
|
9
8
|
name 'sentry.interfaces.Stacktrace'
|
@@ -14,13 +13,13 @@ module Raven
|
|
14
13
|
super(*arguments)
|
15
14
|
end
|
16
15
|
|
17
|
-
def to_hash
|
18
|
-
data = super
|
19
|
-
data['frames'] = data['frames'].map{|frame| frame.to_hash}
|
16
|
+
def to_hash(*args)
|
17
|
+
data = super(*args)
|
18
|
+
data['frames'] = data['frames'].map { |frame| frame.to_hash }
|
20
19
|
data
|
21
20
|
end
|
22
21
|
|
23
|
-
def frame(attributes=nil, &block)
|
22
|
+
def frame(attributes = nil, &block)
|
24
23
|
Frame.new(attributes, &block)
|
25
24
|
end
|
26
25
|
|
@@ -45,12 +44,12 @@ module Raven
|
|
45
44
|
def filename
|
46
45
|
return nil if self.abs_path.nil?
|
47
46
|
|
48
|
-
prefix =
|
47
|
+
prefix = $LOAD_PATH.select { |s| self.abs_path.start_with?(s.to_s) }.sort_by { |s| s.to_s.length }.last
|
49
48
|
prefix ? self.abs_path[prefix.chomp(File::SEPARATOR).length+1..-1] : self.abs_path
|
50
49
|
end
|
51
50
|
|
52
|
-
def to_hash
|
53
|
-
data = super
|
51
|
+
def to_hash(*args)
|
52
|
+
data = super(*args)
|
54
53
|
data['filename'] = self.filename
|
55
54
|
data.delete('vars') unless self.vars && !self.vars.empty?
|
56
55
|
data.delete('pre_context') unless self.pre_context && !self.pre_context.empty?
|
@@ -59,9 +58,7 @@ module Raven
|
|
59
58
|
data
|
60
59
|
end
|
61
60
|
end
|
62
|
-
|
63
61
|
end
|
64
62
|
|
65
63
|
register_interface :stack_trace => StacktraceInterface
|
66
|
-
|
67
64
|
end
|
data/lib/raven/linecache.rb
CHANGED
data/lib/raven/logger.rb
CHANGED
@@ -13,12 +13,10 @@ module Raven
|
|
13
13
|
msg = args[0] # Block-level default args is a 1.9 feature
|
14
14
|
msg ||= block.call if block
|
15
15
|
logger = Raven.configuration[:logger]
|
16
|
-
if logger.nil?
|
17
|
-
|
18
|
-
end
|
16
|
+
logger = ::Logger.new(STDOUT) if logger.nil?
|
17
|
+
|
19
18
|
logger.send(level, "#{LOG_PREFIX}#{msg}") if logger
|
20
19
|
end
|
21
20
|
end
|
22
|
-
|
23
21
|
end
|
24
22
|
end
|