class MongoOplogBackup::Command

Constants

BLOCK_SIZE

Attributes

command[R]
standard_error[R]
standard_output[R]
status[R]

Public Class Methods

execute(command, options={}) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 20
def self.execute(command, options={})
  Command.new(command, options).run
end
logger() click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 11
def self.logger
  @logger
end
logger=(logger) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 7
def self.logger= logger
  @logger = logger
end
new(command, options={}) click to toggle source

command must be an array containing the command and arguments

# File lib/mongo_oplog_backup/command.rb, line 25
def initialize(command, options={})
  @command = command
  @standard_output = ''
  @standard_error = ''
  @out_blocks = []
  @err_blocks = []

  logger = options[:logger] || Command.logger

  if logger
    log_output(logger)
  end

  on_stdout do |data|
    @standard_output << data
  end
  on_stderr do |data|
    @standard_error << data
  end
end

Public Instance Methods

log_output(logger) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 62
def log_output(logger)
  on_stdout_line do |line|
    logger.debug(line)
  end
  on_stderr_line do |line|
    logger.error(line)
  end
end
on_stderr(&block) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 54
def on_stderr &block
  @err_blocks << block
end
on_stderr_line(&block) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 50
def on_stderr_line &block
  on_stderr(&lines_proc(&block))
end
on_stdout(&block) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 58
def on_stdout &block
  @out_blocks << block
end
on_stdout_line(&block) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 46
def on_stdout_line &block
  on_stdout(&lines_proc(&block))
end
raise!() click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 103
def raise!
  unless status.success?
    raise "Command failed with exit code #{status.exitstatus}"
  end
  self
end
run() click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 71
def run
  @status = Open3.popen3(*command) do |stdin, stdout, stderr, wait_thr|
    stdin.close_write
    # until all_eof([stdout, stderr])
    still_open = [stdout, stderr]
    until still_open.empty?
      handles = IO.select(still_open, nil, nil, 0.001)

      unless handles.nil?
        read_available_data(stdout) do |data|
          @out_blocks.each do |block|
            block.call(data)
          end
        end if handles[0].include?(stdout)

        read_available_data(stderr) do |data|
          @err_blocks.each do |block|
            block.call(data)
          end
        end if handles[0].include?(stderr)
      end

      still_open.delete_if { |s| s.closed? }
      sleep 0.001
    end

    wait_thr.value
  end
  raise!
  self
end

Private Instance Methods

lines_proc(&block) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 111
def lines_proc &block
  # TODO: buffer partial lines
  return Proc.new do |data|
    data.split("\n").each do |line|
      block.call line
    end
  end
end
read_available_data(io, &block) click to toggle source
# File lib/mongo_oplog_backup/command.rb, line 122
def read_available_data(io, &block)
  data = io.read_nonblock(BLOCK_SIZE)
  block.call data
rescue EOFError
  io.close
end