minitar 1.0.2 → 1.1.0
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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +285 -0
- data/CONTRIBUTING.md +273 -0
- data/CONTRIBUTORS.md +27 -0
- data/LICENCE.md +39 -0
- data/Manifest.txt +29 -6
- data/README.md +70 -0
- data/Rakefile +74 -19
- data/SECURITY.md +64 -0
- data/docs/ruby.txt +3 -3
- data/lib/minitar/input.rb +69 -56
- data/lib/minitar/output.rb +34 -22
- data/lib/minitar/pax_header.rb +111 -0
- data/lib/minitar/posix_header.rb +96 -57
- data/lib/minitar/reader.rb +65 -70
- data/lib/minitar/version.rb +5 -0
- data/lib/minitar/writer.rb +50 -88
- data/lib/minitar.rb +60 -64
- data/licenses/bsdl.txt +20 -0
- data/licenses/dco.txt +34 -0
- data/licenses/ruby.txt +52 -0
- data/test/fixtures/issue_46.tar.gz +0 -0
- data/test/fixtures/issue_62.tar.gz +0 -0
- data/test/fixtures/tar_input.tgz +0 -0
- data/test/fixtures/test_input_non_strict_octal.tgz +0 -0
- data/test/fixtures/test_input_relative.tgz +0 -0
- data/test/fixtures/test_input_space_octal.tgz +0 -0
- data/test/fixtures/test_minitar.tar.gz +0 -0
- data/test/minitest_helper.rb +12 -1
- data/test/support/minitar_test_helpers/fixtures.rb +38 -0
- data/test/support/minitar_test_helpers/header.rb +130 -0
- data/test/support/minitar_test_helpers/tarball.rb +324 -0
- data/test/support/minitar_test_helpers.rb +36 -0
- data/test/test_filename_boundary_conditions.rb +74 -0
- data/test/test_gnu_tar_compatibility.rb +92 -0
- data/test/test_integration_pack_unpack_cycle.rb +38 -0
- data/test/test_issue_46.rb +5 -23
- data/test/test_issue_62.rb +50 -0
- data/test/test_minitar.rb +168 -39
- data/test/test_pax_header.rb +104 -0
- data/test/test_pax_support.rb +66 -0
- data/test/test_tar_header.rb +289 -75
- data/test/test_tar_input.rb +14 -61
- data/test/test_tar_output.rb +7 -9
- data/test/test_tar_reader.rb +17 -18
- data/test/test_tar_writer.rb +105 -126
- metadata +95 -89
- data/Contributing.md +0 -94
- data/History.md +0 -236
- data/Licence.md +0 -15
- data/README.rdoc +0 -92
- data/test/support/tar_test_helpers.rb +0 -134
- /data/{Code-of-Conduct.md → CODE_OF_CONDUCT.md} +0 -0
data/test/test_tar_writer.rb
CHANGED
@@ -1,6 +1,5 @@
|
|
1
|
-
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
|
-
require "minitar"
|
4
3
|
require "minitest_helper"
|
5
4
|
|
6
5
|
class TestTarWriter < Minitest::Test
|
@@ -17,25 +16,25 @@ class TestTarWriter < Minitest::Test
|
|
17
16
|
end
|
18
17
|
|
19
18
|
def reset
|
20
|
-
@data = ""
|
21
|
-
@data.force_encoding("ascii-8bit")
|
19
|
+
@data = +""
|
20
|
+
@data.force_encoding("ascii-8bit")
|
22
21
|
end
|
23
22
|
end
|
24
23
|
|
25
24
|
def setup
|
26
25
|
@data = "a" * 10
|
27
26
|
@unicode = [0xc3.chr, 0xa5.chr].join * 10
|
28
|
-
@unicode.force_encoding("utf-8")
|
29
|
-
@
|
30
|
-
@
|
27
|
+
@unicode.force_encoding("utf-8")
|
28
|
+
@dummy_writer = DummyIO.new
|
29
|
+
@writer = Minitar::Writer.new(@dummy_writer)
|
31
30
|
end
|
32
31
|
|
33
32
|
def teardown
|
34
|
-
@
|
33
|
+
@writer.close
|
35
34
|
end
|
36
35
|
|
37
36
|
def test_open_no_block
|
38
|
-
writer = Minitar::Writer.open(@
|
37
|
+
writer = Minitar::Writer.open(@dummy_writer)
|
39
38
|
refute writer.closed?
|
40
39
|
ensure
|
41
40
|
writer.close
|
@@ -43,100 +42,76 @@ class TestTarWriter < Minitest::Test
|
|
43
42
|
end
|
44
43
|
|
45
44
|
def test_add_file_simple
|
46
|
-
@
|
47
|
-
|
48
|
-
|
49
|
-
os.add_file_simple("lib/foo/bar", mode: 0o644, size: 10) do |f|
|
50
|
-
f.write "a" * 10
|
51
|
-
end
|
52
|
-
os.add_file_simple("lib/bar/baz", mode: 0o644, size: 100) do |f|
|
53
|
-
f.write "fillme"
|
54
|
-
end
|
45
|
+
Minitar::Writer.open(@dummy_writer) do |os|
|
46
|
+
os.add_file_simple("lib/foo/bar", mode: 0o644, size: 10) { _1.write "a" * 10 }
|
47
|
+
os.add_file_simple("lib/bar/baz", mode: 0o644, size: 100) { _1.write "fillme" }
|
55
48
|
end
|
56
49
|
|
57
|
-
assert_headers_equal(
|
58
|
-
@
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
50
|
+
assert_headers_equal build_tar_file_header("lib/foo/bar", "", 0o644, 10),
|
51
|
+
@dummy_writer.data[0, 512]
|
52
|
+
|
53
|
+
assert_equal "a" * 10 + "\0" * 502, @dummy_writer.data[512, 512]
|
54
|
+
|
55
|
+
assert_headers_equal build_tar_file_header("lib/bar/baz", "", 0o644, 100),
|
56
|
+
@dummy_writer.data[512 * 2, 512]
|
57
|
+
|
58
|
+
assert_equal "fillme" + "\0" * 506, @dummy_writer.data[512 * 3, 512]
|
59
|
+
assert_equal "\0" * 512, @dummy_writer.data[512 * 4, 512]
|
60
|
+
assert_equal "\0" * 512, @dummy_writer.data[512 * 5, 512]
|
65
61
|
end
|
66
62
|
|
67
63
|
def test_write_operations_fail_after_closed
|
68
|
-
@
|
69
|
-
@
|
70
|
-
@
|
71
|
-
assert_raises(Minitar::ClosedStream) { @
|
72
|
-
assert_raises(Minitar::ClosedStream) { @
|
73
|
-
assert_raises(Minitar::ClosedStream) { @
|
74
|
-
assert_raises(Minitar::ClosedStream) { @os.symlink "a", "b", mode: 0o644 }
|
64
|
+
@writer.add_file_simple("sadd", mode: 0o644, size: 20) {}
|
65
|
+
@writer.close
|
66
|
+
assert_raises(Minitar::ClosedStream) { @writer.flush }
|
67
|
+
assert_raises(Minitar::ClosedStream) { @writer.add_file("dfdsf", mode: 0o644) {} }
|
68
|
+
assert_raises(Minitar::ClosedStream) { @writer.mkdir "sdfdsf", mode: 0o644 }
|
69
|
+
assert_raises(Minitar::ClosedStream) { @writer.symlink "a", "b", mode: 0o644 }
|
75
70
|
end
|
76
71
|
|
77
72
|
def test_file_name_is_split_correctly
|
78
|
-
# test
|
79
|
-
|
80
|
-
|
81
|
-
"#{"a" *
|
82
|
-
"
|
83
|
-
"
|
84
|
-
"#{"a" * 49}/#{"b" * 50}x"
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
"#{"qwer/" * 19}bla",
|
90
|
-
"b" * 50,
|
91
|
-
"#{"b" * 50}x",
|
92
|
-
"b" * 50
|
93
|
-
]
|
94
|
-
o_prefixes = [
|
95
|
-
"a" * 155,
|
96
|
-
"a" * 151,
|
97
|
-
"/#{"a" * 49}",
|
98
|
-
"a" * 49,
|
99
|
-
"#{"a" * 49}x"
|
100
|
-
]
|
101
|
-
names.each do |name|
|
102
|
-
@os.add_file_simple(name, mode: 0o644, size: 10) {}
|
73
|
+
# test extreme file lengths, and: a{100}/b{155}, etc
|
74
|
+
names = {
|
75
|
+
"#{"a" * 155}/#{"b" * 100}" => {name: "b" * 100, prefix: "a" * 155},
|
76
|
+
"#{"a" * 151}/#{"qwer/" * 19}bla" => {name: "#{"qwer/" * 19}bla", prefix: "a" * 151},
|
77
|
+
"/#{"a" * 49}/#{"b" * 50}" => {name: "b" * 50, prefix: "/#{"a" * 49}"},
|
78
|
+
"#{"a" * 49}/#{"b" * 50}x" => {name: "#{"b" * 50}x", prefix: "a" * 49},
|
79
|
+
"#{"a" * 49}x/#{"b" * 50}" => {name: "b" * 50, prefix: "#{"a" * 49}x"}
|
80
|
+
}
|
81
|
+
|
82
|
+
names.each_key do |name|
|
83
|
+
@writer.add_file_simple(name, mode: 0o644, size: 10) {}
|
103
84
|
end
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
)
|
85
|
+
|
86
|
+
names.each_key.with_index do |key, index|
|
87
|
+
name, prefix = names[key][:name], names[key][:prefix]
|
88
|
+
|
89
|
+
assert_headers_equal build_tar_file_header(name, prefix, 0o644, 10),
|
90
|
+
@dummy_writer.data[2 * index * 512, 512]
|
109
91
|
end
|
110
92
|
end
|
111
93
|
|
112
94
|
def test_file_name_is_long
|
113
|
-
@
|
114
|
-
|
115
|
-
@
|
116
|
-
mode: 0o644, size: 10) {}
|
117
|
-
@os.add_file_simple(File.join("d" * 162, "e" * 10),
|
118
|
-
mode: 0o644, size: 10) {}
|
119
|
-
@os.add_file_simple(File.join("f" * 10, "g" * 110),
|
120
|
-
mode: 0o644, size: 10) {}
|
95
|
+
@writer.add_file_simple(File.join("a" * 152, "b" * 10, "c" * 92), mode: 0o644, size: 10) {}
|
96
|
+
@writer.add_file_simple(File.join("d" * 162, "e" * 10), mode: 0o644, size: 10) {}
|
97
|
+
@writer.add_file_simple(File.join("f" * 10, "g" * 110), mode: 0o644, size: 10) {}
|
121
98
|
# Issue #6.
|
122
|
-
@
|
99
|
+
@writer.add_file_simple("a" * 114, mode: 0o644, size: 10) {}
|
123
100
|
|
124
101
|
# "././@LongLink", a file name, its actual header, its data, ...
|
125
102
|
4.times do |i|
|
126
|
-
assert_equal
|
127
|
-
@
|
103
|
+
assert_equal Minitar::PosixHeader::GNU_EXT_LONG_LINK,
|
104
|
+
@dummy_writer.data[4 * i * 512, 32].rstrip
|
128
105
|
end
|
129
106
|
end
|
130
107
|
|
131
108
|
def test_add_file_simple_content_with_long_name
|
132
|
-
@dummyos.reset
|
133
|
-
|
134
109
|
long_name_file_content = "where_is_all_the_content_gone"
|
135
110
|
|
136
|
-
@
|
111
|
+
@writer.add_file_simple("a" * 114, mode: 0o0644, data: long_name_file_content)
|
137
112
|
|
138
|
-
assert_equal
|
139
|
-
@
|
113
|
+
assert_equal long_name_file_content,
|
114
|
+
@dummy_writer.data[3 * 512, long_name_file_content.bytesize]
|
140
115
|
end
|
141
116
|
|
142
117
|
def test_add_file_content_with_long_name
|
@@ -157,8 +132,8 @@ class TestTarWriter < Minitest::Test
|
|
157
132
|
end
|
158
133
|
end
|
159
134
|
|
160
|
-
assert_equal
|
161
|
-
dummyos[3 * 512, long_name_file_content.bytesize]
|
135
|
+
assert_equal long_name_file_content,
|
136
|
+
dummyos[3 * 512, long_name_file_content.bytesize]
|
162
137
|
end
|
163
138
|
|
164
139
|
def test_add_file
|
@@ -170,105 +145,109 @@ class TestTarWriter < Minitest::Test
|
|
170
145
|
def dummyos.respond_to_missing?(meth, all)
|
171
146
|
string.respond_to?(meth, all)
|
172
147
|
end
|
148
|
+
|
173
149
|
content1 = ("a".."z").to_a.join("") # 26
|
174
150
|
content2 = ("aa".."zz").to_a.join("") # 1352
|
151
|
+
|
175
152
|
Minitar::Writer.open(dummyos) do |os|
|
176
153
|
os.add_file("lib/foo/bar", mode: 0o644) { |f, _opts| f.write "a" * 10 }
|
177
154
|
os.add_file("lib/bar/baz", mode: 0o644) { |f, _opts| f.write content1 }
|
178
155
|
os.add_file("lib/bar/baz", mode: 0o644) { |f, _opts| f.write content2 }
|
179
156
|
os.add_file("lib/bar/baz", mode: 0o644) { |_f, _opts| }
|
180
157
|
end
|
181
|
-
|
182
|
-
|
158
|
+
|
159
|
+
assert_headers_equal build_tar_file_header("lib/foo/bar", "", 0o644, 10),
|
160
|
+
dummyos[0, 512]
|
161
|
+
|
183
162
|
assert_equal %(#{"a" * 10}#{"\0" * 502}), dummyos[512, 512]
|
184
163
|
offset = 512 * 2
|
164
|
+
|
185
165
|
[content1, content2, ""].each do |data|
|
186
|
-
assert_headers_equal(
|
187
|
-
|
166
|
+
assert_headers_equal build_tar_file_header("lib/bar/baz", "", 0o644, data.bytesize),
|
167
|
+
dummyos[offset, 512]
|
168
|
+
|
188
169
|
offset += 512
|
170
|
+
|
189
171
|
until !data || data == ""
|
190
172
|
chunk = data[0, 512]
|
191
173
|
data[0, 512] = ""
|
192
|
-
|
193
|
-
|
174
|
+
|
175
|
+
assert_equal chunk + "\0" * (512 - chunk.bytesize), dummyos[offset, 512]
|
194
176
|
offset += 512
|
195
177
|
end
|
196
178
|
end
|
179
|
+
|
197
180
|
assert_equal "\0" * 1024, dummyos[offset, 1024]
|
198
181
|
end
|
199
182
|
|
200
183
|
def test_add_file_tests_seekability
|
201
184
|
assert_raises(Minitar::NonSeekableStream) do
|
202
|
-
@
|
185
|
+
@writer.add_file("libdfdsfd", mode: 0o644) { |f| }
|
203
186
|
end
|
204
187
|
end
|
205
188
|
|
206
189
|
def test_write_header
|
207
|
-
@
|
208
|
-
@
|
209
|
-
|
210
|
-
assert_headers_equal(
|
211
|
-
@
|
212
|
-
|
213
|
-
@
|
214
|
-
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
-
|
190
|
+
@writer.add_file_simple("lib/foo/bar", mode: 0o644, size: 0) {}
|
191
|
+
@writer.flush
|
192
|
+
|
193
|
+
assert_headers_equal build_tar_file_header("lib/foo/bar", "", 0o644, 0),
|
194
|
+
@dummy_writer.data[0, 512]
|
195
|
+
|
196
|
+
@dummy_writer.reset
|
197
|
+
@writer.mkdir("lib/foo", mode: 0o644)
|
198
|
+
|
199
|
+
assert_headers_equal build_tar_dir_header("lib/foo", "", 0o644),
|
200
|
+
@dummy_writer.data[0, 512]
|
201
|
+
|
202
|
+
@writer.mkdir("lib/bar", mode: 0o644)
|
203
|
+
|
204
|
+
assert_headers_equal build_tar_dir_header("lib/bar", "", 0o644),
|
205
|
+
@dummy_writer.data[512 * 1, 512]
|
219
206
|
end
|
220
207
|
|
221
208
|
def test_write_data
|
222
|
-
@
|
223
|
-
@os.add_file_simple("lib/foo/bar", mode: 0o644, size: 10) do |f|
|
209
|
+
@writer.add_file_simple("lib/foo/bar", mode: 0o644, size: 10) do |f|
|
224
210
|
f.write @data
|
225
211
|
end
|
226
|
-
@
|
227
|
-
|
228
|
-
|
212
|
+
@writer.flush
|
213
|
+
|
214
|
+
assert_equal @data + ("\0" * (512 - @data.bytesize)), @dummy_writer.data[512, 512]
|
229
215
|
end
|
230
216
|
|
231
217
|
def test_write_unicode_data
|
232
|
-
@
|
233
|
-
|
234
|
-
|
235
|
-
assert_equal 10, @unicode.size
|
236
|
-
assert_equal 20, @unicode.bytesize
|
237
|
-
@unicode.force_encoding("ascii-8bit")
|
238
|
-
end
|
218
|
+
assert_equal 10, @unicode.size
|
219
|
+
assert_equal 20, @unicode.bytesize
|
220
|
+
@unicode.force_encoding("ascii-8bit")
|
239
221
|
|
240
222
|
file = ["lib/foo/b", 0xc3.chr, 0xa5.chr, "r"].join
|
241
223
|
|
242
|
-
@
|
224
|
+
@writer.add_file_simple(file, mode: 0o644, size: 20) do |f|
|
243
225
|
f.write @unicode
|
244
226
|
end
|
245
|
-
@
|
246
|
-
|
247
|
-
|
227
|
+
@writer.flush
|
228
|
+
|
229
|
+
assert_equal @unicode + ("\0" * (512 - @unicode.bytesize)), @dummy_writer.data[512, 512]
|
248
230
|
end
|
249
231
|
|
250
232
|
def test_file_size_is_checked
|
251
|
-
@dummyos.reset
|
252
233
|
assert_raises(Minitar::Writer::WriteBoundaryOverflow) do
|
253
|
-
@
|
234
|
+
@writer.add_file_simple("lib/foo/bar", mode: 0o644, size: 10) do |f|
|
254
235
|
f.write "1" * 100
|
255
236
|
end
|
256
237
|
end
|
257
|
-
@
|
238
|
+
@writer.add_file_simple("lib/foo/bar", mode: 0o644, size: 10) { |f| }
|
258
239
|
end
|
259
240
|
|
260
241
|
def test_symlink
|
261
|
-
@
|
262
|
-
@
|
263
|
-
|
264
|
-
|
265
|
-
@dummyos.data[0, 512])
|
242
|
+
@writer.symlink("lib/foo/bar", "lib/foo/baz", mode: 0o644)
|
243
|
+
@writer.flush
|
244
|
+
assert_headers_equal build_tar_symlink_header("lib/foo/bar", "", 0o644, "lib/foo/baz"),
|
245
|
+
@dummy_writer.data[0, 512]
|
266
246
|
end
|
267
247
|
|
268
248
|
def test_symlink_target_size_is_checked
|
269
|
-
@dummyos.reset
|
270
249
|
assert_raises(Minitar::FileNameTooLong) do
|
271
|
-
@
|
250
|
+
@writer.symlink("lib/foo/bar", "x" * 101)
|
272
251
|
end
|
273
252
|
end
|
274
253
|
end
|