adsp 1.0.2 → 1.0.6

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 (39) hide show
  1. checksums.yaml +4 -4
  2. data/{test → lib/adsp/test}/common.rb +4 -1
  3. data/{test → lib/adsp/test}/coverage_helper.rb +0 -0
  4. data/lib/adsp/test/file.rb +120 -0
  5. data/{test → lib/adsp/test}/minitest.rb +1 -0
  6. data/{test → lib/adsp/test}/mock/common.rb +1 -0
  7. data/{test → lib/adsp/test}/mock/file.rb +1 -0
  8. data/{test → lib/adsp/test}/mock/stream/raw/compressor.rb +1 -0
  9. data/{test → lib/adsp/test}/mock/stream/raw/decompressor.rb +1 -0
  10. data/{test → lib/adsp/test}/mock/stream/raw/native_compressor.rb +1 -0
  11. data/{test → lib/adsp/test}/mock/stream/raw/native_decompressor.rb +1 -0
  12. data/{test → lib/adsp/test}/mock/stream/reader.rb +1 -0
  13. data/{test → lib/adsp/test}/mock/stream/writer.rb +1 -0
  14. data/{test → lib/adsp/test}/mock/string.rb +1 -0
  15. data/{test → lib/adsp/test}/option.rb +1 -0
  16. data/{test → lib/adsp/test}/stream/abstract.rb +1 -0
  17. data/lib/adsp/test/stream/minitar.rb +50 -0
  18. data/{test → lib/adsp/test}/stream/raw/abstract.rb +1 -0
  19. data/lib/adsp/test/stream/raw/compressor.rb +165 -0
  20. data/lib/adsp/test/stream/raw/decompressor.rb +165 -0
  21. data/lib/adsp/test/stream/reader.rb +642 -0
  22. data/lib/adsp/test/stream/reader_helpers.rb +421 -0
  23. data/lib/adsp/test/stream/writer.rb +609 -0
  24. data/lib/adsp/test/stream/writer_helpers.rb +267 -0
  25. data/lib/adsp/test/string.rb +95 -0
  26. data/{test → lib/adsp/test}/validation.rb +7 -0
  27. data/lib/adsp/test/version.rb +18 -0
  28. data/lib/adsp/version.rb +1 -1
  29. data/test/file.test.rb +3 -116
  30. data/test/stream/minitar.test.rb +3 -46
  31. data/test/stream/raw/compressor.test.rb +3 -162
  32. data/test/stream/raw/decompressor.test.rb +3 -162
  33. data/test/stream/reader.test.rb +3 -639
  34. data/test/stream/reader_helpers.test.rb +3 -417
  35. data/test/stream/writer.test.rb +3 -606
  36. data/test/stream/writer_helpers.test.rb +3 -263
  37. data/test/string.test.rb +3 -91
  38. data/test/version.test.rb +3 -14
  39. metadata +28 -19
@@ -1,643 +1,7 @@
1
1
  # Abstract data stream processor.
2
2
  # Copyright (c) 2021 AUTHORS, MIT License.
3
3
 
4
- require "set"
5
- require "socket"
6
- require "stringio"
4
+ require "adsp/test/minitest"
5
+ require "adsp/test/stream/reader"
7
6
 
8
- require_relative "abstract"
9
- require_relative "../common"
10
- require_relative "../minitest"
11
- require_relative "../option"
12
- require_relative "../validation"
13
- require_relative "../mock/stream/reader"
14
- require_relative "../mock/string"
15
-
16
- module ADSP
17
- module Test
18
- module Stream
19
- class Reader < Abstract
20
- Target = Mock::Stream::Reader
21
- String = Mock::String
22
-
23
- ARCHIVE_PATH = Common::ARCHIVE_PATH
24
- ENCODINGS = Common::ENCODINGS
25
- TRANSCODE_OPTIONS = Common::TRANSCODE_OPTIONS
26
- TEXTS = Common::TEXTS
27
- LARGE_TEXTS = Common::LARGE_TEXTS
28
- PORTION_LENGTHS = Common::PORTION_LENGTHS
29
- LARGE_PORTION_LENGTHS = Common::LARGE_PORTION_LENGTHS
30
-
31
- BUFFER_LENGTH_NAMES = %i[source_buffer_length destination_buffer_length].freeze
32
- BUFFER_LENGTH_MAPPING = {
33
- :source_buffer_length => :destination_buffer_length,
34
- :destination_buffer_length => :source_buffer_length
35
- }
36
- .freeze
37
-
38
- def test_invalid_initialize
39
- get_invalid_decompressor_options do |invalid_options|
40
- assert_raises ValidateError do
41
- target.new ::StringIO.new, invalid_options
42
- end
43
- end
44
-
45
- super
46
- end
47
-
48
- # -- synchronous --
49
-
50
- def test_invalid_read
51
- instance = target.new ::StringIO.new
52
-
53
- (Validation::INVALID_NOT_NEGATIVE_INTEGERS - [nil]).each do |invalid_integer|
54
- assert_raises ValidateError do
55
- instance.read invalid_integer
56
- end
57
- end
58
-
59
- (Validation::INVALID_STRINGS - [nil]).each do |invalid_string|
60
- assert_raises ValidateError do
61
- instance.read nil, invalid_string
62
- end
63
- end
64
-
65
- assert_raises ValidateError do
66
- instance = target.new Validation::StringIOWithoutRead.new
67
- instance.read
68
- end
69
-
70
- assert_raises ValidateError do
71
- instance = target.new Validation::StringIOWithoutEOF.new
72
- instance.read
73
- end
74
- end
75
-
76
- def test_read
77
- parallel_compressor_options do |compressor_options|
78
- TEXTS.each do |text|
79
- archive = get_archive text, compressor_options
80
- prev_result = "".b
81
-
82
- Option::BOOLS.each do |with_buffer|
83
- PORTION_LENGTHS.each do |portion_length|
84
- get_compatible_decompressor_options compressor_options do |decompressor_options|
85
- instance = target.new ::StringIO.new(archive), decompressor_options
86
- decompressed_text = "".b
87
-
88
- begin
89
- result = instance.read 0
90
- assert_equal "", result
91
-
92
- loop do
93
- prev_eof = instance.eof?
94
-
95
- result =
96
- if with_buffer
97
- instance.read portion_length, prev_result
98
- else
99
- instance.read portion_length
100
- end
101
-
102
- if result.nil?
103
- assert_predicate instance, :eof?
104
- break
105
- end
106
-
107
- refute prev_eof unless archive.bytesize.zero?
108
-
109
- assert_equal prev_result, result if with_buffer
110
- decompressed_text << result
111
- end
112
-
113
- assert_equal instance.pos, decompressed_text.bytesize
114
- assert_equal instance.pos, instance.tell
115
- ensure
116
- refute_predicate instance, :closed?
117
- instance.close
118
- assert_predicate instance, :closed?
119
- end
120
-
121
- decompressed_text.force_encoding text.encoding
122
- assert_equal text, decompressed_text
123
- end
124
- end
125
-
126
- get_compatible_decompressor_options compressor_options do |decompressor_options|
127
- instance = target.new ::StringIO.new(archive), decompressor_options
128
- decompressed_text = nil
129
-
130
- begin
131
- prev_eof = instance.eof?
132
-
133
- if with_buffer
134
- decompressed_text = instance.read nil, prev_result
135
- assert_equal prev_result, decompressed_text
136
- else
137
- decompressed_text = instance.read
138
- end
139
-
140
- assert_predicate instance, :eof?
141
- refute prev_eof unless archive.bytesize.zero?
142
-
143
- assert_equal instance.pos, decompressed_text.bytesize
144
- assert_equal instance.pos, instance.tell
145
- ensure
146
- refute_predicate instance, :closed?
147
- instance.close
148
- assert_predicate instance, :closed?
149
- end
150
-
151
- decompressed_text.force_encoding text.encoding
152
- assert_equal text, decompressed_text
153
- end
154
- end
155
- end
156
- end
157
- end
158
-
159
- def test_read_with_large_texts
160
- options_generator = OCG.new(
161
- :text => LARGE_TEXTS,
162
- :with_buffer => Option::BOOLS
163
- )
164
-
165
- Common.parallel_options options_generator do |options|
166
- text = options[:text]
167
- with_buffer = options[:with_buffer]
168
-
169
- archive = get_archive text
170
- prev_result = "".b
171
-
172
- LARGE_PORTION_LENGTHS.each do |portion_length|
173
- instance = target.new ::StringIO.new(archive)
174
- decompressed_text = "".b
175
-
176
- begin
177
- loop do
178
- result =
179
- if with_buffer
180
- instance.read portion_length, prev_result
181
- else
182
- instance.read portion_length
183
- end
184
-
185
- break if result.nil?
186
-
187
- assert_equal prev_result, result if with_buffer
188
- decompressed_text << result
189
- end
190
- ensure
191
- instance.close
192
- end
193
-
194
- decompressed_text.force_encoding text.encoding
195
- assert_equal text, decompressed_text
196
- end
197
-
198
- instance = target.new ::StringIO.new(archive)
199
- decompressed_text = nil
200
-
201
- begin
202
- if with_buffer
203
- decompressed_text = instance.read nil, prev_result
204
- assert_equal prev_result, decompressed_text
205
- else
206
- decompressed_text = instance.read
207
- end
208
- ensure
209
- instance.close
210
- end
211
-
212
- decompressed_text.force_encoding text.encoding
213
- assert_equal text, decompressed_text
214
- end
215
- end
216
-
217
- def test_encoding
218
- parallel_compressor_options do |compressor_options|
219
- TEXTS.each do |text|
220
- external_encoding = text.encoding
221
- archive = get_archive text, compressor_options
222
-
223
- PORTION_LENGTHS.each do |portion_length|
224
- get_compatible_decompressor_options compressor_options do |decompressor_options|
225
- instance = target.new ::StringIO.new(archive), decompressor_options
226
- decompressed_text = "".b
227
-
228
- begin
229
- result = instance.read 0
230
- assert_equal Encoding::BINARY, result.encoding
231
-
232
- loop do
233
- result = instance.read portion_length
234
- break if result.nil?
235
-
236
- assert_equal Encoding::BINARY, result.encoding
237
- decompressed_text << result
238
- end
239
- ensure
240
- instance.close
241
- end
242
-
243
- decompressed_text.force_encoding external_encoding
244
- assert_equal text, decompressed_text
245
- end
246
- end
247
-
248
- # We don't need to transcode between same encodings.
249
- (ENCODINGS - [external_encoding]).each do |internal_encoding|
250
- target_text = text.encode internal_encoding, **TRANSCODE_OPTIONS
251
-
252
- get_compatible_decompressor_options compressor_options do |decompressor_options|
253
- instance = target.new(
254
- ::StringIO.new(archive),
255
- decompressor_options,
256
- :external_encoding => external_encoding,
257
- :internal_encoding => internal_encoding,
258
- :transcode_options => TRANSCODE_OPTIONS
259
- )
260
-
261
- assert_equal external_encoding, instance.external_encoding
262
- assert_equal internal_encoding, instance.internal_encoding
263
- assert_equal TRANSCODE_OPTIONS, instance.transcode_options
264
-
265
- decompressed_text = nil
266
-
267
- begin
268
- instance.set_encoding external_encoding, internal_encoding, TRANSCODE_OPTIONS
269
- assert_equal external_encoding, instance.external_encoding
270
- assert_equal internal_encoding, instance.internal_encoding
271
- assert_equal TRANSCODE_OPTIONS, instance.transcode_options
272
-
273
- decompressed_text = instance.read
274
- assert_equal internal_encoding, decompressed_text.encoding
275
- ensure
276
- instance.close
277
- end
278
-
279
- assert_equal target_text, decompressed_text
280
- assert_predicate target_text, :valid_encoding?
281
- end
282
- end
283
- end
284
- end
285
- end
286
-
287
- def test_rewind
288
- parallel_compressor_options do |compressor_options, worker_index|
289
- archive_path = Common.get_path ARCHIVE_PATH, worker_index
290
-
291
- TEXTS.each do |text|
292
- write_archive archive_path, text, compressor_options
293
-
294
- get_compatible_decompressor_options compressor_options do |decompressor_options|
295
- decompressed_text = nil
296
-
297
- ::File.open archive_path, "rb" do |file|
298
- instance = target.new file, decompressor_options
299
-
300
- begin
301
- result_1 = instance.read
302
-
303
- assert_equal 0, instance.rewind
304
- assert_equal 0, instance.pos
305
- assert_equal instance.pos, instance.tell
306
-
307
- result_2 = instance.read
308
- assert_equal result_1, result_2
309
-
310
- decompressed_text = result_1
311
- ensure
312
- instance.close
313
- end
314
- end
315
-
316
- decompressed_text.force_encoding text.encoding
317
- assert_equal text, decompressed_text
318
- end
319
- end
320
- end
321
- end
322
-
323
- def test_invalid_eof
324
- assert_raises ValidateError do
325
- instance = target.new Validation::StringIOWithoutEOF.new
326
- instance.eof?
327
- end
328
- end
329
-
330
- def test_eof
331
- compressed_text = String.compress "ab"
332
- instance = target.new ::StringIO.new(compressed_text)
333
-
334
- refute_predicate instance, :eof?
335
-
336
- byte = instance.read 1
337
- refute_predicate instance, :eof?
338
- assert_equal "a", byte
339
-
340
- byte = instance.read 1
341
- assert_predicate instance, :eof?
342
- assert_equal "b", byte
343
- end
344
-
345
- # -- asynchronous --
346
-
347
- def test_invalid_readpartial_and_read_nonblock
348
- instance = target.new ::StringIO.new
349
-
350
- Validation::INVALID_NOT_NEGATIVE_INTEGERS.each do |invalid_integer|
351
- assert_raises ValidateError do
352
- instance.readpartial invalid_integer
353
- end
354
- assert_raises ValidateError do
355
- instance.read_nonblock invalid_integer
356
- end
357
- end
358
-
359
- (Validation::INVALID_STRINGS - [nil]).each do |invalid_string|
360
- assert_raises ValidateError do
361
- instance.readpartial 0, invalid_string
362
- end
363
- assert_raises ValidateError do
364
- instance.read_nonblock 0, invalid_string
365
- end
366
- end
367
-
368
- assert_raises ValidateError do
369
- instance = target.new Validation::StringIOWithoutReadpartial.new
370
- instance.readpartial 1
371
- end
372
-
373
- assert_raises ValidateError do
374
- instance = target.new Validation::StringIOWithoutReadNonblock.new
375
- instance.read_nonblock 1
376
- end
377
- end
378
-
379
- def test_readpartial
380
- IO.pipe do |read_io, write_io|
381
- instance = target.new read_io
382
- write_io.close
383
-
384
- assert_raises ::EOFError do
385
- instance.readpartial 1
386
- end
387
- end
388
-
389
- nonblock_server do |server|
390
- parallel_compressor_options do |compressor_options|
391
- TEXTS.each do |text|
392
- PORTION_LENGTHS.each do |portion_length|
393
- Option::BOOLS.each do |with_buffer|
394
- nonblock_test server, text, portion_length, compressor_options do |instance|
395
- prev_result = "".b
396
- decompressed_text = "".b
397
-
398
- loop do
399
- if with_buffer
400
- result = instance.readpartial portion_length, prev_result
401
- assert_equal prev_result, result
402
- else
403
- result = instance.readpartial portion_length
404
- end
405
-
406
- decompressed_text << result
407
- rescue ::EOFError
408
- break
409
- end
410
-
411
- decompressed_text
412
- end
413
- end
414
- end
415
- end
416
- end
417
- end
418
- end
419
-
420
- def test_read_nonblock
421
- IO.pipe do |read_io, write_io|
422
- instance = target.new read_io
423
-
424
- assert_raises ::IO::WaitReadable do
425
- instance.read_nonblock 1
426
- end
427
-
428
- write_io.close
429
-
430
- assert_raises ::EOFError do
431
- instance.read_nonblock 1
432
- end
433
- end
434
-
435
- nonblock_server do |server|
436
- parallel_compressor_options do |compressor_options|
437
- TEXTS.each do |text|
438
- PORTION_LENGTHS.each do |portion_length|
439
- nonblock_test server, text, portion_length, compressor_options do |instance, socket|
440
- decompressed_text = "".b
441
-
442
- loop do
443
- begin
444
- decompressed_text << instance.read_nonblock(portion_length)
445
- rescue ::IO::WaitReadable
446
- socket.wait_readable
447
- retry
448
- rescue ::EOFError
449
- break
450
- end
451
-
452
- begin
453
- decompressed_text << instance.readpartial(portion_length)
454
- rescue ::EOFError
455
- break
456
- end
457
-
458
- result = instance.read portion_length
459
- break if result.nil?
460
-
461
- decompressed_text << result
462
- end
463
-
464
- decompressed_text
465
- end
466
- end
467
- end
468
- end
469
- end
470
- end
471
-
472
- def test_read_nonblock_with_large_texts
473
- nonblock_server do |server|
474
- Common.parallel LARGE_TEXTS do |text|
475
- LARGE_PORTION_LENGTHS.each do |portion_length|
476
- nonblock_test server, text, portion_length do |instance, socket|
477
- decompressed_text = "".b
478
-
479
- loop do
480
- begin
481
- decompressed_text << instance.read_nonblock(portion_length)
482
- rescue ::IO::WaitReadable
483
- socket.wait_readable
484
- retry
485
- rescue ::EOFError
486
- break
487
- end
488
-
489
- begin
490
- decompressed_text << instance.readpartial(portion_length)
491
- rescue ::EOFError
492
- break
493
- end
494
-
495
- result = instance.read portion_length
496
- break if result.nil?
497
-
498
- decompressed_text << result
499
- end
500
-
501
- decompressed_text
502
- end
503
- end
504
- end
505
- end
506
- end
507
-
508
- # -- nonblock test --
509
-
510
- protected def nonblock_server
511
- # Server need just to redirect content for client.
512
-
513
- ::TCPServer.open 0 do |server|
514
- # Server loop will be processed in separate (parent) thread.
515
- # Child threads will be collected for later usage.
516
- child_lock = ::Mutex.new
517
- child_threads = ::Set.new
518
-
519
- parent_thread = ::Thread.new do
520
- loop do
521
- child_thread = ::Thread.start server.accept do |socket|
522
- result = "".b
523
-
524
- # Reading head.
525
- result_size, portion_length = socket.read(16).unpack "QQ"
526
- next if result_size.zero?
527
-
528
- # Reading result.
529
- loop do
530
- begin
531
- result << socket.read_nonblock(portion_length)
532
- rescue ::IO::WaitReadable
533
- socket.wait_readable
534
- retry
535
- end
536
-
537
- break if result.bytesize == result_size
538
- end
539
-
540
- # Writing result.
541
- loop do
542
- begin
543
- bytes_written = socket.write_nonblock result
544
- rescue ::IO::WaitWritable
545
- socket.wait_writable
546
- retry
547
- end
548
-
549
- result = result.byteslice bytes_written, result.bytesize - bytes_written
550
- result_size -= bytes_written
551
-
552
- break if result_size.zero?
553
- end
554
-
555
- ensure
556
- socket.close
557
-
558
- # Removing current child thread.
559
- child_lock.synchronize { child_threads.delete ::Thread.current }
560
- end
561
-
562
- # Adding new child thread.
563
- child_lock.synchronize { child_threads.add child_thread }
564
- end
565
- end
566
-
567
- # Processing client.
568
- begin
569
- yield server
570
- ensure
571
- # We need to kill parent thread when client has finished.
572
- # So server won't be able to create new child threads.
573
- # Than we can join all remaining child threads.
574
- parent_thread.kill.join
575
- child_threads.each(&:join)
576
- end
577
- end
578
- end
579
-
580
- protected def nonblock_test(server, text, portion_length, compressor_options = {}, &_block)
581
- port = server.addr[1]
582
- compressed_text = String.compress text, compressor_options
583
-
584
- processor = proc do |decompressor_options|
585
- decompressed_text = ::TCPSocket.open "localhost", port do |socket|
586
- # Writing head.
587
- head = [compressed_text.bytesize, portion_length].pack "QQ"
588
- socket.write head
589
-
590
- # Writing compressed text.
591
- socket.write compressed_text
592
-
593
- instance = target.new socket, decompressor_options
594
-
595
- begin
596
- yield instance, socket
597
- ensure
598
- instance.close
599
- end
600
- end
601
-
602
- # Testing decompressed text.
603
- decompressed_text.force_encoding text.encoding
604
- assert_equal text, decompressed_text
605
- end
606
-
607
- if compressor_options.empty?
608
- processor.call({})
609
- else
610
- get_compatible_decompressor_options compressor_options do |decompressor_options|
611
- processor.call decompressor_options
612
- end
613
- end
614
- end
615
-
616
- # -----
617
-
618
- protected def get_archive(text, compressor_options = {})
619
- String.compress text, compressor_options
620
- end
621
-
622
- protected def write_archive(archive_path, text, compressor_options = {})
623
- compressed_text = String.compress text, compressor_options
624
- ::File.write archive_path, compressed_text, :mode => "wb"
625
- end
626
-
627
- def get_invalid_decompressor_options(&block)
628
- Option.get_invalid_decompressor_options BUFFER_LENGTH_NAMES, &block
629
- end
630
-
631
- def parallel_compressor_options(&block)
632
- Common.parallel_options Option.get_compressor_options_generator(BUFFER_LENGTH_NAMES), &block
633
- end
634
-
635
- def get_compatible_decompressor_options(compressor_options, &block)
636
- Option.get_compatible_decompressor_options compressor_options, BUFFER_LENGTH_MAPPING, &block
637
- end
638
- end
639
-
640
- Minitest << Reader
641
- end
642
- end
643
- end
7
+ Minitest << ADSP::Test::Stream::Reader