opbeat 0.8.0 → 0.9.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/README.md +38 -7
- data/lib/opbeat.rb +8 -5
- data/lib/opbeat/client.rb +0 -1
- data/lib/opbeat/configuration.rb +3 -0
- data/lib/opbeat/event.rb +46 -11
- data/lib/opbeat/rails/middleware/debug_exceptions_catcher.rb +3 -3
- data/lib/opbeat/version.rb +1 -1
- metadata +10 -10
data/README.md
CHANGED
@@ -104,13 +104,6 @@ Resque::Failure::Multiple.classes = [Resque::Failure::Opbeat]
|
|
104
104
|
Resque::Failure.backend = Resque::Failure::Multiple
|
105
105
|
```
|
106
106
|
|
107
|
-
## Testing
|
108
|
-
|
109
|
-
```bash
|
110
|
-
$ bundle install
|
111
|
-
$ rake spec
|
112
|
-
```
|
113
|
-
|
114
107
|
## Explicitly notifying Opbeat
|
115
108
|
|
116
109
|
It is possible to explicitely notify Opbeat. In the case of a simple message:
|
@@ -126,6 +119,12 @@ rescue Exception => e
|
|
126
119
|
Opbeat.captureException(e)
|
127
120
|
```
|
128
121
|
|
122
|
+
Both `Opbeat.captureException` and `Opbeat.captureMessage` take additional `options`:
|
123
|
+
```ruby
|
124
|
+
Opbeat.captureMessage("Device registration error", :extra => {:device_id => my_device_id})
|
125
|
+
```
|
126
|
+
|
127
|
+
|
129
128
|
## Notifications in development mode
|
130
129
|
|
131
130
|
By default events will be sent to Opbeat if your application is running in any of the following environments: `development`, `production`, `default`. Environment is set by default if you are running a Rack application (i.e. anytime `ENV['RACK_ENV']` is set).
|
@@ -182,6 +181,38 @@ Opbeat.configure do |config|
|
|
182
181
|
end
|
183
182
|
```
|
184
183
|
|
184
|
+
## User information
|
185
|
+
|
186
|
+
With Rails, Opbeat expects `controller#current_user` to return an object with `id`, `email` and/or `username` attributes. You can change the name of the current user method in the following manner:
|
187
|
+
|
188
|
+
```ruby
|
189
|
+
Opbeat.configure do |config|
|
190
|
+
...
|
191
|
+
config.user_controller_method = "my_other_user_method"
|
192
|
+
end
|
193
|
+
```
|
194
|
+
|
195
|
+
Opbeat will now call `controller#my_other_user_method` to retrieve the user object.
|
196
|
+
|
197
|
+
## Setting context
|
198
|
+
|
199
|
+
It is possible to set a context which be included an exceptions that are captured.
|
200
|
+
|
201
|
+
```ruby
|
202
|
+
Opbeat.set_context :extra => {:device_id => my_device_id}
|
203
|
+
|
204
|
+
Opbeat.captureMessage("Hello world") # will include the context
|
205
|
+
```
|
206
|
+
|
207
|
+
|
208
|
+
## Testing
|
209
|
+
|
210
|
+
```bash
|
211
|
+
$ bundle install
|
212
|
+
$ rake spec
|
213
|
+
```
|
214
|
+
|
215
|
+
|
185
216
|
## Resources
|
186
217
|
|
187
218
|
* [Bug Tracker](http://github.com/opbeat/opbeat_ruby/issues)
|
data/lib/opbeat.rb
CHANGED
@@ -19,7 +19,7 @@ require 'opbeat/railtie' if defined?(Rails::Railtie)
|
|
19
19
|
module Opbeat
|
20
20
|
class << self
|
21
21
|
# The client object is responsible for delivering formatted data to the Opbeat server.
|
22
|
-
# Must respond to #
|
22
|
+
# Must respond to #send_event. See Opbeat::Client.
|
23
23
|
attr_accessor :client
|
24
24
|
|
25
25
|
# A Opbeat configuration object. Must act like a hash and return sensible
|
@@ -91,15 +91,18 @@ module Opbeat
|
|
91
91
|
end
|
92
92
|
end
|
93
93
|
|
94
|
-
def captureException(exception)
|
95
|
-
evt = Event.capture_exception(exception)
|
94
|
+
def captureException(exception, options={})
|
95
|
+
evt = Event.capture_exception(exception, options)
|
96
96
|
send(evt) if evt
|
97
97
|
end
|
98
98
|
|
99
|
-
def captureMessage(message)
|
100
|
-
evt = Event.capture_message(message)
|
99
|
+
def captureMessage(message, options={})
|
100
|
+
evt = Event.capture_message(message, options)
|
101
101
|
send(evt) if evt
|
102
102
|
end
|
103
103
|
|
104
|
+
def set_context(options={})
|
105
|
+
Event.set_context(options)
|
106
|
+
end
|
104
107
|
end
|
105
108
|
end
|
data/lib/opbeat/client.rb
CHANGED
@@ -95,7 +95,6 @@ module Opbeat
|
|
95
95
|
req.headers[AUTH_HEADER_KEY] = self.generate_auth_header(req.body)
|
96
96
|
req.headers["User-Agent"] = USER_AGENT
|
97
97
|
end
|
98
|
-
|
99
98
|
unless response.status == 202
|
100
99
|
raise Error.new("Error from Opbeat server (#{response.status}): #{response.body}")
|
101
100
|
end
|
data/lib/opbeat/configuration.rb
CHANGED
@@ -42,6 +42,8 @@ module Opbeat
|
|
42
42
|
|
43
43
|
attr_reader :current_environment
|
44
44
|
|
45
|
+
attr_accessor :user_controller_method
|
46
|
+
|
45
47
|
def initialize
|
46
48
|
self.server = ENV['OPBEAT_SERVER'] || "https://opbeat.com"
|
47
49
|
self.secret_token = ENV['OPBEAT_SECRET_TOKEN'] if ENV['OPBEAT_SECRET_TOKEN']
|
@@ -55,6 +57,7 @@ module Opbeat
|
|
55
57
|
self.timeout = 1
|
56
58
|
self.backoff_multiplier = 2
|
57
59
|
self.ssl_verification = true
|
60
|
+
self.user_controller_method = 'current_user'
|
58
61
|
end
|
59
62
|
|
60
63
|
# Allows config options to be read like a hash
|
data/lib/opbeat/event.rb
CHANGED
@@ -21,7 +21,7 @@ module Opbeat
|
|
21
21
|
|
22
22
|
attr_reader :id
|
23
23
|
attr_accessor :organization, :app, :message, :timestamp, :level
|
24
|
-
attr_accessor :logger, :culprit, :hostname, :modules, :extra
|
24
|
+
attr_accessor :logger, :culprit, :hostname, :modules, :extra, :user
|
25
25
|
attr_accessor :environment
|
26
26
|
|
27
27
|
def initialize(options={}, configuration=nil, &block)
|
@@ -36,6 +36,7 @@ module Opbeat
|
|
36
36
|
@culprit = options[:culprit]
|
37
37
|
@environment = @configuration[:current_environment]
|
38
38
|
@extra = options[:extra]
|
39
|
+
@user = options[:user]
|
39
40
|
|
40
41
|
# Try to resolve the hostname to an FQDN, but fall back to whatever the load name is
|
41
42
|
hostname = Socket.gethostname
|
@@ -81,14 +82,20 @@ module Opbeat
|
|
81
82
|
data['machine'] = {'hostname' => self.hostname } if self.hostname
|
82
83
|
data['environment'] = self.environment if self.environment
|
83
84
|
data['extra'] = self.extra if self.extra
|
85
|
+
if self.user
|
86
|
+
data['user'] = self.user
|
87
|
+
if self.user[:id] or self.user[:email] or self.user[:username]
|
88
|
+
data['user'][:is_authenticated] = true
|
89
|
+
end
|
90
|
+
end
|
84
91
|
@interfaces.each_pair do |name, int_data|
|
85
92
|
data[name] = int_data.to_hash
|
86
93
|
end
|
87
94
|
data
|
88
95
|
end
|
89
96
|
|
90
|
-
def self.capture_exception(exc,
|
91
|
-
configuration
|
97
|
+
def self.capture_exception(exc, options={}, &block)
|
98
|
+
configuration = Opbeat.configuration
|
92
99
|
if exc.is_a?(Opbeat::Error)
|
93
100
|
# Try to prevent error reporting loops
|
94
101
|
Opbeat.logger.info "Refusing to capture Opbeat error: #{exc.inspect}"
|
@@ -98,7 +105,8 @@ module Opbeat
|
|
98
105
|
Opbeat.logger.info "User excluded error: #{exc.inspect}"
|
99
106
|
return nil
|
100
107
|
end
|
101
|
-
self.
|
108
|
+
options = self.merge_context(options)
|
109
|
+
self.new(options, configuration) do |evt|
|
102
110
|
evt.message = "#{exc.class.to_s}: #{exc.message}"
|
103
111
|
evt.level = :error
|
104
112
|
evt.parse_exception(exc)
|
@@ -114,19 +122,29 @@ module Opbeat
|
|
114
122
|
end
|
115
123
|
end
|
116
124
|
|
117
|
-
def self.capture_rack_exception(exc, rack_env,
|
118
|
-
|
119
|
-
capture_exception(exc, configuration) do |evt|
|
125
|
+
def self.capture_rack_exception(exc, rack_env, options={}, &block)
|
126
|
+
capture_exception(exc, options) do |evt|
|
120
127
|
evt.interface :http do |int|
|
121
128
|
int.from_rack(rack_env)
|
122
129
|
end
|
130
|
+
|
131
|
+
if not evt.user
|
132
|
+
controller = rack_env["action_controller.instance"]
|
133
|
+
user_method_name = Opbeat.configuration.user_controller_method
|
134
|
+
if controller and controller.respond_to? user_method_name
|
135
|
+
user_obj = controller.send user_method_name
|
136
|
+
evt.from_user_object(user_obj)
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
123
140
|
block.call(evt) if block
|
124
141
|
end
|
125
142
|
end
|
126
143
|
|
127
|
-
def self.capture_message(message,
|
144
|
+
def self.capture_message(message, options={})
|
128
145
|
configuration ||= Opbeat.configuration
|
129
|
-
self.
|
146
|
+
options = self.merge_context(options)
|
147
|
+
self.new(options, configuration) do |evt|
|
130
148
|
evt.message = message
|
131
149
|
evt.level = :error
|
132
150
|
evt.interface :message do |int|
|
@@ -135,6 +153,10 @@ module Opbeat
|
|
135
153
|
end
|
136
154
|
end
|
137
155
|
|
156
|
+
def self.set_context(options={})
|
157
|
+
Thread.current["_opbeat_context"] = options
|
158
|
+
end
|
159
|
+
|
138
160
|
def get_culprit(frames)
|
139
161
|
lastframe = frames[-2]
|
140
162
|
"#{lastframe.filename} in #{lastframe.function}" if lastframe
|
@@ -157,11 +179,18 @@ module Opbeat
|
|
157
179
|
frame.filename = strip_load_path_from(frame.abs_path)
|
158
180
|
if context_lines = @configuration[:context_lines]
|
159
181
|
frame.pre_context, frame.context_line, frame.post_context = \
|
160
|
-
|
182
|
+
get_contextlines(frame.abs_path, frame.lineno, context_lines)
|
161
183
|
end
|
162
184
|
frame
|
163
185
|
end
|
164
186
|
|
187
|
+
def from_user_object(user_obj)
|
188
|
+
@user = {} if not @user
|
189
|
+
@user[:id] = user_obj.send(:id) rescue nil
|
190
|
+
@user[:email] = user_obj.send(:email) rescue nil
|
191
|
+
@user[:username] = user_obj.send(:username) rescue nil
|
192
|
+
end
|
193
|
+
|
165
194
|
# For cross-language compat
|
166
195
|
class << self
|
167
196
|
alias :captionException :capture_exception
|
@@ -170,11 +199,17 @@ module Opbeat
|
|
170
199
|
|
171
200
|
private
|
172
201
|
|
202
|
+
def self.merge_context(options={})
|
203
|
+
context_options = Thread.current["_opbeat_context"] || {}
|
204
|
+
context_options.merge(options)
|
205
|
+
end
|
206
|
+
|
207
|
+
|
173
208
|
# Because linecache can go to hell
|
174
209
|
def self._source_lines(path, from, to)
|
175
210
|
end
|
176
211
|
|
177
|
-
def
|
212
|
+
def get_contextlines(path, line, context)
|
178
213
|
lines = (2 * context + 1).times.map do |i|
|
179
214
|
Opbeat::LineCache::getline(path, line - context + i)
|
180
215
|
end
|
@@ -3,10 +3,10 @@ module Opbeat
|
|
3
3
|
module Middleware
|
4
4
|
module DebugExceptionsCatcher
|
5
5
|
def self.included(base)
|
6
|
-
base.send(:alias_method_chain, :render_exception, :
|
6
|
+
base.send(:alias_method_chain, :render_exception, :opbeat)
|
7
7
|
end
|
8
8
|
|
9
|
-
def
|
9
|
+
def render_exception_with_opbeat(env, exception)
|
10
10
|
begin
|
11
11
|
evt = Opbeat::Event.capture_rack_exception(exception, env)
|
12
12
|
Opbeat.send(evt) if evt
|
@@ -14,7 +14,7 @@ module Opbeat
|
|
14
14
|
::Rails::logger.debug "Error capturing or sending exception #{$!}"
|
15
15
|
end
|
16
16
|
|
17
|
-
|
17
|
+
render_exception_without_opbeat(env, exception)
|
18
18
|
end
|
19
19
|
end
|
20
20
|
end
|
data/lib/opbeat/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: opbeat
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.9.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -10,11 +10,11 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date: 2014-
|
13
|
+
date: 2014-08-14 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: faraday
|
17
|
-
requirement: &
|
17
|
+
requirement: &17054920 !ruby/object:Gem::Requirement
|
18
18
|
none: false
|
19
19
|
requirements:
|
20
20
|
- - ! '>='
|
@@ -25,10 +25,10 @@ dependencies:
|
|
25
25
|
version: '0.10'
|
26
26
|
type: :runtime
|
27
27
|
prerelease: false
|
28
|
-
version_requirements: *
|
28
|
+
version_requirements: *17054920
|
29
29
|
- !ruby/object:Gem::Dependency
|
30
30
|
name: uuidtools
|
31
|
-
requirement: &
|
31
|
+
requirement: &17054160 !ruby/object:Gem::Requirement
|
32
32
|
none: false
|
33
33
|
requirements:
|
34
34
|
- - ~>
|
@@ -36,10 +36,10 @@ dependencies:
|
|
36
36
|
version: 2.1.4
|
37
37
|
type: :runtime
|
38
38
|
prerelease: false
|
39
|
-
version_requirements: *
|
39
|
+
version_requirements: *17054160
|
40
40
|
- !ruby/object:Gem::Dependency
|
41
41
|
name: multi_json
|
42
|
-
requirement: &
|
42
|
+
requirement: &17053700 !ruby/object:Gem::Requirement
|
43
43
|
none: false
|
44
44
|
requirements:
|
45
45
|
- - ~>
|
@@ -47,10 +47,10 @@ dependencies:
|
|
47
47
|
version: '1.0'
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
|
-
version_requirements: *
|
50
|
+
version_requirements: *17053700
|
51
51
|
- !ruby/object:Gem::Dependency
|
52
52
|
name: hashie
|
53
|
-
requirement: &
|
53
|
+
requirement: &17053240 !ruby/object:Gem::Requirement
|
54
54
|
none: false
|
55
55
|
requirements:
|
56
56
|
- - ~>
|
@@ -58,7 +58,7 @@ dependencies:
|
|
58
58
|
version: 2.1.1
|
59
59
|
type: :runtime
|
60
60
|
prerelease: false
|
61
|
-
version_requirements: *
|
61
|
+
version_requirements: *17053240
|
62
62
|
description:
|
63
63
|
email: ron@opbeat.com
|
64
64
|
executables: []
|