mirror of
https://github.com/meineerde/rackstash.git
synced 2025-12-19 15:01:12 +00:00
Add Callable adapter to handle a log in a custom way
Users can provide a "callable", i.e. a proc or block which will be called for each written log. This allows users to custom handle the logs without having to write a full adapter. Usually, users should still write a full adapter to handle all cases of their wrapped log device.
This commit is contained in:
parent
0aa39483dd
commit
aad1660135
@ -56,3 +56,4 @@ end
|
|||||||
require 'rackstash/logger'
|
require 'rackstash/logger'
|
||||||
|
|
||||||
require 'rackstash/adapters/io'
|
require 'rackstash/adapters/io'
|
||||||
|
require 'rackstash/adapters/callable'
|
||||||
|
|||||||
69
lib/rackstash/adapters/callable.rb
Normal file
69
lib/rackstash/adapters/callable.rb
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
# Copyright 2017 Holger Just
|
||||||
|
#
|
||||||
|
# This software may be modified and distributed under the terms
|
||||||
|
# of the MIT license. See the LICENSE.txt file for details.
|
||||||
|
|
||||||
|
require 'rackstash/adapters/adapter'
|
||||||
|
require 'rackstash/encoders/raw'
|
||||||
|
|
||||||
|
module Rackstash
|
||||||
|
module Adapters
|
||||||
|
# This adapter calls a user-provided "callable", i.e., a `Proc` or block for
|
||||||
|
# each written log line. This allows users to custom handle the logs without
|
||||||
|
# having to write a full custom adapter class.
|
||||||
|
#
|
||||||
|
# You can pass the callable as a block to {#initialize} or as a Proc or any
|
||||||
|
# other object responding to `call`. For each written log, we call the block
|
||||||
|
# once.
|
||||||
|
#
|
||||||
|
# Note that we do not ensure that the calls are sequentially. If multiple
|
||||||
|
# threads are concurrently writing logs to the logger, the calable might be
|
||||||
|
# called concurrently from multiple threads too.
|
||||||
|
#
|
||||||
|
# To create an adapter instance, you can use this example:
|
||||||
|
#
|
||||||
|
# Rackstash::Adapters::Callable.new do |log|
|
||||||
|
# # handle the log as required
|
||||||
|
# end
|
||||||
|
class Callable < Adapter
|
||||||
|
register_for ::Proc, :call
|
||||||
|
|
||||||
|
# Create a new Callable adapter by wrapping a proc. You can pass the proc
|
||||||
|
# either as the firat parameter to {#initialize} or as a block which is
|
||||||
|
# then transformed into a proc internally.
|
||||||
|
#
|
||||||
|
# @param callable [Proc, #call] a callable object, usually a proc or
|
||||||
|
# lambda
|
||||||
|
def initialize(callable = nil, &block)
|
||||||
|
if callable.respond_to?(:call)
|
||||||
|
@callable = callable
|
||||||
|
elsif block_given?
|
||||||
|
@callable = block
|
||||||
|
else
|
||||||
|
raise TypeError, "#{callable.inspect} does not appear to be callable"
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
# By default, we use an {Rackstash::Encoders::Raw} to encode the events.
|
||||||
|
# This ensures that the raw event is passed through to to the callable by
|
||||||
|
# default.
|
||||||
|
#
|
||||||
|
# You can define a custom encoder in the responsible {Flow}.
|
||||||
|
#
|
||||||
|
# @return [Rackstash::Encoders::Raw] a new Raw encoder
|
||||||
|
def default_encoder
|
||||||
|
Rackstash::Encoders::Raw.new
|
||||||
|
end
|
||||||
|
|
||||||
|
# Write a single log line by calling the defined `callable` given in
|
||||||
|
# {#initialize}.
|
||||||
|
#
|
||||||
|
# @param log [Object] the encoded log event
|
||||||
|
# @return [nil]
|
||||||
|
def write_single(log)
|
||||||
|
@callable.call(log)
|
||||||
|
nil
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
63
spec/rackstash/adapters/callable_spec.rb
Normal file
63
spec/rackstash/adapters/callable_spec.rb
Normal file
@ -0,0 +1,63 @@
|
|||||||
|
# Copyright 2017 Holger Just
|
||||||
|
#
|
||||||
|
# This software may be modified and distributed under the terms
|
||||||
|
# of the MIT license. See the LICENSE.txt file for details.
|
||||||
|
|
||||||
|
require 'spec_helper'
|
||||||
|
|
||||||
|
require 'rackstash/adapters/callable'
|
||||||
|
|
||||||
|
describe Rackstash::Adapters::Callable do
|
||||||
|
let(:callable) { ->(log) { log } }
|
||||||
|
let(:adapter) { Rackstash::Adapters::Callable.new(callable) }
|
||||||
|
|
||||||
|
describe '#initialize' do
|
||||||
|
it 'accepts a callable' do
|
||||||
|
expect { Rackstash::Adapters::Callable.new(->{}) }.not_to raise_error
|
||||||
|
expect { Rackstash::Adapters::Callable.new(proc {}) }.not_to raise_error
|
||||||
|
expect { Rackstash::Adapters::Callable.new(Struct.new(:call).new) }.not_to raise_error
|
||||||
|
|
||||||
|
expect { Rackstash::Adapters::Callable.new { |log| log } }.not_to raise_error
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'rejects non-IO objects' do
|
||||||
|
expect { Rackstash::Adapters::Callable.new(nil) }.to raise_error TypeError
|
||||||
|
expect { Rackstash::Adapters::Callable.new('hello') }.to raise_error TypeError
|
||||||
|
expect { Rackstash::Adapters::Callable.new(Object.new) }.to raise_error TypeError
|
||||||
|
expect { Rackstash::Adapters::Callable.new([]) }.to raise_error TypeError
|
||||||
|
expect { Rackstash::Adapters::Callable.new(Struct.new(:foo).new) }.to raise_error TypeError
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
describe '.default_encoder' do
|
||||||
|
it 'returns a Raw encoder' do
|
||||||
|
expect(adapter.default_encoder).to be_instance_of Rackstash::Encoders::Raw
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
describe '#close' do
|
||||||
|
it 'does nothing' do
|
||||||
|
expect(callable).not_to receive(:close)
|
||||||
|
adapter.close
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
describe '#reopen' do
|
||||||
|
it 'does nothing' do
|
||||||
|
expect(callable).not_to receive(:close)
|
||||||
|
adapter.reopen
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
describe '#write_single' do
|
||||||
|
it 'calls the callable with the log' do
|
||||||
|
expect(callable).to receive(:call).with('a log line')
|
||||||
|
adapter.write('a log line')
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'passes through the original object' do
|
||||||
|
expect(callable).to receive(:call).with([123, 'hello'])
|
||||||
|
adapter.write([123, 'hello'])
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
Loading…
x
Reference in New Issue
Block a user