honeybadger 1.16.7 → 2.0.0.beta.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/LICENSE +19 -0
- data/README.md +37 -16
- data/bin/honeybadger +5 -0
- data/lib/honeybadger.rb +167 -191
- data/lib/honeybadger/agent.rb +136 -0
- data/lib/honeybadger/backend.rb +26 -0
- data/lib/honeybadger/backend/base.rb +66 -0
- data/lib/honeybadger/backend/debug.rb +12 -0
- data/lib/honeybadger/backend/null.rb +16 -0
- data/lib/honeybadger/backend/server.rb +51 -0
- data/lib/honeybadger/backend/test.rb +24 -0
- data/lib/honeybadger/backtrace.rb +29 -24
- data/lib/honeybadger/cli.rb +367 -0
- data/lib/honeybadger/config.rb +333 -0
- data/lib/honeybadger/config/callbacks.rb +70 -0
- data/lib/honeybadger/config/defaults.rb +175 -0
- data/lib/honeybadger/config/env.rb +40 -0
- data/lib/honeybadger/config/yaml.rb +43 -0
- data/lib/honeybadger/const.rb +28 -0
- data/lib/honeybadger/init/rails.rb +84 -0
- data/lib/honeybadger/init/sinatra.rb +27 -0
- data/lib/honeybadger/logging.rb +133 -0
- data/lib/honeybadger/notice.rb +243 -280
- data/lib/honeybadger/plugin.rb +110 -0
- data/lib/honeybadger/plugins/delayed_job.rb +22 -0
- data/lib/honeybadger/{integrations → plugins}/delayed_job/plugin.rb +6 -7
- data/lib/honeybadger/{integrations → plugins}/local_variables.rb +7 -8
- data/lib/honeybadger/{integrations → plugins}/net_http.rb +10 -8
- data/lib/honeybadger/plugins/passenger.rb +24 -0
- data/lib/honeybadger/plugins/rails.rb +61 -0
- data/lib/honeybadger/plugins/sidekiq.rb +35 -0
- data/lib/honeybadger/{integrations → plugins}/thor.rb +9 -8
- data/lib/honeybadger/{integrations → plugins}/unicorn.rb +10 -9
- data/lib/honeybadger/rack/error_notifier.rb +44 -27
- data/lib/honeybadger/rack/metrics_reporter.rb +41 -0
- data/lib/honeybadger/rack/request_hash.rb +50 -0
- data/lib/honeybadger/rack/user_feedback.rb +15 -10
- data/lib/honeybadger/rack/user_informer.rb +14 -3
- data/lib/honeybadger/trace.rb +185 -0
- data/lib/honeybadger/util/http.rb +79 -0
- data/lib/honeybadger/util/request_sanitizer.rb +35 -0
- data/lib/honeybadger/util/sanitizer.rb +71 -0
- data/lib/honeybadger/util/stats.rb +31 -0
- data/lib/honeybadger/version.rb +4 -0
- data/lib/honeybadger/worker.rb +224 -0
- data/lib/honeybadger/worker/batch.rb +50 -0
- data/lib/honeybadger/worker/metered_queue.rb +80 -0
- data/lib/honeybadger/worker/metrics_collection.rb +61 -0
- data/lib/honeybadger/worker/metrics_collector.rb +96 -0
- data/{lib/honeybadger/capistrano.rb → vendor/capistrano-honeybadger/lib/capistrano/honeybadger.rb} +1 -3
- data/vendor/capistrano-honeybadger/lib/capistrano/tasks/deploy.cap +76 -0
- data/vendor/capistrano-honeybadger/lib/honeybadger/capistrano.rb +2 -0
- data/{lib → vendor/capistrano-honeybadger/lib}/honeybadger/capistrano/legacy.rb +16 -15
- data/vendor/thor/lib/thor.rb +484 -0
- data/vendor/thor/lib/thor/actions.rb +319 -0
- data/vendor/thor/lib/thor/actions/create_file.rb +103 -0
- data/vendor/thor/lib/thor/actions/create_link.rb +59 -0
- data/vendor/thor/lib/thor/actions/directory.rb +118 -0
- data/vendor/thor/lib/thor/actions/empty_directory.rb +135 -0
- data/vendor/thor/lib/thor/actions/file_manipulation.rb +316 -0
- data/vendor/thor/lib/thor/actions/inject_into_file.rb +107 -0
- data/vendor/thor/lib/thor/base.rb +656 -0
- data/vendor/thor/lib/thor/command.rb +133 -0
- data/vendor/thor/lib/thor/core_ext/hash_with_indifferent_access.rb +77 -0
- data/vendor/thor/lib/thor/core_ext/io_binary_read.rb +10 -0
- data/vendor/thor/lib/thor/core_ext/ordered_hash.rb +98 -0
- data/vendor/thor/lib/thor/error.rb +32 -0
- data/vendor/thor/lib/thor/group.rb +281 -0
- data/vendor/thor/lib/thor/invocation.rb +178 -0
- data/vendor/thor/lib/thor/line_editor.rb +17 -0
- data/vendor/thor/lib/thor/line_editor/basic.rb +35 -0
- data/vendor/thor/lib/thor/line_editor/readline.rb +88 -0
- data/vendor/thor/lib/thor/parser.rb +4 -0
- data/vendor/thor/lib/thor/parser/argument.rb +73 -0
- data/vendor/thor/lib/thor/parser/arguments.rb +175 -0
- data/vendor/thor/lib/thor/parser/option.rb +125 -0
- data/vendor/thor/lib/thor/parser/options.rb +218 -0
- data/vendor/thor/lib/thor/rake_compat.rb +71 -0
- data/vendor/thor/lib/thor/runner.rb +322 -0
- data/vendor/thor/lib/thor/shell.rb +81 -0
- data/vendor/thor/lib/thor/shell/basic.rb +421 -0
- data/vendor/thor/lib/thor/shell/color.rb +149 -0
- data/vendor/thor/lib/thor/shell/html.rb +126 -0
- data/vendor/thor/lib/thor/util.rb +267 -0
- data/vendor/thor/lib/thor/version.rb +3 -0
- metadata +97 -305
- data/Appraisals +0 -95
- data/CHANGELOG.md +0 -422
- data/Gemfile +0 -8
- data/Gemfile.lock +0 -136
- data/Guardfile +0 -5
- data/MIT-LICENSE +0 -32
- data/Rakefile +0 -159
- data/features/metal.feature +0 -20
- data/features/rack.feature +0 -55
- data/features/rails.feature +0 -343
- data/features/rails3.x.feature +0 -26
- data/features/rake.feature +0 -25
- data/features/sinatra.feature +0 -27
- data/features/standalone.feature +0 -73
- data/features/step_definitions/metal_steps.rb +0 -24
- data/features/step_definitions/rack_steps.rb +0 -18
- data/features/step_definitions/rails_steps.rb +0 -270
- data/features/step_definitions/rake_steps.rb +0 -17
- data/features/step_definitions/standalone_steps.rb +0 -12
- data/features/step_definitions/thor_steps.rb +0 -4
- data/features/support/env.rb +0 -22
- data/features/support/honeybadger_failure_shim.rb.template +0 -5
- data/features/support/honeybadger_shim.rb.template +0 -6
- data/features/support/rails.rb +0 -202
- data/features/support/rake/Rakefile +0 -68
- data/features/support/test.thor +0 -22
- data/features/thor.feature +0 -5
- data/gemfiles/binding_of_caller.gemfile +0 -13
- data/gemfiles/delayed_job.gemfile +0 -13
- data/gemfiles/rack.gemfile +0 -13
- data/gemfiles/rails.gemfile +0 -16
- data/gemfiles/rails2.3.gemfile +0 -15
- data/gemfiles/rails3.0.gemfile +0 -16
- data/gemfiles/rails3.1.gemfile +0 -16
- data/gemfiles/rails3.2.gemfile +0 -16
- data/gemfiles/rails4.0.gemfile +0 -16
- data/gemfiles/rails4.1.gemfile +0 -16
- data/gemfiles/rake.gemfile +0 -13
- data/gemfiles/sinatra.gemfile +0 -13
- data/gemfiles/standalone.gemfile +0 -12
- data/gemfiles/thor.gemfile +0 -13
- data/generators/honeybadger/honeybadger_generator.rb +0 -95
- data/generators/honeybadger/lib/insert_commands.rb +0 -34
- data/generators/honeybadger/lib/rake_commands.rb +0 -24
- data/generators/honeybadger/templates/capistrano_hook.rb +0 -6
- data/generators/honeybadger/templates/honeybadger_tasks.rake +0 -25
- data/generators/honeybadger/templates/initializer.rb +0 -6
- data/honeybadger.gemspec +0 -174
- data/lib/honeybadger/array.rb +0 -53
- data/lib/honeybadger/capistrano/tasks.rake +0 -73
- data/lib/honeybadger/configuration.rb +0 -397
- data/lib/honeybadger/dependency.rb +0 -65
- data/lib/honeybadger/integrations.rb +0 -9
- data/lib/honeybadger/integrations/delayed_job.rb +0 -20
- data/lib/honeybadger/integrations/passenger.rb +0 -18
- data/lib/honeybadger/integrations/sidekiq.rb +0 -37
- data/lib/honeybadger/monitor.rb +0 -17
- data/lib/honeybadger/monitor/railtie.rb +0 -53
- data/lib/honeybadger/monitor/sender.rb +0 -44
- data/lib/honeybadger/monitor/trace.rb +0 -187
- data/lib/honeybadger/monitor/worker.rb +0 -169
- data/lib/honeybadger/payload.rb +0 -101
- data/lib/honeybadger/rack.rb +0 -12
- data/lib/honeybadger/rails.rb +0 -45
- data/lib/honeybadger/rails/action_controller_catcher.rb +0 -30
- data/lib/honeybadger/rails/controller_methods.rb +0 -78
- data/lib/honeybadger/rails/middleware/exceptions_catcher.rb +0 -29
- data/lib/honeybadger/rails3_tasks.rb +0 -94
- data/lib/honeybadger/railtie.rb +0 -52
- data/lib/honeybadger/rake_handler.rb +0 -66
- data/lib/honeybadger/sender.rb +0 -185
- data/lib/honeybadger/shared_tasks.rb +0 -56
- data/lib/honeybadger/stats.rb +0 -29
- data/lib/honeybadger/tasks.rb +0 -95
- data/lib/honeybadger/user_feedback.rb +0 -8
- data/lib/honeybadger/user_informer.rb +0 -8
- data/lib/honeybadger_tasks.rb +0 -69
- data/lib/rails/generators/honeybadger/honeybadger_generator.rb +0 -99
- data/rails/init.rb +0 -1
- data/resources/README.md +0 -34
- data/script/integration_test.rb +0 -38
- data/spec/allocation_stats.rb +0 -32
- data/spec/honeybadger/backtrace_spec.rb +0 -242
- data/spec/honeybadger/capistrano_spec.rb +0 -36
- data/spec/honeybadger/configuration_spec.rb +0 -328
- data/spec/honeybadger/dependency_spec.rb +0 -134
- data/spec/honeybadger/integrations/delayed_job_spec.rb +0 -82
- data/spec/honeybadger/integrations/local_variables_spec.rb +0 -60
- data/spec/honeybadger/integrations/net_http_spec.rb +0 -29
- data/spec/honeybadger/integrations/passenger_spec.rb +0 -29
- data/spec/honeybadger/integrations/sidekiq_spec.rb +0 -60
- data/spec/honeybadger/integrations/thor_spec.rb +0 -32
- data/spec/honeybadger/integrations/unicorn_spec.rb +0 -40
- data/spec/honeybadger/logger_spec.rb +0 -79
- data/spec/honeybadger/monitor/trace_spec.rb +0 -65
- data/spec/honeybadger/monitor/worker_spec.rb +0 -274
- data/spec/honeybadger/notice_spec.rb +0 -669
- data/spec/honeybadger/notifier_spec.rb +0 -328
- data/spec/honeybadger/payload_spec.rb +0 -162
- data/spec/honeybadger/rack_spec.rb +0 -85
- data/spec/honeybadger/rails/action_controller_spec.rb +0 -328
- data/spec/honeybadger/rails_spec.rb +0 -37
- data/spec/honeybadger/sender_spec.rb +0 -317
- data/spec/honeybadger/stats_spec.rb +0 -57
- data/spec/honeybadger/user_feedback_spec.rb +0 -80
- data/spec/honeybadger/user_informer_spec.rb +0 -30
- data/spec/honeybadger_tasks_spec.rb +0 -171
- data/spec/spec_helper.rb +0 -24
- data/spec/support/array_including.rb +0 -31
- data/spec/support/backtraced_exception.rb +0 -9
- data/spec/support/collected_sender.rb +0 -12
- data/spec/support/defines_constants.rb +0 -18
- data/spec/support/helpers.rb +0 -101
@@ -0,0 +1,136 @@
|
|
1
|
+
require 'forwardable'
|
2
|
+
|
3
|
+
require 'honeybadger/version'
|
4
|
+
require 'honeybadger/config'
|
5
|
+
require 'honeybadger/worker'
|
6
|
+
require 'honeybadger/notice'
|
7
|
+
require 'honeybadger/plugin'
|
8
|
+
require 'honeybadger/logging'
|
9
|
+
|
10
|
+
module Honeybadger
|
11
|
+
# Internal: A broker for the configuration and the worker.
|
12
|
+
class Agent
|
13
|
+
extend Forwardable
|
14
|
+
|
15
|
+
include Logging::Helper
|
16
|
+
|
17
|
+
class << self
|
18
|
+
extend Forwardable
|
19
|
+
|
20
|
+
def_delegators :callbacks, :exception_filter, :exception_fingerprint, :backtrace_filter
|
21
|
+
|
22
|
+
def callbacks
|
23
|
+
@callbacks ||= Config::Callbacks.new
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
private
|
28
|
+
|
29
|
+
def self.load_plugins(config)
|
30
|
+
Dir[File.expand_path('../plugins/*.rb', __FILE__)].each do |plugin|
|
31
|
+
require plugin
|
32
|
+
end
|
33
|
+
Plugin.load!(config)
|
34
|
+
end
|
35
|
+
|
36
|
+
public
|
37
|
+
|
38
|
+
def self.instance
|
39
|
+
@instance
|
40
|
+
end
|
41
|
+
|
42
|
+
def self.running?
|
43
|
+
!instance.nil?
|
44
|
+
end
|
45
|
+
|
46
|
+
def self.start(config = {})
|
47
|
+
return true if running?
|
48
|
+
|
49
|
+
unless config.kind_of?(Config)
|
50
|
+
config = Config.new(config)
|
51
|
+
end
|
52
|
+
|
53
|
+
if !config[:enabled]
|
54
|
+
config.logger.info('Unable to start Honeybadger -- disabled by configuration.')
|
55
|
+
return false
|
56
|
+
elsif !config.valid?
|
57
|
+
config.logger.warn('Unable to start Honeybadger -- invalid configuration.')
|
58
|
+
return false
|
59
|
+
elsif !config.ping
|
60
|
+
config.logger.warn('Unable to start Honeybadger -- failed to connect to server.')
|
61
|
+
return false
|
62
|
+
end
|
63
|
+
|
64
|
+
config.logger.info("Starting Honeybadger version #{VERSION}")
|
65
|
+
load_plugins(config)
|
66
|
+
@instance = new(config)
|
67
|
+
@instance.start
|
68
|
+
end
|
69
|
+
|
70
|
+
def self.stop(*args)
|
71
|
+
@instance.stop(*args) if @instance
|
72
|
+
@instance = nil
|
73
|
+
end
|
74
|
+
|
75
|
+
def self.fork(*args)
|
76
|
+
self.instance ? self.instance.fork(*args) : false
|
77
|
+
end
|
78
|
+
|
79
|
+
def self.trace(*args)
|
80
|
+
self.instance ? self.instance.trace(*args) : false
|
81
|
+
end
|
82
|
+
|
83
|
+
def self.timing(*args)
|
84
|
+
self.instance ? self.instance.timing(*args) : false
|
85
|
+
end
|
86
|
+
|
87
|
+
def self.increment(*args)
|
88
|
+
self.instance ? self.instance.increment(*args) : false
|
89
|
+
end
|
90
|
+
|
91
|
+
# Internal: Callback to perform after agent has been stopped at_exit.
|
92
|
+
#
|
93
|
+
# block - An optional block to execute.
|
94
|
+
#
|
95
|
+
# Returns Proc callback.
|
96
|
+
def self.at_exit(&block)
|
97
|
+
@at_exit = Proc.new if block_given?
|
98
|
+
@at_exit
|
99
|
+
end
|
100
|
+
|
101
|
+
def initialize(config)
|
102
|
+
@config = config
|
103
|
+
@worker = Worker.new(config)
|
104
|
+
|
105
|
+
at_exit do
|
106
|
+
stop
|
107
|
+
self.class.at_exit.call if self.class.at_exit
|
108
|
+
end
|
109
|
+
end
|
110
|
+
|
111
|
+
def_delegators :@worker, :start, :fork, :trace, :timing, :increment
|
112
|
+
|
113
|
+
def stop(force = false)
|
114
|
+
info("Shutting down Honeybadger version #{VERSION}")
|
115
|
+
worker.stop(force)
|
116
|
+
end
|
117
|
+
|
118
|
+
def notice(opts)
|
119
|
+
opts.merge!(callbacks: self.class.callbacks)
|
120
|
+
notice = Notice.new(config, opts)
|
121
|
+
|
122
|
+
if notice.ignore?
|
123
|
+
debug { sprintf('ignore notice feature=notices id=%s', notice.id) }
|
124
|
+
false
|
125
|
+
else
|
126
|
+
debug { sprintf('notice feature=notices id=%s', notice.id) }
|
127
|
+
worker.notice(notice)
|
128
|
+
notice.id
|
129
|
+
end
|
130
|
+
end
|
131
|
+
|
132
|
+
private
|
133
|
+
|
134
|
+
attr_reader :worker, :config
|
135
|
+
end
|
136
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
require 'forwardable'
|
2
|
+
|
3
|
+
module Honeybadger
|
4
|
+
module Backend
|
5
|
+
class BackendError < StandardError; end
|
6
|
+
|
7
|
+
def self.mapping
|
8
|
+
@@mapping ||= {
|
9
|
+
server: Server,
|
10
|
+
test: Test,
|
11
|
+
null: Null,
|
12
|
+
debug: Debug
|
13
|
+
}.freeze
|
14
|
+
end
|
15
|
+
|
16
|
+
def self.for(backend)
|
17
|
+
mapping[backend] or raise(BackendError, "Unable to locate backend: #{backend}")
|
18
|
+
end
|
19
|
+
|
20
|
+
autoload :Base, 'honeybadger/backend/base'
|
21
|
+
autoload :Server, 'honeybadger/backend/server'
|
22
|
+
autoload :Test, 'honeybadger/backend/test'
|
23
|
+
autoload :Null, 'honeybadger/backend/null'
|
24
|
+
autoload :Debug, 'honeybadger/backend/debug'
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
require 'forwardable'
|
2
|
+
require 'net/http'
|
3
|
+
|
4
|
+
require 'honeybadger/logging'
|
5
|
+
|
6
|
+
module Honeybadger
|
7
|
+
module Backend
|
8
|
+
class Response
|
9
|
+
attr_reader :code, :body, :message
|
10
|
+
|
11
|
+
# Public: Initializes the Response instance.
|
12
|
+
#
|
13
|
+
# response - With 1 argument Net::HTTPResponse, the code, body, and
|
14
|
+
# message will be determined automatically. (optional)
|
15
|
+
# code - The Integer status code. May also be :error for requests which
|
16
|
+
# failed to reach the server.
|
17
|
+
# body - The String body of the response.
|
18
|
+
# message - The String message returned by the server (or set by the
|
19
|
+
# backend in the case of an :error code).
|
20
|
+
#
|
21
|
+
# Returns nothing
|
22
|
+
def initialize(*args)
|
23
|
+
if (response = args.first).kind_of?(Net::HTTPResponse)
|
24
|
+
@code, @body, @message = response.code.to_i, response.body.to_s, response.message
|
25
|
+
else
|
26
|
+
@code, @body, @message = args
|
27
|
+
end
|
28
|
+
|
29
|
+
@success = (200..299).cover?(@code)
|
30
|
+
end
|
31
|
+
|
32
|
+
def success?
|
33
|
+
@success
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
class Base
|
38
|
+
extend Forwardable
|
39
|
+
|
40
|
+
include Honeybadger::Logging::Helper
|
41
|
+
|
42
|
+
def initialize(config)
|
43
|
+
@config = config
|
44
|
+
end
|
45
|
+
|
46
|
+
# Internal: Process payload for feature.
|
47
|
+
#
|
48
|
+
# feature - A Symbol feature name (corresponds to HTTP endpoint). Current
|
49
|
+
# options are: :notices, :metrics, :traces.
|
50
|
+
# payload - Any Object responding to #to_json.
|
51
|
+
#
|
52
|
+
# Examples:
|
53
|
+
#
|
54
|
+
# backend.notify(:notices, Notice.new(...))
|
55
|
+
#
|
56
|
+
# Raises NotImplementedError
|
57
|
+
def notify(feature, payload)
|
58
|
+
raise NotImplementedError, 'must define #notify on subclass.'
|
59
|
+
end
|
60
|
+
|
61
|
+
private
|
62
|
+
|
63
|
+
attr_reader :config
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
require 'honeybadger/backend/base'
|
2
|
+
|
3
|
+
module Honeybadger
|
4
|
+
module Backend
|
5
|
+
class Null < Base
|
6
|
+
def initialize(*args)
|
7
|
+
super
|
8
|
+
logger.warn('Initializing development backend: data will not be reported.')
|
9
|
+
end
|
10
|
+
|
11
|
+
def notify(feature, payload)
|
12
|
+
Response.new(201, '{}')
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,51 @@
|
|
1
|
+
require 'net/http'
|
2
|
+
require 'json'
|
3
|
+
require 'zlib'
|
4
|
+
require 'openssl'
|
5
|
+
|
6
|
+
require 'honeybadger/backend/base'
|
7
|
+
require 'honeybadger/util/http'
|
8
|
+
|
9
|
+
module Honeybadger
|
10
|
+
module Backend
|
11
|
+
class Server < Base
|
12
|
+
ENDPOINTS = {
|
13
|
+
ping: '/v1/ping'.freeze,
|
14
|
+
notices: '/v1/notices'.freeze,
|
15
|
+
metrics: '/v1/metrics'.freeze,
|
16
|
+
traces: '/v1/traces'.freeze,
|
17
|
+
deploys: '/v1/deploys'.freeze
|
18
|
+
}.freeze
|
19
|
+
|
20
|
+
HTTP_ERRORS = [Timeout::Error,
|
21
|
+
Errno::EINVAL,
|
22
|
+
Errno::ECONNRESET,
|
23
|
+
EOFError,
|
24
|
+
Net::HTTPBadResponse,
|
25
|
+
Net::HTTPHeaderSyntaxError,
|
26
|
+
Net::ProtocolError,
|
27
|
+
Errno::ECONNREFUSED,
|
28
|
+
SocketError].freeze
|
29
|
+
|
30
|
+
def initialize(config)
|
31
|
+
@http = Util::HTTP.new(config)
|
32
|
+
super
|
33
|
+
end
|
34
|
+
|
35
|
+
# Internal: Post payload to endpoint for feature.
|
36
|
+
#
|
37
|
+
# feature - The feature which is being notified.
|
38
|
+
# payload - The payload to send, responding to `#to_json`.
|
39
|
+
#
|
40
|
+
# Returns Response.
|
41
|
+
def notify(feature, payload)
|
42
|
+
ENDPOINTS[feature] or raise(BackendError, "Unknown feature: #{feature}")
|
43
|
+
Response.new(@http.post(ENDPOINTS[feature], payload))
|
44
|
+
rescue *HTTP_ERRORS => e
|
45
|
+
Response.new(:error, nil, "HTTP Error: #{e.class}").tap do |response|
|
46
|
+
error { sprintf('http error class=%s message=%s', e.class, e.message.dump) }
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
require 'honeybadger/backend/null'
|
2
|
+
|
3
|
+
module Honeybadger
|
4
|
+
module Backend
|
5
|
+
class Test < Null
|
6
|
+
# Public: The notification list.
|
7
|
+
#
|
8
|
+
# Examples:
|
9
|
+
#
|
10
|
+
# backend.notifications[:notices] # => [Notice, Notice, ...]
|
11
|
+
#
|
12
|
+
# Returns the Hash notifications.
|
13
|
+
def notifications
|
14
|
+
@notifications ||= Hash.new([])
|
15
|
+
end
|
16
|
+
|
17
|
+
def notify(feature, payload)
|
18
|
+
notifications[feature] = [] unless notifications.include?(feature)
|
19
|
+
notifications[feature] << payload
|
20
|
+
super
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -1,33 +1,38 @@
|
|
1
|
+
require 'json'
|
2
|
+
|
1
3
|
module Honeybadger
|
2
|
-
#
|
4
|
+
# Internal: Front end to parsing the backtrace for each notice
|
3
5
|
class Backtrace
|
4
|
-
|
5
|
-
# Public: Handles backtrace parsing line by line
|
6
|
+
# Internal: Handles backtrace parsing line by line
|
6
7
|
class Line
|
7
|
-
# regexp (optionally allowing leading X: for windows support)
|
8
|
+
# Backtrace line regexp (optionally allowing leading X: for windows support)
|
8
9
|
INPUT_FORMAT = %r{^((?:[a-zA-Z]:)?[^:]+):(\d+)(?::in `([^']+)')?$}.freeze
|
9
10
|
|
10
|
-
#
|
11
|
+
# The file portion of the line (such as app/models/user.rb)
|
11
12
|
attr_reader :file
|
12
13
|
|
13
|
-
#
|
14
|
+
# The line number portion of the line
|
14
15
|
attr_reader :number
|
15
16
|
|
16
|
-
#
|
17
|
+
# The method of the line (such as index)
|
17
18
|
attr_reader :method
|
18
19
|
|
19
|
-
#
|
20
|
+
# Filtered representations
|
20
21
|
attr_reader :filtered_file, :filtered_number, :filtered_method
|
21
22
|
|
22
|
-
#
|
23
|
+
# Parses a single line of a given backtrace
|
23
24
|
#
|
24
25
|
# unparsed_line - The raw line from +caller+ or some backtrace
|
25
26
|
#
|
26
27
|
# Returns the parsed backtrace line
|
27
28
|
def self.parse(unparsed_line, opts = {})
|
28
29
|
filters = opts[:filters] || []
|
29
|
-
filtered_line = filters.
|
30
|
-
proc.
|
30
|
+
filtered_line = filters.reduce(unparsed_line) do |line, proc|
|
31
|
+
if proc.arity == 2
|
32
|
+
proc.call(line, opts[:config])
|
33
|
+
else
|
34
|
+
proc.call(line)
|
35
|
+
end
|
31
36
|
end
|
32
37
|
|
33
38
|
if filtered_line
|
@@ -49,7 +54,7 @@ module Honeybadger
|
|
49
54
|
self.method = method
|
50
55
|
end
|
51
56
|
|
52
|
-
#
|
57
|
+
# Reconstructs the line in a readable fashion.
|
53
58
|
def to_s
|
54
59
|
"#{filtered_file}:#{filtered_number}:in `#{filtered_method}'"
|
55
60
|
end
|
@@ -62,13 +67,13 @@ module Honeybadger
|
|
62
67
|
"<Line:#{to_s}>"
|
63
68
|
end
|
64
69
|
|
65
|
-
#
|
70
|
+
# Determines if this line is part of the application trace or not.
|
66
71
|
def application?
|
67
72
|
(filtered_file =~ /^\[PROJECT_ROOT\]/i) && !(filtered_file =~ /^\[PROJECT_ROOT\]\/vendor/i)
|
68
73
|
end
|
69
74
|
|
70
|
-
#
|
71
|
-
# performance
|
75
|
+
# An excerpt from the source file, lazily loaded to preserve
|
76
|
+
# performance.
|
72
77
|
def source(radius = 2)
|
73
78
|
@source ||= get_source(file, number, radius)
|
74
79
|
end
|
@@ -77,9 +82,9 @@ module Honeybadger
|
|
77
82
|
|
78
83
|
attr_writer :file, :number, :method, :filtered_file, :filtered_number, :filtered_method
|
79
84
|
|
80
|
-
#
|
85
|
+
# Open source file and read line(s).
|
81
86
|
#
|
82
|
-
# Returns an array of line(s) from source file
|
87
|
+
# Returns an array of line(s) from source file.
|
83
88
|
def get_source(file, number, radius = 2)
|
84
89
|
if file && File.exists?(file)
|
85
90
|
before = after = radius
|
@@ -98,7 +103,7 @@ module Honeybadger
|
|
98
103
|
end
|
99
104
|
end
|
100
105
|
|
101
|
-
#
|
106
|
+
# Holder for an Array of Backtrace::Line instances.
|
102
107
|
attr_reader :lines, :application_lines
|
103
108
|
|
104
109
|
def self.parse(ruby_backtrace, opts = {})
|
@@ -116,24 +121,24 @@ module Honeybadger
|
|
116
121
|
self.application_lines = lines.select(&:application?)
|
117
122
|
end
|
118
123
|
|
119
|
-
#
|
124
|
+
# Convert Backtrace to arry.
|
120
125
|
#
|
121
|
-
# Returns array containing backtrace lines
|
126
|
+
# Returns array containing backtrace lines.
|
122
127
|
def to_ary
|
123
128
|
lines.map { |l| { :number => l.filtered_number, :file => l.filtered_file, :method => l.filtered_method } }
|
124
129
|
end
|
125
130
|
alias :to_a :to_ary
|
126
131
|
|
127
|
-
#
|
132
|
+
# JSON support.
|
128
133
|
#
|
129
|
-
# Returns JSON representation of backtrace
|
134
|
+
# Returns JSON representation of backtrace.
|
130
135
|
def as_json(options = {})
|
131
136
|
to_ary
|
132
137
|
end
|
133
138
|
|
134
|
-
#
|
139
|
+
# Creates JSON.
|
135
140
|
#
|
136
|
-
# Returns valid JSON representation of backtrace
|
141
|
+
# Returns valid JSON representation of backtrace.
|
137
142
|
def to_json(*a)
|
138
143
|
as_json.to_json(*a)
|
139
144
|
end
|