lib/lightio/module/io.rb in lightio-0.4.1 vs lib/lightio/module/io.rb in lightio-0.4.2

- old
+ new

@@ -10,14 +10,22 @@ # helper methods def convert_to_io(io) unless io.respond_to?(:to_io) raise TypeError, "no implicit conversion of #{io.class} into IO" end - to_io = io.to_io + to_io = io.is_a?(LightIO::Library::IO) ? io : io.to_io unless to_io.is_a?(LightIO::Library::IO) - raise TypeError, "can't process raw IO, use LightIO::IO._wrap(obj) to wrap it" if to_io.is_a?(::IO) - raise TypeError, "can't convert #{io.class} to IO (#{io.class}#to_io gives #{to_io.class})" + raise TypeError, "can't convert #{io.class} to IO (#{io.class}#to_io gives #{to_io.class})" unless to_io.is_a?(::IO) + + # try wrap raw io instead of raise error + wrapped_io = to_io.instance_variable_get(:@_lightio_wrapped_io) + unless wrapped_io + wrapped_io = LightIO::Library::IO._wrap(to_io) + to_io.instance_variable_set(:@_lightio_wrapped_io, wrapped_io) + end + to_io = wrapped_io + # raise TypeError, "can't process raw IO, use LightIO::IO._wrap(obj) to wrap it" end to_io end def get_io_watcher(io) @@ -49,11 +57,31 @@ ensure w.close r.close end end - # [r, w] [wrap_to_library(r), wrap_to_library(w)] + end + + def copy_stream(*args) + raise ArgumentError, "wrong number of arguments (given #{args.size}, expected 2..4)" unless (2..4).include?(args.size) + src, dst, copy_length, src_offset = args + src = src.respond_to?(:to_io) ? src.to_io : LightIO::Library::File.open(src, 'r') unless src.is_a?(IO) + dst = dst.respond_to?(:to_io) ? dst.to_io : LightIO::Library::File.open(dst, 'w') unless dst.is_a?(IO) + buf_size = 4096 + copy_chars = 0 + buf_size = [buf_size, copy_length].min if copy_length + src.seek(src_offset) if src_offset + while (buf = src.read(buf_size)) + size = dst.write(buf) + copy_chars += size + if copy_length + copy_length -= size + break if copy_length.zero? + buf_size = [buf_size, copy_length].min + end + end + copy_chars end def select(read_fds, write_fds=nil, _except_fds=nil, timeout=nil) timer = timeout && Time.now read_fds ||= []