logging-appenders-airbrake 0.0.1 → 0.0.2

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: e929ba30042809af24030e50fced5b64859fc26b
4
- data.tar.gz: 94880fe8ac8fed00c0cffd06b9a46a7c111afe35
3
+ metadata.gz: 97f073a81dd1862e5c006694dbb3504a141f1a62
4
+ data.tar.gz: b208c5332f9065293128d65dfb62357d455525d9
5
5
  SHA512:
6
- metadata.gz: eb14162f105a6cfaaa72388662bf2050b95773c0cd66ae1f4ac4545b37d5cd3272269e7655f401566edca5212f9246a3da07855d128fffb617b289d53f5cfcc6
7
- data.tar.gz: 81da15b60be0f1909fbf6e745d9b8070ae672c54be98c74e89a4baa81373caeb4e3d42183cce95c6c66ff85a5be3c4c6facc5df5d765ac92e164ceb3b19379b7
6
+ metadata.gz: 1f5b049f21615fbf3e913fb845d1a2f4bbd7a04ba4d4f48631797b4e1ed0a96ad1250c03484d04cc5cd65fd89bc8f765b11079de51eb8f07be0bac120f081098
7
+ data.tar.gz: 6ca6d8a69d741182206c717edd31e33aa292f75d9adfe1356b22806d2d487f76359e792c3e89ea0a2909af5a21097aa8cf23a4582dfb3531c639106cddffba51
@@ -0,0 +1,10 @@
1
+ language: ruby
2
+ rvm:
3
+ - 1.9.3
4
+ - jruby-19mode
5
+ - 2.0
6
+ - 2.1
7
+ - 2.2
8
+
9
+ notifications:
10
+ email: false
data/Changes ADDED
@@ -0,0 +1,5 @@
1
+ v0.0.2 2015-03-21
2
+ --------------------
3
+ Bug fixes:
4
+ * Ignore error/fatal calls from the Airbrake sender
5
+ * Under Rails, prevent exceptions caught by the Airbrake middleware from being sent twice
data/README.md CHANGED
@@ -1,6 +1,8 @@
1
1
  # Logging::Appenders::Airbrake
2
2
 
3
- Airbrake appender for [the logging gem](https://github.com/TwP/logging).
3
+ [![Build Status](https://travis-ci.org/sshaw/logging-appenders-airbrake.svg?branch=master)](https://travis-ci.org/sshaw/logging-appenders-airbrake)
4
+
5
+ Airbrake appender for [the Logging gem](https://github.com/TwP/logging).
4
6
 
5
7
  ## Overview
6
8
 
@@ -19,10 +21,10 @@ Airbrake appender for [the logging gem](https://github.com/TwP/logging).
19
21
  end
20
22
 
21
23
  log.add_appenders(Logging.appenders.airbrake)
22
-
24
+
23
25
  log.info "Not sent to airbrake"
24
26
  log.error "Airbrake here I come!"
25
- log.error SomeError.new("See you @ airbrake.io!")
27
+ log.error SomeError.new("See you @ airbrake.io!")
26
28
 
27
29
  ## Description
28
30
 
@@ -34,8 +36,9 @@ to the `airbrake` method:
34
36
 
35
37
  Logging.appenders.airbrake("another_name", options)
36
38
 
37
- Airbrake configuration can be done via `Airbrake.configure` or via `Logging.appenders.airbrake`.
38
- All Airbrake options can be passed to the latter.
39
+ Airbrake configuration can be done via `Airbrake.configure` or via `Logging.appenders.airbrake`.
40
+ All [`Airbrake::Configuration` options](http://www.rubydoc.info/gems/airbrake/Airbrake/Configuration) can be passed
41
+ to the latter.
39
42
 
40
43
  ## Using With `logging-rails`
41
44
 
@@ -1,5 +1,5 @@
1
1
  require "airbrake"
2
- require "logging/appender"
2
+ require "logging"
3
3
 
4
4
  module Logging::Appenders
5
5
  def self.airbrake(*args)
@@ -11,53 +11,59 @@ module Logging::Appenders
11
11
  end
12
12
 
13
13
  class Airbrake < Logging::Appender
14
- FILTER = lambda do |line|
14
+ VERSION = "0.0.2"
15
+
16
+ # Ignore errors logged by an Airbrake sender
17
+ INTERNAL_BT_FILTER = %r{:in\s+`send_to_airbrake'}.freeze
18
+
19
+ # Remove calls to this class in the stacktrace sent to Airbrake
20
+ AIRBRAKE_BT_FILTER = lambda do |line|
15
21
  line =~ %r{/logging-[^/]+/lib/logging/} ? nil : line
16
22
  end
17
23
 
18
- attr :options
19
-
20
24
  def initialize(*args)
21
- args.compact!
22
-
23
- name = args.first.is_a?(String) ? args.shift : "airbrake"
24
- super(name, :level => :error)
25
-
26
25
  cfg = ::Airbrake.configuration
27
26
  cfg.framework = "Logging #{Logging.version}"
28
27
 
29
- @options = args.shift || {}
30
- @options[:backtrace_filters] ||= []
31
- @options[:backtrace_filters] << FILTER
28
+ appender = { :level => :error }
29
+
30
+ args.compact!
31
+ name = args.first.is_a?(String) ? args.shift : "airbrake"
32
+ airbrake = args.last.is_a?(Hash) ? args.pop : {}
32
33
 
33
- @options.each do |k,v|
34
- unless ::Airbrake::Configuration::OPTIONS.include?(k)
35
- raise ArgumentError, "unknown Airbrake configuration option #{k}"
34
+ airbrake[:backtrace_filters] ||= []
35
+ airbrake[:backtrace_filters] << AIRBRAKE_BT_FILTER
36
+
37
+ airbrake.keys.each do |name|
38
+ unless ::Airbrake::Configuration::OPTIONS.include?(name)
39
+ appender[name] = airbrake.delete(name)
40
+ next
36
41
  end
37
42
 
38
43
  # Airbrake array attributes have no setter
39
- if cfg[k].is_a?(Array)
40
- cfg[k].concat(Array(v))
44
+ if cfg[name].is_a?(Array)
45
+ cfg[name].concat(Array(airbrake[name]))
41
46
  else
42
- cfg.method("#{k}=")[v]
47
+ cfg.public_send("#{name}=", airbrake[name])
43
48
  end
44
49
  end
50
+
51
+ super(name, appender)
45
52
  end
46
53
 
47
54
  private
48
55
 
49
56
  def write(event)
50
- if ::Airbrake.configuration.configured?
51
- # Docs say event can be a String too, not sure when/how but we'll check anyways
52
- error = event.is_a?(Logging::LogEvent) ? event.data : event
53
- error = { :error_message => error } if error.is_a?(String)
54
-
55
- ::Airbrake.notify_or_ignore(error)
56
- else
57
- # TODO: better to just set Airbrake's logger to something so it can log this?
58
- Logging.log_internal { 'Not logging #{event.inspect}: Airbrake is not configured' }
59
- end
57
+ return self if caller.any? { |bt| bt =~ INTERNAL_BT_FILTER }
58
+
59
+ # Docs say event can be a String too, not sure when/how but we'll check anyways
60
+ error = event.is_a?(Logging::LogEvent) ? event.data : event
61
+ error = { :error_message => error } if error.is_a?(String)
62
+
63
+ ::Airbrake.notify_or_ignore(error)
60
64
  self
61
65
  end
62
66
  end
63
67
  end
68
+
69
+ require "logging/appenders/airbrake/railtie" if defined?(Rails::Railtie)
@@ -0,0 +1,26 @@
1
+ require "rails"
2
+ require "logging/appenders/airbrake"
3
+
4
+ module Logging
5
+ module Appenders
6
+ class Airbrake
7
+ class Railtie < ::Rails::Railtie
8
+ config.after_initialize do |app|
9
+ next unless defined?(::Airbrake::Rails::Middleware) && app.middleware.include?(::Airbrake::Rails::Middleware)
10
+
11
+ log = app.env_config["action_dispatch.logger"]
12
+ next unless log.is_a?(Logging::Logger)
13
+
14
+ # After sending an exception to Airbrake its middleware passes the exception (`raise`es) it up
15
+ # the stack. Rails' middleware (DebugException, ShowExceptions) ends up logging these as fatal,
16
+ # which triggers the Airbrake appender. To avoid sending the exception twice we remove the appender.
17
+ log.appenders = Logging.logger.root.appenders if log.appenders.none?
18
+ log.appenders = log.appenders.reject { |a| a.is_a?(Logging::Appenders::Airbrake) }
19
+ log.additive = false
20
+
21
+ app.env_config["action_dispatch.logger"] = log
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
@@ -4,11 +4,11 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
4
 
5
5
  Gem::Specification.new do |spec|
6
6
  spec.name = "logging-appenders-airbrake"
7
- spec.version = "0.0.1"
7
+ spec.version = "0.0.2"
8
8
  spec.authors = ["Skye Shaw"]
9
9
  spec.email = ["skye.shaw@gmail.com"]
10
- spec.summary = %q{Airbrake appender for the logging gem}
11
- spec.description = %q{An appender for the logging gem that will send all messages logged at the :error level to Airbrake}
10
+ spec.summary = %q{Airbrake appender for the Logging gem}
11
+ spec.description = %q{An appender for the Logging gem that sends all messages logged at the :error level to Airbrake}
12
12
  spec.homepage = "https://github.com/sshaw/logging-appenders-airbrake"
13
13
  spec.license = "MIT"
14
14
 
@@ -16,6 +16,7 @@ Gem::Specification.new do |spec|
16
16
  spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
17
17
  spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
18
18
  spec.require_paths = ["lib"]
19
+ spec.required_ruby_version = "> 1.8.7"
19
20
 
20
21
  spec.add_dependency "airbrake"
21
22
  spec.add_dependency "logging"
@@ -5,7 +5,20 @@ require "minitest/mock"
5
5
  require "logging"
6
6
  require "logging/appenders/airbrake"
7
7
 
8
+ class FailingSender < Airbrake::Sender
9
+ def send_to_airbrake(notice)
10
+ logger.error("error!")
11
+ logger.fatal("fatal!")
12
+ end
13
+ end
14
+
8
15
  class TestAirbrake < MiniTest::Unit::TestCase
16
+ CFG = Airbrake.configuration
17
+
18
+ def setup
19
+ Airbrake.configuration = CFG
20
+ end
21
+
9
22
  def test_configuration_without_appender_name
10
23
  app = appender(config)
11
24
 
@@ -32,16 +45,12 @@ class TestAirbrake < MiniTest::Unit::TestCase
32
45
  end
33
46
  end
34
47
 
35
- def test_invalid_configuration
36
- assert_raises(ArgumentError, /unknown/) { appender(:ass => "bass") }
37
- end
38
-
39
48
  def test_only_error_level_logged
40
49
  count = 0
41
50
  app = appender
42
51
  app.define_singleton_method(:write) { |e| count += 1 }
43
52
 
44
- log = Logging.logger[self]
53
+ log = Logging.logger[__method__]
45
54
  log.add_appenders(app)
46
55
 
47
56
  log.info("Hi")
@@ -53,6 +62,18 @@ class TestAirbrake < MiniTest::Unit::TestCase
53
62
  assert_equal 2, count
54
63
  end
55
64
 
65
+ def test_errors_from_airbrake_sender_ignored
66
+ log = Logging.logger[__method__]
67
+ log.add_appenders(appender)
68
+
69
+ Airbrake.configuration.logger = log
70
+ Airbrake.sender = FailingSender.new
71
+
72
+ log.info("info")
73
+ # If the test fails this will trigger a SystemStackError
74
+ log.error("some error")
75
+ end
76
+
56
77
  private
57
78
  def config
58
79
  @config ||= {
@@ -62,6 +83,7 @@ class TestAirbrake < MiniTest::Unit::TestCase
62
83
  }
63
84
  end
64
85
 
86
+ # With this the appender is created only once unless there's a name
65
87
  def appender(*args)
66
88
  args << { :api_key => "X123" } unless args.last.is_a?(Hash)
67
89
  Logging.appenders.airbrake(*args)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: logging-appenders-airbrake
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.0.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Skye Shaw
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-10-09 00:00:00.000000000 Z
11
+ date: 2015-03-21 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: airbrake
@@ -66,8 +66,8 @@ dependencies:
66
66
  - - ">="
67
67
  - !ruby/object:Gem::Version
68
68
  version: '0'
69
- description: An appender for the logging gem that will send all messages logged at
70
- the :error level to Airbrake
69
+ description: An appender for the Logging gem that sends all messages logged at the
70
+ :error level to Airbrake
71
71
  email:
72
72
  - skye.shaw@gmail.com
73
73
  executables: []
@@ -75,10 +75,13 @@ extensions: []
75
75
  extra_rdoc_files: []
76
76
  files:
77
77
  - ".gitignore"
78
+ - ".travis.yml"
79
+ - Changes
78
80
  - Gemfile
79
81
  - README.md
80
82
  - Rakefile
81
83
  - lib/logging/appenders/airbrake.rb
84
+ - lib/logging/appenders/airbrake/railtie.rb
82
85
  - logging-appenders-airbrake.gemspec
83
86
  - test/test_airbrake.rb
84
87
  homepage: https://github.com/sshaw/logging-appenders-airbrake
@@ -91,9 +94,9 @@ require_paths:
91
94
  - lib
92
95
  required_ruby_version: !ruby/object:Gem::Requirement
93
96
  requirements:
94
- - - ">="
97
+ - - ">"
95
98
  - !ruby/object:Gem::Version
96
- version: '0'
99
+ version: 1.8.7
97
100
  required_rubygems_version: !ruby/object:Gem::Requirement
98
101
  requirements:
99
102
  - - ">="
@@ -101,9 +104,9 @@ required_rubygems_version: !ruby/object:Gem::Requirement
101
104
  version: '0'
102
105
  requirements: []
103
106
  rubyforge_project:
104
- rubygems_version: 2.2.2
107
+ rubygems_version: 2.4.5
105
108
  signing_key:
106
109
  specification_version: 4
107
- summary: Airbrake appender for the logging gem
110
+ summary: Airbrake appender for the Logging gem
108
111
  test_files:
109
112
  - test/test_airbrake.rb