amqp_logging 0.4.0 → 0.5.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.
@@ -1,24 +1,19 @@
1
1
  =AMQPLogging
2
2
 
3
-
4
- A ruby logger class that logs to an {AMQP}[http://www.amqp.org/] exchange in addition to your default log device.
3
+ A ruby logger class that logs to an {AMQP}[http://www.amqp.org/] exchange
5
4
 
6
5
  ==Basic Configuration
7
6
  By default the logs are routed to the host, exchange and key specified in DEFAULT_OPTIONS.
8
7
  You can change the configuration when creating the logger object by specifying an argument hash:
9
8
 
10
- require 'amqp_logging'
11
-
12
- logging_config = { :routing_key => "applogging",
13
- :host => AppConfig.amqp_logging.host,
14
- :exchange => AppConfig.amqp_logging.exchange }
9
+ require 'amqp_logging'
15
10
 
16
- logger = AMQPLogging::Logger.new(config.log_path, logging_config)
17
- config.logger = logger
18
-
19
- With Rails 3 you will need to modify this a bit, as config.log_path no longer has the desired effect:
11
+ logging_config = { :routing_key => "applogging",
12
+ :host => AppConfig.amqp_logging.host,
13
+ :exchange => AppConfig.amqp_logging.exchange }
20
14
 
21
- config.logger = AMQPLogging::Logger.new(config.paths.log.to_a.first, logging_config)
15
+ logger = AMQPLogging::Logger.new(logging_config)
16
+ config.logger = logger
22
17
 
23
18
  ==Routing Keys
24
19
 
@@ -27,18 +22,23 @@ receives the logline as the first argument and returns the routing key.
27
22
 
28
23
  Example:
29
24
 
30
- # You can use a lambda or whatever responds to #call as the routing key generator
31
- AMQPRoutingKeyGenerator = lambda do |logline|
32
- if logline =~ /(?:engine\[([^\]]*)\])\: (Completed in|Processing|Session ID)?/
33
- key = "logs.app.#{$1}"
34
- key << ".statistics" unless $2.nil?
35
- else
36
- key = "logs.app.system"
37
- end
38
- key
39
- end
40
-
41
- AMQPLogging::Logger.new($stdout, :routing_key => AMQPRoutingKeyGenerator)
25
+ # You can use a lambda or whatever responds to #call as the routing key generator
26
+ AMQPRoutingKeyGenerator = lambda do |logline|
27
+ if logline =~ /(?:engine\[([^\]]*)\])\: (Completed in|Processing|Session ID)?/
28
+ key = "logs.app.#{$1}"
29
+ key << ".statistics" unless $2.nil?
30
+ else
31
+ key = "logs.app.system"
32
+ end
33
+ key
34
+ end
35
+
36
+ AMQPLogging::Logger.new($stdout, :routing_key => AMQPRoutingKeyGenerator)
37
+
38
+ ==Fallback to disk
39
+
40
+ The support for a fallback logdevice was removed with version 0.5.0. A multi logger thatallows
41
+ you get the same behaviour will follow soonish.
42
42
 
43
43
  ==License
44
44
 
@@ -1,99 +1,17 @@
1
1
  require 'bunny'
2
2
 
3
3
  begin
4
- require 'active_support/time' # ActiveSupport 3.x
4
+ # ActiveSupport 3.x
5
+ require 'active_support/time'
6
+ require 'active_support/core_ext/hash/slice'
5
7
  rescue LoadError
6
8
  require 'active_support' # ActiveSupport 2.x
7
9
  end
8
10
 
9
11
  module AMQPLogging
10
-
11
- DEFAULT_OPTIONS = {
12
- :shift_age => 0,
13
- :shift_size => 1048576,
14
- :host => "localhost",
15
- :exchange => "logging_exchange",
16
- :queue => "logging_queue",
17
- :routing_key => "logs"
18
- }
19
-
20
- RETRY_AFTER = 10.seconds
21
-
22
- class Logger < ::Logger
23
- attr_accessor :extra_attributes
24
- attr_accessor :errback
25
-
26
- def initialize(logdev, *args)
27
- options = args.first.is_a?(Hash) ? DEFAULT_OPTIONS.merge(args.first) : DEFAULT_OPTIONS
28
- super(logdev, options[:shift_age], options[:shift_size])
29
- @logdev = AMQPLogDevice.new(@logdev, options)
30
- @logdev.logger = self
31
- end
32
- end
33
-
34
- class AMQPLogDevice
35
- attr_reader :exchange, :configuration
36
- attr_accessor :logger
37
-
38
- def initialize(dev, opts = {})
39
- @configuration = opts
40
- @fallback_logdev = dev
41
- end
42
-
43
- def write(msg)
44
- begin
45
- if !@paused || @paused <= RETRY_AFTER.ago
46
- routing_key = configuration[:routing_key].respond_to?(:call) ? configuration[:routing_key].call(msg).to_s : configuration[:routing_key]
47
- exchange.publish(msg, :key => routing_key)
48
- end
49
- rescue Exception => exception
50
- reraise_expectation_errors!
51
- pause_amqp_logging(exception)
52
- ensure
53
- @fallback_logdev.write(msg)
54
- end
55
- end
56
-
57
- def close
58
- @fallback_logdev.close
59
- end
60
-
61
- private
62
- def pause_amqp_logging(exception)
63
- @paused = Time.now
64
- reset_amqp
65
- logger.errback.call(exception) if logger.errback && logger.errback.respond_to?(:call)
66
- end
67
-
68
- def reset_amqp
69
- begin
70
- bunny.stop if bunny.connected?
71
- rescue
72
- # if bunny throws an exception here, its not usable anymore anyway
73
- ensure
74
- @exchange = @bunny = nil
75
- end
76
- end
77
-
78
- def exchange
79
- bunny.start unless bunny.connected?
80
- @exchange ||= bunny.exchange(configuration[:exchange], :type => :topic)
81
- end
82
-
83
- def bunny
84
- @bunny ||= Bunny.new(:host => configuration[:host])
85
- @bunny
86
- end
87
-
88
- if defined?(Mocha)
89
- def reraise_expectation_errors! #:nodoc:
90
- raise if $!.is_a?(Mocha::ExpectationError)
91
- end
92
- else
93
- def reraise_expectation_errors! #:nodoc:
94
- # noop
95
- end
96
- end
97
- end
12
+ autoload :MetricsAgent, 'amqp_logging/metrics_agent'
98
13
  end
99
14
 
15
+ require 'logger'
16
+ require 'amqp_logging/logger'
17
+ require 'amqp_logging/log_device'
@@ -0,0 +1,65 @@
1
+ class AMQPLogging::LogDevice
2
+ RETRY_AFTER = 10.seconds
3
+
4
+ attr_reader :exchange, :configuration
5
+ attr_accessor :logger
6
+
7
+ def initialize(opts = {})
8
+ @configuration = opts
9
+ end
10
+
11
+ def write(msg)
12
+ begin
13
+ if !@paused || @paused <= RETRY_AFTER.ago
14
+ routing_key = configuration[:routing_key].respond_to?(:call) ? configuration[:routing_key].call(msg).to_s : configuration[:routing_key]
15
+ exchange.publish(msg, :key => routing_key)
16
+ end
17
+ rescue Exception => exception
18
+ reraise_expectation_errors!
19
+ pause_amqp_logging(exception)
20
+ end
21
+ end
22
+
23
+ def close
24
+ reset_amqp # TODO: Test!
25
+ end
26
+
27
+ private
28
+ def pause_amqp_logging(exception)
29
+ @paused = Time.now
30
+ reset_amqp
31
+ logger.errback.call(exception) if logger.errback && logger.errback.respond_to?(:call)
32
+ end
33
+
34
+ def reset_amqp
35
+ begin
36
+ bunny.stop if bunny.connected?
37
+ rescue
38
+ # if bunny throws an exception here, its not usable anymore anyway
39
+ ensure
40
+ @exchange = @bunny = nil
41
+ end
42
+ end
43
+
44
+ def exchange
45
+ bunny.start unless bunny.connected?
46
+ @exchange ||= bunny.exchange(configuration[:exchange], :durable => configuration[:exchange_durable],
47
+ :auto_delete => configuration[:exchange_auto_delete],
48
+ :type => configuration[:exchange_type])
49
+ end
50
+
51
+ def bunny
52
+ @bunny ||= Bunny.new(configuration.slice(:host, :port, :user, :pass))
53
+ @bunny
54
+ end
55
+
56
+ if defined?(Mocha)
57
+ def reraise_expectation_errors! #:nodoc:
58
+ raise if $!.is_a?(Mocha::ExpectationError)
59
+ end
60
+ else
61
+ def reraise_expectation_errors! #:nodoc:
62
+ # noop
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,23 @@
1
+ class AMQPLogging::Logger < ::Logger
2
+ DEFAULT_OPTIONS = {
3
+ :shift_age => 0,
4
+ :shift_size => 1048576,
5
+ :host => "localhost",
6
+ :exchange => "logging_exchange",
7
+ :queue => "logging_queue",
8
+ :routing_key => "logs",
9
+ :exchange_durable => true,
10
+ :exchange_auto_delete => false,
11
+ :exchange_type => :topic,
12
+ }
13
+
14
+ attr_accessor :extra_attributes
15
+ attr_accessor :errback
16
+
17
+ def initialize(options=DEFAULT_OPTIONS)
18
+ options = DEFAULT_OPTIONS.merge(options)
19
+ super(nil)
20
+ @logdev = AMQPLogging::LogDevice.new(options)
21
+ @logdev.logger = self
22
+ end
23
+ end
@@ -0,0 +1,91 @@
1
+ require 'json'
2
+
3
+
4
+ module AMQPLogging
5
+ class MetricsAgent
6
+ attr_reader :fields
7
+
8
+ def initialize
9
+ @default_fields = {
10
+ :host => Socket.gethostname.split('.').first,
11
+ :pid => Process.pid,
12
+ :loglines => {
13
+ :default => []
14
+ }
15
+ }
16
+ @logger_types = {}
17
+ reset_fields
18
+ end
19
+
20
+ def logger
21
+ @logger || (self.logger = ::Logger.new($stdout))
22
+ end
23
+
24
+ def logger=(logger)
25
+ @logger = logger
26
+ @logger.formatter = Proc.new {|_, _, msg, progname| msg || progname}
27
+ @logger
28
+ end
29
+
30
+ def flush
31
+ logger.info(@fields.to_json + "\n")
32
+ reset_fields
33
+ end
34
+
35
+ def [](fieldname)
36
+ @fields[fieldname]
37
+ end
38
+
39
+ def []=(fieldname, value)
40
+ @fields[fieldname] = value
41
+ end
42
+
43
+ def add_logline(severity, message, progname, logger)
44
+ t = Time.now
45
+ msg = (message || progname).strip
46
+ @fields[:loglines][@logger_types[logger]] << [severity, t.strftime("%Y-%d-%mT%H:%M:%S.#{t.usec}"), msg]
47
+ end
48
+
49
+ def wrap_logger(logger, type = :default)
50
+ agent = self
51
+ register_logger(logger, type)
52
+ logger.instance_eval do
53
+ @agent = agent
54
+ class << self
55
+ include MetricsAgentSupport
56
+ end
57
+ end
58
+ logger
59
+ end
60
+
61
+ private
62
+ def register_logger(logger, type)
63
+ @logger_types[logger] = type
64
+ @fields[:loglines][type] = []
65
+ end
66
+
67
+ def reset_fields
68
+ @fields = {
69
+ }.merge!(@default_fields)
70
+ @logger_types.values.each {|logtype| @fields[:loglines][logtype] = []}
71
+ end
72
+
73
+ module MetricsAgentSupport
74
+ def self.included(base)
75
+ base.class_eval do
76
+ alias :add_without_proxy :add
77
+ alias :add :add_with_proxy
78
+ end
79
+ end
80
+
81
+ def agent
82
+ @agent
83
+ end
84
+
85
+ def add_with_proxy(severity, message = nil, progname = nil)
86
+ @agent.add_logline(severity, message, progname, self) unless severity < @level
87
+ add_without_proxy(severity, message, progname)
88
+ end
89
+ end
90
+ end
91
+ end
@@ -0,0 +1,16 @@
1
+ require 'amqp_logging'
2
+ require 'amqp_logging/metrics_agent/rails/after_dispatch_callback_handler'
3
+
4
+ ActionController::Dispatcher.after_dispatch do |dispatcher|
5
+ AMQPLogging::Rails::AfterDispatchCallbackHandler.run(dispatcher)
6
+ end
7
+
8
+ class ActionController::Base
9
+ def log_processing_for_request_id_with_metrics_agent
10
+ logger.agent[:page] = "#{self.class.name}\##{action_name}"
11
+ t = Time.now
12
+ logger.agent[:started_at] = t.strftime("%Y-%d-%mT%H:%M:%S.#{t.usec}")
13
+ log_processing_for_request_id_without_metrics_agent
14
+ end
15
+ alias_method_chain :log_processing_for_request_id, :metrics_agent
16
+ end
@@ -0,0 +1,28 @@
1
+ module AMQPLogging
2
+ module Rails
3
+ class AfterDispatchCallbackHandler
4
+ def self.run(dispatcher)
5
+ env = dispatcher.instance_variable_get(:@env)
6
+ response = env["action_controller.rescue.response"]
7
+ request = env["action_controller.rescue.request"]
8
+ request_headers = request.headers.dup
9
+ request_headers.each do |k, v|
10
+ case v
11
+ when String, Fixnum, Numeric
12
+ else
13
+ request_headers[k] = "#<#{v.class.name}>"
14
+ end
15
+ end
16
+ agent = ActionController::Base.logger.agent
17
+ agent.fields.merge!({
18
+ :env => RAILS_ENV,
19
+ :response_code => response.status,
20
+ :request_params => request.request_parameters,
21
+ :request_headers => request_headers,
22
+ :response_headers => response.headers
23
+ })
24
+ agent.flush
25
+ end
26
+ end
27
+ end
28
+ end
@@ -6,34 +6,21 @@ class TheAMQPLoggerTest < Test::Unit::TestCase
6
6
  @io = StringIO.new
7
7
  end
8
8
 
9
- test "should be instanciated like a normal logger" do
10
- assert_nothing_raised { AMQPLogging::Logger.new(@io) }
11
- assert_nothing_raised { AMQPLogging::Logger.new(@io, 2) }
12
- assert_nothing_raised { AMQPLogging::Logger.new(@io, 2, 1048576) }
13
- end
14
-
15
9
  test "should be instanciated with an amqp configuration hash" do
16
- config = { :queue => "testqueue", :exchange => "testexchange", :host => "testhost", :shift_age => 4, :shift_size => 1338, :routing_key => "foobar" }
17
- AMQPLogging::AMQPLogDevice.expects(:new).with(anything, config).returns(stub_everything)
18
-
19
- logger = AMQPLogging::Logger.new(@io, config)
20
- end
10
+ config = { :queue => "testqueue", :exchange => "testexchange", :host => "testhost", :shift_age => 4, :shift_size => 1338, :routing_key => "foobar", :exchange_durable => true, :exchange_auto_delete => false, :exchange_type => :topic }
11
+ AMQPLogging::LogDevice.expects(:new).with(config).returns(stub_everything)
21
12
 
22
- test "should write to the default io" do
23
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:exchange).returns(stub_everything('test_exchange'))
24
- logger = AMQPLogging::Logger.new(@io)
25
- logger.debug "logging something"
26
- assert_match "logging something", @io.string
13
+ logger = AMQPLogging::Logger.new(config)
27
14
  end
28
15
 
29
16
  test "should pause AMQP logging if exceptions during logging occure" do
30
17
  # in case you ask why not just using mocha expectations here: the rescue in the tested code also rescues the mocha exception
31
18
  # this fake exchange object increases a counter everytime publish is executed so we can check the number of executions
32
19
  class TestExchange; attr_reader :counter; def publish(*args); @counter ||= 0; @counter += 1; raise 'Foo'; end; end
33
- logger = AMQPLogging::Logger.new(@io)
20
+ logger = AMQPLogging::Logger.new
34
21
  exchange = TestExchange.new
35
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:exchange).returns(exchange)
36
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:bunny).returns(stub_everything("bunny stub"))
22
+ AMQPLogging::LogDevice.any_instance.stubs(:exchange).returns(exchange)
23
+ AMQPLogging::LogDevice.any_instance.stubs(:bunny).returns(stub_everything("bunny stub"))
37
24
  2.times { logger.debug "This will raise" }
38
25
 
39
26
  assert_equal 1, exchange.counter
@@ -46,8 +33,8 @@ class TheAMQPLoggerTest < Test::Unit::TestCase
46
33
  errback = lambda {|exception| begin raise exception; rescue FooBarException; @called = true; end}
47
34
  raising_exchange = mock("mocked exchange")
48
35
  raising_exchange.expects(:publish).raises(FooBarException)
49
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:exchange).returns(raising_exchange)
50
- logger = AMQPLogging::Logger.new(@io)
36
+ AMQPLogging::LogDevice.any_instance.stubs(:exchange).returns(raising_exchange)
37
+ logger = AMQPLogging::Logger.new
51
38
  logger.errback = errback
52
39
 
53
40
  assert_nothing_raised do
@@ -59,10 +46,10 @@ class TheAMQPLoggerTest < Test::Unit::TestCase
59
46
  test "should reset the bunny and exchange instance if a exception occures" do
60
47
  raising_exchange = mock("mocked exchange")
61
48
  raising_exchange.expects(:publish).raises("FFFFFFFFUUUUUUUUUU")
62
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:exchange).returns(raising_exchange)
63
- logger = AMQPLogging::Logger.new(@io)
49
+ AMQPLogging::LogDevice.any_instance.stubs(:exchange).returns(raising_exchange)
50
+ logger = AMQPLogging::Logger.new
64
51
 
65
- AMQPLogging::AMQPLogDevice.any_instance.expects(:reset_amqp)
52
+ AMQPLogging::LogDevice.any_instance.expects(:reset_amqp)
66
53
  logger.debug("This will raise and send a notification")
67
54
  end
68
55
 
@@ -73,9 +60,11 @@ class TheLogDeviceTest < Test::Unit::TestCase
73
60
  config = { :queue => "testqueue", :exchange => "testexchange", :host => "testhost", :shift_age => 4, :shift_size => 1338 }
74
61
  bunny_stub = stub_everything("bunny_stub")
75
62
  Bunny.expects(:new).with(:host => "testhost").returns(bunny_stub)
76
- bunny_stub.expects(:exchange).with(config[:exchange], :type => :topic).returns(stub("exchange stub", :publish => true))
63
+ bunny_stub.expects(:exchange).with(config[:exchange], :durable => true,
64
+ :auto_delete => false,
65
+ :type => :topic).returns(stub("exchange stub", :publish => true))
77
66
 
78
- logger = AMQPLogging::Logger.new(StringIO.new, config)
67
+ logger = AMQPLogging::Logger.new(config)
79
68
  logger.debug("foobar")
80
69
  end
81
70
 
@@ -83,16 +72,16 @@ class TheLogDeviceTest < Test::Unit::TestCase
83
72
  message = "some stuff to log"
84
73
  exchange = mock()
85
74
  exchange.expects(:publish).with(anything, :key => "a_routing_key")
86
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:exchange).returns(exchange)
87
- AMQPLogging::Logger.new(StringIO.new, {:routing_key => "a_routing_key"}).debug(message)
75
+ AMQPLogging::LogDevice.any_instance.stubs(:exchange).returns(exchange)
76
+ AMQPLogging::Logger.new(:routing_key => "a_routing_key").debug(message)
88
77
  end
89
78
 
90
79
  test "should take a proc argument which gets the logline passed to generate the routing key" do
91
80
  key_generator = lambda {|msg| !!(msg =~ /a message/) }
92
81
  exchange = mock()
93
82
  exchange.expects(:publish).with(anything, :key => "true")
94
- AMQPLogging::AMQPLogDevice.any_instance.stubs(:exchange).returns(exchange)
95
- AMQPLogging::Logger.new(StringIO.new, {:routing_key => key_generator}).debug("a message")
83
+ AMQPLogging::LogDevice.any_instance.stubs(:exchange).returns(exchange)
84
+ AMQPLogging::Logger.new(:routing_key => key_generator).debug("a message")
96
85
  end
97
86
  end
98
87
 
@@ -0,0 +1,108 @@
1
+ require File.dirname(__FILE__) + '/test_helper.rb'
2
+
3
+
4
+ module AMQPLogging
5
+ class MetricsAgentTest < Test::Unit::TestCase
6
+ def setup
7
+ @agent = MetricsAgent.new
8
+ @out = StringIO.new
9
+ @agent.logger = ::Logger.new(@out)
10
+ end
11
+
12
+ test "should record the process id" do
13
+ assert_equal Process.pid, @agent[:pid]
14
+ end
15
+
16
+ test "should record the hostname" do
17
+ assert_equal Socket.gethostname.split('.').first, @agent[:host]
18
+ end
19
+
20
+ test "should have convenience methods for accessing the fields" do
21
+ @agent[:foo] = :bar
22
+ assert_equal :bar, @agent[:foo]
23
+ assert_equal @agent[:foo], @agent[:foo]
24
+ end
25
+
26
+ test "should send the collected data as json when flushed" do
27
+ @agent.flush
28
+ json = JSON.parse(@out.string)
29
+ assert_equal Process.pid, json["pid"]
30
+ end
31
+
32
+ test "should reset the collected data when flushed" do
33
+ @agent[:foo] = :bar
34
+ @agent.flush
35
+ assert_equal nil, @agent[:foo]
36
+ end
37
+ end
38
+
39
+ class LoggingProxyTest < Test::Unit::TestCase
40
+ def setup
41
+ @agent = MetricsAgent.new
42
+ @agent.logger = ::Logger.new('/dev/null')
43
+ @logger = ::Logger.new('/dev/null')
44
+ @proxy = @agent.wrap_logger(@logger)
45
+ end
46
+
47
+ test "should return a logger proxy that quaks like a regular logger" do
48
+ @logger.expects(:debug)
49
+ @proxy.debug "foobar"
50
+ end
51
+
52
+ test "should register every logline on the agent" do
53
+ @agent.expects(:add_logline).with(0, nil, "foobar", @logger)
54
+ @proxy.debug("foobar")
55
+ end
56
+
57
+ test "should take the loglevel of the logger into account" do
58
+ @logger.level = ::Logger::INFO
59
+ no_lines_before_logging = @agent[:loglines][:default].size
60
+ @logger.debug "something"
61
+ assert_equal no_lines_before_logging, @agent[:loglines][:default].size
62
+ end
63
+
64
+ test "should store the loglines" do
65
+ assert_equal 0, @agent[:loglines][:default].size
66
+ @proxy.debug("foobar")
67
+ assert_equal 1, @agent[:loglines][:default].size
68
+ end
69
+
70
+ test "should store each logline with severity, a timestamp and the message" do
71
+ some_logline = "asdf0asdf"
72
+ @proxy.debug "foo"
73
+ @proxy.warn "bar"
74
+ @proxy.info some_logline
75
+ severity, timestamp, message = @agent[:loglines][:default][2]
76
+ assert_equal Logger::INFO, severity
77
+ assert_nothing_raised { Time.parse(timestamp) }
78
+ assert_equal some_logline, message
79
+ end
80
+
81
+ test "should allow to register multiple loggers with different types" do
82
+ other_logger = ::Logger.new('/dev/null')
83
+ @agent.wrap_logger(other_logger, :sql)
84
+ other_logger.info("some fancy stuff here")
85
+ assert_equal 1, @agent[:loglines][:sql].size
86
+ end
87
+
88
+ test "should reset the collected loglines when flushed" do
89
+ @proxy.debug "foo"
90
+ @agent.flush
91
+ assert_equal [], @agent[:loglines][:default]
92
+ end
93
+
94
+ test "should keep loglines fields for the registered loggers after flushing" do
95
+ other_logger = ::Logger.new('/dev/null')
96
+ @agent.wrap_logger(other_logger, :sql)
97
+ other_logger.info "foo"
98
+ @agent.flush
99
+
100
+ assert_equal [], @agent[:loglines][:sql]
101
+ end
102
+
103
+ test "should remove leading and trailing newlines from the stored loglines" do
104
+ @proxy.debug "\n\nfoo\n\n"
105
+ assert_equal "foo", @agent[:loglines][:default][-1][2]
106
+ end
107
+ end
108
+ end
@@ -1,3 +1,4 @@
1
+ $:.unshift(File.expand_path('../../lib', __FILE__))
1
2
  require 'rubygems'
2
3
  require 'test/unit'
3
4
  require 'mocha'
@@ -13,3 +14,5 @@ end
13
14
  class Test::Unit::TestCase
14
15
  extend ActiveSupport::Testing::Declarative
15
16
  end
17
+
18
+ require 'amqp_logging'
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: amqp_logging
3
3
  version: !ruby/object:Gem::Version
4
- hash: 15
4
+ hash: 11
5
5
  prerelease: false
6
6
  segments:
7
7
  - 0
8
- - 4
8
+ - 5
9
9
  - 0
10
- version: 0.4.0
10
+ version: 0.5.0
11
11
  platform: ruby
12
12
  authors:
13
13
  - Pascal Friederich
@@ -51,9 +51,25 @@ dependencies:
51
51
  type: :runtime
52
52
  version_requirements: *id002
53
53
  - !ruby/object:Gem::Dependency
54
- name: mocha
54
+ name: json
55
55
  prerelease: false
56
56
  requirement: &id003 !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ hash: 7
62
+ segments:
63
+ - 1
64
+ - 4
65
+ - 0
66
+ version: 1.4.0
67
+ type: :runtime
68
+ version_requirements: *id003
69
+ - !ruby/object:Gem::Dependency
70
+ name: mocha
71
+ prerelease: false
72
+ requirement: &id004 !ruby/object:Gem::Requirement
57
73
  none: false
58
74
  requirements:
59
75
  - - ">="
@@ -63,7 +79,21 @@ dependencies:
63
79
  - 0
64
80
  version: "0"
65
81
  type: :development
66
- version_requirements: *id003
82
+ version_requirements: *id004
83
+ - !ruby/object:Gem::Dependency
84
+ name: redgreen
85
+ prerelease: false
86
+ requirement: &id005 !ruby/object:Gem::Requirement
87
+ none: false
88
+ requirements:
89
+ - - ">="
90
+ - !ruby/object:Gem::Version
91
+ hash: 3
92
+ segments:
93
+ - 0
94
+ version: "0"
95
+ type: :development
96
+ version_requirements: *id005
67
97
  description:
68
98
  email:
69
99
  - pascal.friederich@xing.com
@@ -74,9 +104,15 @@ extensions: []
74
104
  extra_rdoc_files:
75
105
  - Readme.rdoc
76
106
  files:
107
+ - lib/amqp_logging/log_device.rb
108
+ - lib/amqp_logging/logger.rb
109
+ - lib/amqp_logging/metrics_agent/rails/after_dispatch_callback_handler.rb
110
+ - lib/amqp_logging/metrics_agent/rails.rb
111
+ - lib/amqp_logging/metrics_agent.rb
77
112
  - lib/amqp_logging.rb
78
113
  - Readme.rdoc
79
- - test/amqp_logger_test.rb
114
+ - test/logger_test.rb
115
+ - test/metrics_agent_test.rb
80
116
  - test/test_helper.rb
81
117
  has_rdoc: true
82
118
  homepage: http://github.com/paukul/amqp_logging
@@ -115,5 +151,6 @@ signing_key:
115
151
  specification_version: 3
116
152
  summary: A ruby logger class that logs to an AMQP exchange in addition to your default log device.
117
153
  test_files:
118
- - test/amqp_logger_test.rb
154
+ - test/logger_test.rb
155
+ - test/metrics_agent_test.rb
119
156
  - test/test_helper.rb