class BlueShell::BufferedReaderExpector

Attributes

output[R]

Public Class Methods

new(out, debug = false) click to toggle source
# File lib/blue-shell/buffered_reader_expector.rb, line 5
def initialize(out, debug = false)
  @out = out
  @debug = debug
  @unused = ""
  @output = ""
end

Public Instance Methods

expect(pattern) click to toggle source
# File lib/blue-shell/buffered_reader_expector.rb, line 12
def expect(pattern)
  case pattern
    when String
      pattern = Regexp.new(Regexp.quote(pattern))
    when Regexp
    else
      raise TypeError, "unsupported pattern class: #{pattern.class}"
  end

  result, buffer = read_pipe(BlueShell.timeout, pattern)

  @output << buffer

  result
end
read_to_end() click to toggle source
# File lib/blue-shell/buffered_reader_expector.rb, line 28
def read_to_end
  _, buffer = read_pipe(0.01)
  @output << buffer
end

Private Instance Methods

output_ended?(timeout) click to toggle source
# File lib/blue-shell/buffered_reader_expector.rb, line 79
def output_ended?(timeout)
  (@out.is_a?(IO) && !IO.select([@out], nil, nil, timeout)) || @out.eof?
end
read_pipe(timeout, pattern = nil) click to toggle source
# File lib/blue-shell/buffered_reader_expector.rb, line 35
def read_pipe(timeout, pattern = nil)
  buffer = ""
  result = nil
  position = 0
  @unused ||= ""

  while true
    if !@unused.empty?
      c = @unused.slice!(0).chr
    elsif output_ended?(timeout)
      @unused = buffer
      break
    else
      c = @out.getc.chr
    end

    STDOUT.putc c if @debug

    # wear your flip flops
    unless (c == "\e") .. (c == "m")
      if c == "\b"
        if position > 0 && buffer[position - 1] && buffer[position - 1].chr != "\n"
          position -= 1
        end
      else
        if buffer.size > position
          buffer[position] = c
        else
          buffer << c
        end

        position += 1
      end
    end

    if pattern && matches = pattern.match(buffer)
      result = [buffer, *matches.to_a[1..-1]]
      break
    end
  end

  return result, buffer
end