Class: Proxy::Dynflow::IOBuffer

Inherits:
Object
  • Object
show all
Defined in:
lib/smart_proxy_dynflow/io_buffer.rb

Overview

Note:

Using a single IOBuffer with a single IO for both reads and writes might not be a good idea. If you need to use a single IO for both reads and writes, wrap it in two separate IOBuffers.

A buffer around an IO object providing buffering and convenience methods for non-blocking reads and writes.

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(io) ⇒ IOBuffer

Returns a new instance of IOBuffer.

Parameters:

  • io (IO)

    The IO object to be buffered



15
16
17
18
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 15

def initialize(io)
  @buffer = ''
  @io = io
end

Instance Attribute Details

#bufferString (readonly)

The buffer where the data read from the underlying IO is buffered

Returns:

  • (String)

    the current value of buffer



10
11
12
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 10

def buffer
  @buffer
end

#ioObject

Returns the value of attribute io.



11
12
13
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 11

def io
  @io
end

Instance Method Details

#add_data(data) ⇒ void

This method returns an undefined value.

Adds data to the buffer. If the buffer is used for writing, then this should be the preferred method of queueing the data to be written.



100
101
102
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 100

def add_data(data)
  @buffer += data
end

#closevoid

This method returns an undefined value.

Closes the underlying IO. Does nothing if the IO is already closed.



63
64
65
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 63

def close
  @io.close unless @io.closed?
end

#closed?true, false

Checks whether the underlying IO is empty

Returns:

  • (true, false)

    whether the underlying IO is empty



56
57
58
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 56

def closed?
  @io.closed?
end

#empty?true, false

Checks whether the buffer is empty

Returns:

  • (true, false)

    whether the buffer is empty



49
50
51
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 49

def empty?
  @buffer.empty?
end

#on_data {|data| ... } ⇒ void

Note:

Note that if the callback is provided, the buffer will store the return value of the callback instead of the raw data.

This method returns an undefined value.

Sets a callback to be executed each time data is read from the underlying IO.

Yield Parameters:

  • data (String)

    read from the underlying IO

Yield Returns:

  • (String)

    data to be buffered



28
29
30
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 28

def on_data(&block)
  @callback = block
end

#read_available!void

This method returns an undefined value.

Reads all the data that is currently waiting in the IO and stores it. If EOFError is encountered during the read, the underlying IO is closed.



71
72
73
74
75
76
77
78
79
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 71

def read_available!
  data = ''
  loop { data += @io.read_nonblock(4096) }
rescue IO::WaitReadable # rubocop:disable Lint/HandleExceptions
rescue EOFError
  close
ensure
  @buffer += with_callback(data) unless data.empty?
end

#to_ioIO

Exposes the underlying IO so that the buffer itself can be used in IO.select calls.

Returns:

  • (IO)

    the underlying IO



35
36
37
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 35

def to_io
  @io
end

#to_sString

Exposes the contents of the buffer as a String

Returns:

  • (String)

    the buffered data



42
43
44
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 42

def to_s
  @buffer
end

#write_available!void

This method returns an undefined value.

Writes all the data into the IO that can be written without blocking. It is a no-op if there are no data to be written. If an EOFError is encountered during the write, the underlying IO is closed.



86
87
88
89
90
91
92
93
94
# File 'lib/smart_proxy_dynflow/io_buffer.rb', line 86

def write_available!
  until @buffer.empty?
    n = @io.write_nonblock(@buffer)
    @buffer = @buffer[n..-1]
  end
rescue IO::WaitWritable # rubocop:disable Lint/HandleExceptions
rescue EOFError
  close
end