Class: Philiprehberger::StructuredLogger::AsyncWriter

Inherits:
Object
  • Object
show all
Defined in:
lib/philiprehberger/structured_logger/async_writer.rb

Overview

Non-blocking log writer that enqueues log lines to a background thread. Falls back to synchronous writes when the buffer is full (backpressure).

Instance Method Summary collapse

Constructor Details

#initialize(output, buffer_size: 1000) ⇒ AsyncWriter

Returns a new instance of AsyncWriter.

Parameters:

  • output (IO)

    writable output destination

  • buffer_size (Integer) (defaults to: 1000)

    maximum number of queued log lines



10
11
12
13
14
15
16
17
18
# File 'lib/philiprehberger/structured_logger/async_writer.rb', line 10

def initialize(output, buffer_size: 1000)
  @output = output
  @buffer_size = buffer_size
  @queue = SizedQueue.new(buffer_size)
  @stopped = false
  @closed = false
  @mutex = Mutex.new
  @thread = Thread.new { drain }
end

Instance Method Details

#closeObject

Flush remaining log lines and stop the background thread. Safe to call multiple times.



51
52
53
54
55
56
57
58
59
60
61
# File 'lib/philiprehberger/structured_logger/async_writer.rb', line 51

def close
  @mutex.synchronize do
    return if @closed

    @stopped = true
    @closed = true
  end
  @queue.push(:stop)
  @thread.join
  @output.flush if @output.respond_to?(:flush)
end

#flushObject

Force all buffered log lines to be written immediately.



44
45
46
47
# File 'lib/philiprehberger/structured_logger/async_writer.rb', line 44

def flush
  Thread.pass until @queue.empty?
  @output.flush if @output.respond_to?(:flush)
end

#puts(line) ⇒ Object

Write a log line using puts.

Parameters:

  • line (String)

    the formatted log line



39
40
41
# File 'lib/philiprehberger/structured_logger/async_writer.rb', line 39

def puts(line)
  write(line)
end

#write(line) ⇒ Object

Enqueue a log line for asynchronous writing. Falls back to synchronous write if the buffer is full.

Parameters:

  • line (String)

    the formatted log line



24
25
26
27
28
29
30
31
32
33
34
# File 'lib/philiprehberger/structured_logger/async_writer.rb', line 24

def write(line)
  @mutex.synchronize do
    return sync_write(line) if @stopped
  end

  begin
    @queue.push(line, true)
  rescue ThreadError
    sync_write(line)
  end
end