rubyzip 1.3.0 → 3.0.0.alpha

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (134) hide show
  1. checksums.yaml +4 -4
  2. data/Changelog.md +368 -0
  3. data/README.md +123 -46
  4. data/Rakefile +13 -6
  5. data/lib/zip/central_directory.rb +166 -116
  6. data/lib/zip/compressor.rb +3 -1
  7. data/lib/zip/constants.rb +77 -21
  8. data/lib/zip/crypto/decrypted_io.rb +42 -0
  9. data/lib/zip/crypto/encryption.rb +4 -2
  10. data/lib/zip/crypto/null_encryption.rb +5 -3
  11. data/lib/zip/crypto/traditional_encryption.rb +14 -12
  12. data/lib/zip/decompressor.rb +21 -2
  13. data/lib/zip/deflater.rb +10 -8
  14. data/lib/zip/dirtyable.rb +32 -0
  15. data/lib/zip/dos_time.rb +53 -12
  16. data/lib/zip/entry.rb +306 -184
  17. data/lib/zip/entry_set.rb +11 -7
  18. data/lib/zip/errors.rb +115 -15
  19. data/lib/zip/extra_field/generic.rb +11 -17
  20. data/lib/zip/extra_field/ntfs.rb +8 -2
  21. data/lib/zip/extra_field/old_unix.rb +6 -2
  22. data/lib/zip/extra_field/universal_time.rb +45 -13
  23. data/lib/zip/extra_field/unix.rb +7 -3
  24. data/lib/zip/extra_field/unknown.rb +33 -0
  25. data/lib/zip/extra_field/zip64.rb +16 -7
  26. data/lib/zip/extra_field.rb +22 -26
  27. data/lib/zip/file.rb +196 -240
  28. data/lib/zip/file_split.rb +97 -0
  29. data/lib/zip/filesystem/dir.rb +86 -0
  30. data/lib/zip/filesystem/directory_iterator.rb +48 -0
  31. data/lib/zip/filesystem/file.rb +262 -0
  32. data/lib/zip/filesystem/file_stat.rb +110 -0
  33. data/lib/zip/filesystem/zip_file_name_mapper.rb +81 -0
  34. data/lib/zip/filesystem.rb +31 -584
  35. data/lib/zip/inflater.rb +27 -37
  36. data/lib/zip/input_stream.rb +67 -42
  37. data/lib/zip/ioextras/abstract_input_stream.rb +32 -16
  38. data/lib/zip/ioextras/abstract_output_stream.rb +5 -3
  39. data/lib/zip/ioextras.rb +7 -7
  40. data/lib/zip/null_compressor.rb +3 -1
  41. data/lib/zip/null_decompressor.rb +4 -10
  42. data/lib/zip/null_input_stream.rb +3 -1
  43. data/lib/zip/output_stream.rb +58 -43
  44. data/lib/zip/pass_thru_compressor.rb +5 -3
  45. data/lib/zip/pass_thru_decompressor.rb +16 -23
  46. data/lib/zip/streamable_directory.rb +6 -4
  47. data/lib/zip/streamable_stream.rb +9 -10
  48. data/lib/zip/version.rb +3 -1
  49. data/lib/zip.rb +19 -4
  50. data/rubyzip.gemspec +38 -0
  51. data/samples/example.rb +9 -4
  52. data/samples/example_filesystem.rb +3 -2
  53. data/samples/example_recursive.rb +3 -1
  54. data/samples/gtk_ruby_zip.rb +22 -20
  55. data/samples/qtzip.rb +12 -11
  56. data/samples/write_simple.rb +3 -4
  57. data/samples/zipfind.rb +24 -22
  58. metadata +86 -179
  59. data/TODO +0 -15
  60. data/lib/zip/extra_field/zip64_placeholder.rb +0 -15
  61. data/test/basic_zip_file_test.rb +0 -60
  62. data/test/case_sensitivity_test.rb +0 -69
  63. data/test/central_directory_entry_test.rb +0 -69
  64. data/test/central_directory_test.rb +0 -100
  65. data/test/crypto/null_encryption_test.rb +0 -57
  66. data/test/crypto/traditional_encryption_test.rb +0 -80
  67. data/test/data/WarnInvalidDate.zip +0 -0
  68. data/test/data/file1.txt +0 -46
  69. data/test/data/file1.txt.deflatedData +0 -0
  70. data/test/data/file2.txt +0 -1504
  71. data/test/data/globTest/foo/bar/baz/foo.txt +0 -0
  72. data/test/data/globTest/foo.txt +0 -0
  73. data/test/data/globTest/food.txt +0 -0
  74. data/test/data/globTest.zip +0 -0
  75. data/test/data/gpbit3stored.zip +0 -0
  76. data/test/data/mimetype +0 -1
  77. data/test/data/notzippedruby.rb +0 -7
  78. data/test/data/ntfs.zip +0 -0
  79. data/test/data/oddExtraField.zip +0 -0
  80. data/test/data/path_traversal/Makefile +0 -10
  81. data/test/data/path_traversal/jwilk/README.md +0 -5
  82. data/test/data/path_traversal/jwilk/absolute1.zip +0 -0
  83. data/test/data/path_traversal/jwilk/absolute2.zip +0 -0
  84. data/test/data/path_traversal/jwilk/dirsymlink.zip +0 -0
  85. data/test/data/path_traversal/jwilk/dirsymlink2a.zip +0 -0
  86. data/test/data/path_traversal/jwilk/dirsymlink2b.zip +0 -0
  87. data/test/data/path_traversal/jwilk/relative0.zip +0 -0
  88. data/test/data/path_traversal/jwilk/relative2.zip +0 -0
  89. data/test/data/path_traversal/jwilk/symlink.zip +0 -0
  90. data/test/data/path_traversal/relative1.zip +0 -0
  91. data/test/data/path_traversal/tilde.zip +0 -0
  92. data/test/data/path_traversal/tuzovakaoff/README.md +0 -3
  93. data/test/data/path_traversal/tuzovakaoff/absolutepath.zip +0 -0
  94. data/test/data/path_traversal/tuzovakaoff/symlink.zip +0 -0
  95. data/test/data/rubycode.zip +0 -0
  96. data/test/data/rubycode2.zip +0 -0
  97. data/test/data/test.xls +0 -0
  98. data/test/data/testDirectory.bin +0 -0
  99. data/test/data/zip64-sample.zip +0 -0
  100. data/test/data/zipWithDirs.zip +0 -0
  101. data/test/data/zipWithEncryption.zip +0 -0
  102. data/test/deflater_test.rb +0 -65
  103. data/test/encryption_test.rb +0 -42
  104. data/test/entry_set_test.rb +0 -163
  105. data/test/entry_test.rb +0 -154
  106. data/test/errors_test.rb +0 -35
  107. data/test/extra_field_test.rb +0 -76
  108. data/test/file_extract_directory_test.rb +0 -54
  109. data/test/file_extract_test.rb +0 -145
  110. data/test/file_permissions_test.rb +0 -65
  111. data/test/file_split_test.rb +0 -57
  112. data/test/file_test.rb +0 -666
  113. data/test/filesystem/dir_iterator_test.rb +0 -58
  114. data/test/filesystem/directory_test.rb +0 -139
  115. data/test/filesystem/file_mutating_test.rb +0 -87
  116. data/test/filesystem/file_nonmutating_test.rb +0 -508
  117. data/test/filesystem/file_stat_test.rb +0 -64
  118. data/test/gentestfiles.rb +0 -126
  119. data/test/inflater_test.rb +0 -14
  120. data/test/input_stream_test.rb +0 -182
  121. data/test/ioextras/abstract_input_stream_test.rb +0 -102
  122. data/test/ioextras/abstract_output_stream_test.rb +0 -106
  123. data/test/ioextras/fake_io_test.rb +0 -18
  124. data/test/local_entry_test.rb +0 -154
  125. data/test/output_stream_test.rb +0 -128
  126. data/test/pass_thru_compressor_test.rb +0 -30
  127. data/test/pass_thru_decompressor_test.rb +0 -14
  128. data/test/path_traversal_test.rb +0 -141
  129. data/test/samples/example_recursive_test.rb +0 -37
  130. data/test/settings_test.rb +0 -95
  131. data/test/test_helper.rb +0 -234
  132. data/test/unicode_file_names_and_comments_test.rb +0 -62
  133. data/test/zip64_full_test.rb +0 -51
  134. data/test/zip64_support_test.rb +0 -14
data/lib/zip/inflater.rb CHANGED
@@ -1,64 +1,54 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- class Inflater < Decompressor #:nodoc:all
3
- def initialize(input_stream, decrypter = NullDecrypter.new)
4
- super(input_stream)
5
- @zlib_inflater = ::Zlib::Inflate.new(-Zlib::MAX_WBITS)
6
- @output_buffer = ''.dup
7
- @has_returned_empty_string = false
8
- @decrypter = decrypter
9
- end
4
+ class Inflater < Decompressor # :nodoc:all
5
+ def initialize(*args)
6
+ super
10
7
 
11
- def sysread(number_of_bytes = nil, buf = '')
12
- readEverything = number_of_bytes.nil?
13
- while readEverything || @output_buffer.bytesize < number_of_bytes
14
- break if internal_input_finished?
15
- @output_buffer << internal_produce_input(buf)
16
- end
17
- return value_when_finished if @output_buffer.bytesize == 0 && input_finished?
18
- end_index = number_of_bytes.nil? ? @output_buffer.bytesize : number_of_bytes
19
- @output_buffer.slice!(0...end_index)
8
+ @buffer = +''
9
+ @zlib_inflater = ::Zlib::Inflate.new(-Zlib::MAX_WBITS)
20
10
  end
21
11
 
22
- def produce_input
23
- if @output_buffer.empty?
24
- internal_produce_input
25
- else
26
- @output_buffer.slice!(0...(@output_buffer.length))
12
+ def read(length = nil, outbuf = +'')
13
+ return (length.nil? || length.zero? ? '' : nil) if eof
14
+
15
+ while length.nil? || (@buffer.bytesize < length)
16
+ break if input_finished?
17
+
18
+ @buffer << produce_input
27
19
  end
20
+
21
+ outbuf.replace(@buffer.slice!(0...(length || @buffer.bytesize)))
28
22
  end
29
23
 
30
- # to be used with produce_input, not read (as read may still have more data cached)
31
- # is data cached anywhere other than @outputBuffer? the comment above may be wrong
32
- def input_finished?
33
- @output_buffer.empty? && internal_input_finished?
24
+ def eof
25
+ @buffer.empty? && input_finished?
34
26
  end
35
27
 
36
- alias :eof input_finished?
37
- alias :eof? input_finished?
28
+ alias eof? eof
38
29
 
39
30
  private
40
31
 
41
- def internal_produce_input(buf = '')
32
+ def produce_input
42
33
  retried = 0
43
34
  begin
44
- @zlib_inflater.inflate(@decrypter.decrypt(@input_stream.read(Decompressor::CHUNK_SIZE, buf)))
35
+ @zlib_inflater.inflate(input_stream.read(Decompressor::CHUNK_SIZE))
45
36
  rescue Zlib::BufError
46
37
  raise if retried >= 5 # how many times should we retry?
38
+
47
39
  retried += 1
48
40
  retry
49
41
  end
42
+ rescue Zlib::Error => e
43
+ raise ::Zip::DecompressionError, e
50
44
  end
51
45
 
52
- def internal_input_finished?
46
+ def input_finished?
53
47
  @zlib_inflater.finished?
54
48
  end
55
-
56
- def value_when_finished # mimic behaviour of ruby File object.
57
- return if @has_returned_empty_string
58
- @has_returned_empty_string = true
59
- ''
60
- end
61
49
  end
50
+
51
+ ::Zip::Decompressor.register(::Zip::COMPRESSION_METHOD_DEFLATE, ::Zip::Inflater)
62
52
  end
63
53
 
64
54
  # Copyright (C) 2002, 2003 Thomas Sondergaard
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
4
  # InputStream is the basic class for reading zip entries in a
3
5
  # zip file. It is possible to create a InputStream object directly,
@@ -39,6 +41,8 @@ module Zip
39
41
  # class.
40
42
 
41
43
  class InputStream
44
+ CHUNK_SIZE = 32_768
45
+
42
46
  include ::Zip::IOExtras::AbstractInputStream
43
47
 
44
48
  # Opens the indicated zip file. An exception is thrown
@@ -47,30 +51,37 @@ module Zip
47
51
  #
48
52
  # @param context [String||IO||StringIO] file path or IO/StringIO object
49
53
  # @param offset [Integer] offset in the IO/StringIO
50
- def initialize(context, offset = 0, decrypter = nil)
54
+ def initialize(context, offset: 0, decrypter: nil)
51
55
  super()
52
56
  @archive_io = get_io(context, offset)
53
- @decompressor = ::Zip::NullDecompressor
54
- @decrypter = decrypter || ::Zip::NullDecrypter.new
57
+ @decompressor = ::Zip::NullDecompressor
58
+ @decrypter = decrypter || ::Zip::NullDecrypter.new
55
59
  @current_entry = nil
60
+ @complete_entry = nil
56
61
  end
57
62
 
58
63
  def close
59
64
  @archive_io.close
60
65
  end
61
66
 
62
- # Returns a Entry object. It is necessary to call this
63
- # method on a newly created InputStream before reading from
64
- # the first entry in the archive. Returns nil when there are
65
- # no more entries.
67
+ # Returns an Entry object and positions the stream at the beginning of
68
+ # the entry data. It is necessary to call this method on a newly created
69
+ # InputStream before reading from the first entry in the archive.
70
+ # Returns nil when there are no more entries.
66
71
  def get_next_entry
67
- @archive_io.seek(@current_entry.next_header_offset, IO::SEEK_SET) if @current_entry
72
+ unless @current_entry.nil?
73
+ raise StreamingError, @current_entry if @current_entry.incomplete?
74
+
75
+ @archive_io.seek(@current_entry.next_header_offset, IO::SEEK_SET)
76
+ end
77
+
68
78
  open_entry
69
79
  end
70
80
 
71
81
  # Rewinds the stream to the beginning of the current entry
72
82
  def rewind
73
83
  return if @current_entry.nil?
84
+
74
85
  @lineno = 0
75
86
  @pos = 0
76
87
  @archive_io.seek(@current_entry.local_header_offset, IO::SEEK_SET)
@@ -78,23 +89,25 @@ module Zip
78
89
  end
79
90
 
80
91
  # Modeled after IO.sysread
81
- def sysread(number_of_bytes = nil, buf = nil)
82
- @decompressor.sysread(number_of_bytes, buf)
92
+ def sysread(length = nil, outbuf = '')
93
+ @decompressor.read(length, outbuf)
83
94
  end
84
95
 
85
- def eof
86
- @output_buffer.empty? && @decompressor.eof
87
- end
96
+ # Returns the size of the current entry, or `nil` if there isn't one.
97
+ def size
98
+ return if @current_entry.nil?
88
99
 
89
- alias :eof? eof
100
+ @current_entry.size
101
+ end
90
102
 
91
103
  class << self
92
104
  # Same as #initialize but if a block is passed the opened
93
105
  # stream is passed to the block and closed when the block
94
106
  # returns.
95
- def open(filename_or_io, offset = 0, decrypter = nil)
96
- zio = new(filename_or_io, offset, decrypter)
107
+ def open(filename_or_io, offset: 0, decrypter: nil)
108
+ zio = new(filename_or_io, offset: offset, decrypter: decrypter)
97
109
  return zio unless block_given?
110
+
98
111
  begin
99
112
  yield zio
100
113
  ensure
@@ -102,9 +115,9 @@ module Zip
102
115
  end
103
116
  end
104
117
 
105
- def open_buffer(filename_or_io, offset = 0)
106
- puts 'open_buffer is deprecated!!! Use open instead!'
107
- open(filename_or_io, offset)
118
+ def open_buffer(filename_or_io, offset: 0)
119
+ warn 'open_buffer is deprecated!!! Use open instead!'
120
+ ::Zip::InputStream.open(filename_or_io, offset: offset)
108
121
  end
109
122
  end
110
123
 
@@ -124,46 +137,58 @@ module Zip
124
137
 
125
138
  def open_entry
126
139
  @current_entry = ::Zip::Entry.read_local_entry(@archive_io)
127
- if @current_entry && @current_entry.gp_flags & 1 == 1 && @decrypter.is_a?(NullEncrypter)
128
- raise Error, 'password required to decode zip file'
140
+ return if @current_entry.nil?
141
+
142
+ if @current_entry.encrypted? && @decrypter.kind_of?(NullDecrypter)
143
+ raise Error,
144
+ 'A password is required to decode this zip file'
129
145
  end
130
- if @current_entry && @current_entry.gp_flags & 8 == 8 && @current_entry.crc == 0 \
131
- && @current_entry.compressed_size == 0 \
132
- && @current_entry.size == 0 && !@complete_entry
133
- raise GPFBit3Error,
134
- 'General purpose flag Bit 3 is set so not possible to get proper info from local header.' \
135
- 'Please use ::Zip::File instead of ::Zip::InputStream'
146
+
147
+ if @current_entry.incomplete? && @current_entry.compressed_size == 0 \
148
+ && !@complete_entry
149
+ raise StreamingError, @current_entry
136
150
  end
151
+
152
+ @decrypted_io = get_decrypted_io
137
153
  @decompressor = get_decompressor
138
154
  flush
139
155
  @current_entry
140
156
  end
141
157
 
158
+ def get_decrypted_io
159
+ header = @archive_io.read(@decrypter.header_bytesize)
160
+ @decrypter.reset!(header)
161
+
162
+ ::Zip::DecryptedIo.new(@archive_io, @decrypter)
163
+ end
164
+
142
165
  def get_decompressor
143
- if @current_entry.nil?
144
- ::Zip::NullDecompressor
145
- elsif @current_entry.compression_method == ::Zip::Entry::STORED
146
- if @current_entry.gp_flags & 8 == 8 && @current_entry.crc == 0 && @current_entry.size == 0 && @complete_entry
147
- ::Zip::PassThruDecompressor.new(@archive_io, @complete_entry.size)
166
+ return ::Zip::NullDecompressor if @current_entry.nil?
167
+
168
+ decompressed_size =
169
+ if @current_entry.incomplete? && @current_entry.crc == 0 \
170
+ && @current_entry.size == 0 && @complete_entry
171
+ @complete_entry.size
148
172
  else
149
- ::Zip::PassThruDecompressor.new(@archive_io, @current_entry.size)
173
+ @current_entry.size
150
174
  end
151
- elsif @current_entry.compression_method == ::Zip::Entry::DEFLATED
152
- header = @archive_io.read(@decrypter.header_bytesize)
153
- @decrypter.reset!(header)
154
- ::Zip::Inflater.new(@archive_io, @decrypter)
155
- else
156
- raise ::Zip::CompressionMethodError,
157
- "Unsupported compression method #{@current_entry.compression_method}"
175
+
176
+ decompressor_class = ::Zip::Decompressor.find_by_compression_method(
177
+ @current_entry.compression_method
178
+ )
179
+ if decompressor_class.nil?
180
+ raise ::Zip::CompressionMethodError, @current_entry.compression_method
158
181
  end
182
+
183
+ decompressor_class.new(@decrypted_io, decompressed_size)
159
184
  end
160
185
 
161
186
  def produce_input
162
- @decompressor.produce_input
187
+ @decompressor.read(CHUNK_SIZE)
163
188
  end
164
189
 
165
190
  def input_finished?
166
- @decompressor.input_finished?
191
+ @decompressor.eof
167
192
  end
168
193
  end
169
194
  end
@@ -1,9 +1,11 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- module IOExtras
4
+ module IOExtras # :nodoc:
3
5
  # Implements many of the convenience methods of IO
4
6
  # such as gets, getc, readline and readlines
5
7
  # depends on: input_finished?, produce_input and read
6
- module AbstractInputStream
8
+ module AbstractInputStream # :nodoc:
7
9
  include Enumerable
8
10
  include FakeIO
9
11
 
@@ -11,15 +13,15 @@ module Zip
11
13
  super
12
14
  @lineno = 0
13
15
  @pos = 0
14
- @output_buffer = ''
16
+ @output_buffer = +''
15
17
  end
16
18
 
17
19
  attr_accessor :lineno
18
20
  attr_reader :pos
19
21
 
20
- def read(number_of_bytes = nil, buf = '')
22
+ def read(number_of_bytes = nil, buf = +'')
21
23
  tbuf = if @output_buffer.bytesize > 0
22
- if number_of_bytes <= @output_buffer.bytesize
24
+ if number_of_bytes && number_of_bytes <= @output_buffer.bytesize
23
25
  @output_buffer.slice!(0, number_of_bytes)
24
26
  else
25
27
  number_of_bytes -= @output_buffer.bytesize if number_of_bytes
@@ -34,7 +36,8 @@ module Zip
34
36
  end
35
37
 
36
38
  if tbuf.nil? || tbuf.empty?
37
- return nil if number_of_bytes
39
+ return nil if number_of_bytes&.positive?
40
+
38
41
  return ''
39
42
  end
40
43
 
@@ -48,13 +51,13 @@ module Zip
48
51
  buf
49
52
  end
50
53
 
51
- def readlines(a_sep_string = $/)
54
+ def readlines(a_sep_string = $INPUT_RECORD_SEPARATOR)
52
55
  ret_val = []
53
56
  each_line(a_sep_string) { |line| ret_val << line }
54
57
  ret_val
55
58
  end
56
59
 
57
- def gets(a_sep_string = $/, number_of_bytes = nil)
60
+ def gets(a_sep_string = $INPUT_RECORD_SEPARATOR, number_of_bytes = nil)
58
61
  @lineno = @lineno.next
59
62
 
60
63
  if number_of_bytes.respond_to?(:to_int)
@@ -62,24 +65,29 @@ module Zip
62
65
  a_sep_string = a_sep_string.to_str if a_sep_string
63
66
  elsif a_sep_string.respond_to?(:to_int)
64
67
  number_of_bytes = a_sep_string.to_int
65
- a_sep_string = $/
68
+ a_sep_string = $INPUT_RECORD_SEPARATOR
66
69
  else
67
70
  number_of_bytes = nil
68
71
  a_sep_string = a_sep_string.to_str if a_sep_string
69
72
  end
70
73
 
71
74
  return read(number_of_bytes) if a_sep_string.nil?
72
- a_sep_string = "#{$/}#{$/}" if a_sep_string.empty?
75
+
76
+ a_sep_string = "#{$INPUT_RECORD_SEPARATOR}#{$INPUT_RECORD_SEPARATOR}" if a_sep_string.empty?
73
77
 
74
78
  buffer_index = 0
75
79
  over_limit = (number_of_bytes && @output_buffer.bytesize >= number_of_bytes)
76
80
  while (match_index = @output_buffer.index(a_sep_string, buffer_index)).nil? && !over_limit
77
81
  buffer_index = [buffer_index, @output_buffer.bytesize - a_sep_string.bytesize].max
78
82
  return @output_buffer.empty? ? nil : flush if input_finished?
83
+
79
84
  @output_buffer << produce_input
80
85
  over_limit = (number_of_bytes && @output_buffer.bytesize >= number_of_bytes)
81
86
  end
82
- sep_index = [match_index + a_sep_string.bytesize, number_of_bytes || @output_buffer.bytesize].min
87
+ sep_index = [
88
+ match_index + a_sep_string.bytesize,
89
+ number_of_bytes || @output_buffer.bytesize
90
+ ].min
83
91
  @pos += sep_index
84
92
  @output_buffer.slice!(0...sep_index)
85
93
  end
@@ -90,22 +98,30 @@ module Zip
90
98
 
91
99
  def flush
92
100
  ret_val = @output_buffer
93
- @output_buffer = ''
101
+ @output_buffer = +''
94
102
  ret_val
95
103
  end
96
104
 
97
- def readline(a_sep_string = $/)
105
+ def readline(a_sep_string = $INPUT_RECORD_SEPARATOR)
98
106
  ret_val = gets(a_sep_string)
99
107
  raise EOFError unless ret_val
108
+
100
109
  ret_val
101
110
  end
102
111
 
103
- def each_line(a_sep_string = $/)
104
- yield readline(a_sep_string) while true
112
+ def each_line(a_sep_string = $INPUT_RECORD_SEPARATOR)
113
+ loop { yield readline(a_sep_string) }
105
114
  rescue EOFError
115
+ # We just need to catch this; we don't need to handle it.
116
+ end
117
+
118
+ alias each each_line
119
+
120
+ def eof
121
+ @output_buffer.empty? && input_finished?
106
122
  end
107
123
 
108
- alias_method :each, :each_line
124
+ alias eof? eof
109
125
  end
110
126
  end
111
127
  end
@@ -1,8 +1,10 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- module IOExtras
4
+ module IOExtras # :nodoc:
3
5
  # Implements many of the output convenience methods of IO.
4
6
  # relies on <<
5
- module AbstractOutputStream
7
+ module AbstractOutputStream # :nodoc:
6
8
  include FakeIO
7
9
 
8
10
  def write(data)
@@ -11,7 +13,7 @@ module Zip
11
13
  end
12
14
 
13
15
  def print(*params)
14
- self << params.join($,) << $\.to_s
16
+ self << params.join << $OUTPUT_RECORD_SEPARATOR.to_s
15
17
  end
16
18
 
17
19
  def printf(a_format_string, *params)
data/lib/zip/ioextras.rb CHANGED
@@ -1,31 +1,31 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- module IOExtras #:nodoc:
4
+ module IOExtras # :nodoc:
3
5
  CHUNK_SIZE = 131_072
4
6
 
5
- RANGE_ALL = 0..-1
6
-
7
7
  class << self
8
8
  def copy_stream(ostream, istream)
9
- ostream.write(istream.read(CHUNK_SIZE, '')) until istream.eof?
9
+ ostream.write(istream.read(CHUNK_SIZE, +'')) until istream.eof?
10
10
  end
11
11
 
12
12
  def copy_stream_n(ostream, istream, nbytes)
13
13
  toread = nbytes
14
14
  while toread > 0 && !istream.eof?
15
15
  tr = toread > CHUNK_SIZE ? CHUNK_SIZE : toread
16
- ostream.write(istream.read(tr, ''))
16
+ ostream.write(istream.read(tr, +''))
17
17
  toread -= tr
18
18
  end
19
19
  end
20
20
  end
21
21
 
22
22
  # Implements kind_of? in order to pretend to be an IO object
23
- module FakeIO
23
+ module FakeIO # :nodoc:
24
24
  def kind_of?(object)
25
25
  object == IO || super
26
26
  end
27
27
  end
28
- end # IOExtras namespace module
28
+ end
29
29
  end
30
30
 
31
31
  require 'zip/ioextras/abstract_input_stream'
@@ -1,5 +1,7 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- class NullCompressor < Compressor #:nodoc:all
4
+ class NullCompressor < Compressor # :nodoc:all
3
5
  include Singleton
4
6
 
5
7
  def <<(_data)
@@ -1,19 +1,13 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- module NullDecompressor #:nodoc:all
4
+ module NullDecompressor # :nodoc:all
3
5
  module_function
4
6
 
5
- def sysread(_numberOfBytes = nil, _buf = nil)
6
- nil
7
- end
8
-
9
- def produce_input
7
+ def read(_length = nil, _outbuf = nil)
10
8
  nil
11
9
  end
12
10
 
13
- def input_finished?
14
- true
15
- end
16
-
17
11
  def eof
18
12
  true
19
13
  end
@@ -1,5 +1,7 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Zip
2
- module NullInputStream #:nodoc:all
4
+ module NullInputStream # :nodoc:all
3
5
  include ::Zip::NullDecompressor
4
6
  include ::Zip::IOExtras::AbstractInputStream
5
7
  end