omnizip 0.4.7-x86_64-linux
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 +7 -0
- data/.rspec +3 -0
- data/.rubocop.yml +32 -0
- data/.rubocop_todo.yml +293 -0
- data/CHANGELOG.md +1647 -0
- data/CONTEXT.md +68 -0
- data/COPYING +502 -0
- data/Gemfile +19 -0
- data/LICENSE +12 -0
- data/README.adoc +1327 -0
- data/Rakefile +15 -0
- data/TODO.refactor/00-overview.md +67 -0
- data/TODO.refactor/01-registry-base-class.md +81 -0
- data/TODO.refactor/02-error-hierarchy.md +57 -0
- data/TODO.refactor/03-autoload-entry-point.md +69 -0
- data/TODO.refactor/04-filter-base-consolidation.md +49 -0
- data/TODO.refactor/05-send-private-methods.md +64 -0
- data/TODO.refactor/06-instance-variable-access.md +69 -0
- data/TODO.refactor/07-respond-to-replacement.md +237 -0
- data/TODO.refactor/08-spec-doubles.md +27 -0
- data/TODO.refactor/09-cli-shared-module.md +35 -0
- data/TODO.refactor/10-format-detector-ocp.md +34 -0
- data/TODO.refactor/11-convenience-decoupling.md +38 -0
- data/TODO.refactor/12-thread-safety.md +8 -0
- data/TODO.refactor/13-lutaml-model-migration.md +158 -0
- data/TODO.refactor/14-add-missing-specs.md +25 -0
- data/benchmark/README.md +260 -0
- data/benchmark/benchmark_suite.rb +125 -0
- data/benchmark/compression_bench.rb +181 -0
- data/benchmark/filter_bench.rb +180 -0
- data/benchmark/models/benchmark_result.rb +59 -0
- data/benchmark/models/comparison_result.rb +69 -0
- data/benchmark/profile_suite.rb +167 -0
- data/benchmark/reporter.rb +150 -0
- data/benchmark/run_benchmarks.rb +66 -0
- data/benchmark/test_data.rb +137 -0
- data/config/formats/rar3_spec.yml +92 -0
- data/config/formats/rar5_spec.yml +102 -0
- data/docs/.github/workflows/docs.yml +142 -0
- data/docs/.gitignore +21 -0
- data/docs/.lychee.toml +67 -0
- data/docs/Gemfile +13 -0
- data/docs/RAR_WRITE_SUPPORT.md +26 -0
- data/docs/README.md +101 -0
- data/docs/_config.yml +112 -0
- data/docs/assets/logo.svg +1 -0
- data/docs/assets/omnizip-logo.pdf +1540 -11
- data/docs/comparison/feature-matrix.adoc +694 -0
- data/docs/comparison/index.adoc +113 -0
- data/docs/comparison/vs-7zip.adoc +309 -0
- data/docs/comparison/vs-peazip.adoc +77 -0
- data/docs/comparison/vs-rubyzip.adoc +342 -0
- data/docs/comparison/vs-winrar.adoc +100 -0
- data/docs/compatibility.adoc +579 -0
- data/docs/concepts/index.adoc +129 -0
- data/docs/developer/architecture.adoc +256 -0
- data/docs/developer/contributing.adoc +158 -0
- data/docs/developer/index.adoc +25 -0
- data/docs/developer/testing.adoc +212 -0
- data/docs/getting-started/basic-usage.adoc +263 -0
- data/docs/getting-started/index.adoc +42 -0
- data/docs/getting-started/installation.adoc +138 -0
- data/docs/getting-started/quick-start.adoc +183 -0
- data/docs/getting-started/your-first-archive.adoc +219 -0
- data/docs/guides/advanced-features/encryption.adoc +277 -0
- data/docs/guides/advanced-features/index.adoc +59 -0
- data/docs/guides/advanced-features/parallel-processing.adoc +144 -0
- data/docs/guides/advanced-features/progress-tracking.adoc +124 -0
- data/docs/guides/advanced-features/streaming.adoc +142 -0
- data/docs/guides/archive-formats/gzip-format.adoc +105 -0
- data/docs/guides/archive-formats/index.adoc +160 -0
- data/docs/guides/archive-formats/ole-format.adoc +151 -0
- data/docs/guides/archive-formats/rar-format.adoc +104 -0
- data/docs/guides/archive-formats/rar5.adoc +521 -0
- data/docs/guides/archive-formats/rpm-format.adoc +108 -0
- data/docs/guides/archive-formats/seven-zip-format.adoc +35 -0
- data/docs/guides/archive-formats/tar-format.adoc +106 -0
- data/docs/guides/archive-formats/xz-format.adoc +118 -0
- data/docs/guides/archive-formats/zip-format.adoc +35 -0
- data/docs/guides/compression-algorithms/bzip2.adoc +114 -0
- data/docs/guides/compression-algorithms/deflate.adoc +313 -0
- data/docs/guides/compression-algorithms/index.adoc +190 -0
- data/docs/guides/compression-algorithms/lzma.adoc +394 -0
- data/docs/guides/compression-algorithms/lzma2.adoc +244 -0
- data/docs/guides/compression-algorithms/ppmd.adoc +313 -0
- data/docs/guides/compression-algorithms/zstandard.adoc +296 -0
- data/docs/guides/creating-archives.adoc +348 -0
- data/docs/guides/extracting-archives.adoc +53 -0
- data/docs/guides/format-conversion.adoc +64 -0
- data/docs/guides/index.adoc +49 -0
- data/docs/guides/migration-rubyzip.adoc +217 -0
- data/docs/guides/parity-archives.adoc +605 -0
- data/docs/guides/performance-tuning.adoc +88 -0
- data/docs/index.adoc +228 -0
- data/docs/lychee.toml +67 -0
- data/docs/reference/api/overview.adoc +187 -0
- data/docs/reference/cli/compress-command.adoc +114 -0
- data/docs/reference/cli/overview.adoc +140 -0
- data/docs/reference/index.adoc +26 -0
- data/docs/resources/faq.adoc +185 -0
- data/docs/resources/quick-reference.adoc +222 -0
- data/docs/rust-backend.md +0 -0
- data/docs/troubleshooting/index.adoc +207 -0
- data/docs/xar_format.md +216 -0
- data/examples/api_comparison.rb +205 -0
- data/examples/deflate64_example.rb +96 -0
- data/examples/par2_demo.rb +121 -0
- data/examples/quick_start_native.rb +150 -0
- data/examples/quick_start_rubyzip.rb +115 -0
- data/examples/rubyzip_compatibility_demo.rb +194 -0
- data/exe/omnizip +27 -0
- data/lib/omnizip/algorithm.rb +176 -0
- data/lib/omnizip/algorithm_registry.rb +65 -0
- data/lib/omnizip/algorithms/.keep +0 -0
- data/lib/omnizip/algorithms/bzip2/bwt.rb +236 -0
- data/lib/omnizip/algorithms/bzip2/bz2.rb +687 -0
- data/lib/omnizip/algorithms/bzip2/rle.rb +146 -0
- data/lib/omnizip/algorithms/bzip2.rb +108 -0
- data/lib/omnizip/algorithms/deflate/constants.rb +28 -0
- data/lib/omnizip/algorithms/deflate/decoder.rb +37 -0
- data/lib/omnizip/algorithms/deflate/encoder.rb +45 -0
- data/lib/omnizip/algorithms/deflate.rb +135 -0
- data/lib/omnizip/algorithms/deflate64/constants.rb +45 -0
- data/lib/omnizip/algorithms/deflate64/decoder.rb +151 -0
- data/lib/omnizip/algorithms/deflate64/encoder.rb +95 -0
- data/lib/omnizip/algorithms/deflate64/huffman_coder.rb +352 -0
- data/lib/omnizip/algorithms/deflate64/lz77_encoder.rb +140 -0
- data/lib/omnizip/algorithms/deflate64.rb +118 -0
- data/lib/omnizip/algorithms/lzma/bit_model.rb +120 -0
- data/lib/omnizip/algorithms/lzma/constants.rb +112 -0
- data/lib/omnizip/algorithms/lzma/decoder.rb +146 -0
- data/lib/omnizip/algorithms/lzma/dictionary.rb +70 -0
- data/lib/omnizip/algorithms/lzma/distance_coder.rb +326 -0
- data/lib/omnizip/algorithms/lzma/encoder.rb +139 -0
- data/lib/omnizip/algorithms/lzma/length_coder.rb +172 -0
- data/lib/omnizip/algorithms/lzma/literal_decoder.rb +204 -0
- data/lib/omnizip/algorithms/lzma/literal_encoder.rb +208 -0
- data/lib/omnizip/algorithms/lzma/lzip_decoder.rb +368 -0
- data/lib/omnizip/algorithms/lzma/lzma1_encoder.rb +105 -0
- data/lib/omnizip/algorithms/lzma/lzma_alone_decoder.rb +194 -0
- data/lib/omnizip/algorithms/lzma/lzma_state.rb +128 -0
- data/lib/omnizip/algorithms/lzma/match.rb +32 -0
- data/lib/omnizip/algorithms/lzma/match_finder.rb +233 -0
- data/lib/omnizip/algorithms/lzma/match_finder_config.rb +142 -0
- data/lib/omnizip/algorithms/lzma/match_finder_factory.rb +84 -0
- data/lib/omnizip/algorithms/lzma/optimal_encoder.rb +159 -0
- data/lib/omnizip/algorithms/lzma/probability_models.rb +72 -0
- data/lib/omnizip/algorithms/lzma/range_coder.rb +82 -0
- data/lib/omnizip/algorithms/lzma/range_decoder.rb +274 -0
- data/lib/omnizip/algorithms/lzma/range_encoder.rb +202 -0
- data/lib/omnizip/algorithms/lzma/state.rb +127 -0
- data/lib/omnizip/algorithms/lzma/xz_buffered_range_encoder.rb +323 -0
- data/lib/omnizip/algorithms/lzma/xz_encoder.rb +420 -0
- data/lib/omnizip/algorithms/lzma/xz_encoder_fast.rb +640 -0
- data/lib/omnizip/algorithms/lzma/xz_match_finder_adapter.rb +224 -0
- data/lib/omnizip/algorithms/lzma/xz_price_calculator.rb +167 -0
- data/lib/omnizip/algorithms/lzma/xz_probability_models.rb +258 -0
- data/lib/omnizip/algorithms/lzma/xz_range_encoder.rb +223 -0
- data/lib/omnizip/algorithms/lzma/xz_range_encoder_exact.rb +314 -0
- data/lib/omnizip/algorithms/lzma/xz_state.rb +108 -0
- data/lib/omnizip/algorithms/lzma/xz_utils_decoder.rb +1311 -0
- data/lib/omnizip/algorithms/lzma.rb +266 -0
- data/lib/omnizip/algorithms/lzma2/chunk_manager.rb +180 -0
- data/lib/omnizip/algorithms/lzma2/constants.rb +38 -0
- data/lib/omnizip/algorithms/lzma2/encoder.rb +145 -0
- data/lib/omnizip/algorithms/lzma2/lzma2_chunk.rb +165 -0
- data/lib/omnizip/algorithms/lzma2/properties.rb +179 -0
- data/lib/omnizip/algorithms/lzma2/simple_lzma2_encoder.rb +122 -0
- data/lib/omnizip/algorithms/lzma2/xz_encoder_adapter.rb +85 -0
- data/lib/omnizip/algorithms/lzma2.rb +133 -0
- data/lib/omnizip/algorithms/ppmd7/constants.rb +74 -0
- data/lib/omnizip/algorithms/ppmd7/context.rb +151 -0
- data/lib/omnizip/algorithms/ppmd7/decoder.rb +127 -0
- data/lib/omnizip/algorithms/ppmd7/encoder.rb +153 -0
- data/lib/omnizip/algorithms/ppmd7/model.rb +245 -0
- data/lib/omnizip/algorithms/ppmd7/symbol_state.rb +57 -0
- data/lib/omnizip/algorithms/ppmd7.rb +146 -0
- data/lib/omnizip/algorithms/ppmd8/constants.rb +61 -0
- data/lib/omnizip/algorithms/ppmd8/context.rb +32 -0
- data/lib/omnizip/algorithms/ppmd8/decoder.rb +104 -0
- data/lib/omnizip/algorithms/ppmd8/encoder.rb +135 -0
- data/lib/omnizip/algorithms/ppmd8/model.rb +246 -0
- data/lib/omnizip/algorithms/ppmd8/restoration_method.rb +78 -0
- data/lib/omnizip/algorithms/ppmd8.rb +122 -0
- data/lib/omnizip/algorithms/ppmd_base.rb +142 -0
- data/lib/omnizip/algorithms/registration.rb +28 -0
- data/lib/omnizip/algorithms/zstandard/constants.rb +158 -0
- data/lib/omnizip/algorithms/zstandard/decoder.rb +249 -0
- data/lib/omnizip/algorithms/zstandard/dictionary.rb +73 -0
- data/lib/omnizip/algorithms/zstandard/encoder.rb +294 -0
- data/lib/omnizip/algorithms/zstandard/frame/block.rb +143 -0
- data/lib/omnizip/algorithms/zstandard/frame/header.rb +233 -0
- data/lib/omnizip/algorithms/zstandard/frame.rb +33 -0
- data/lib/omnizip/algorithms/zstandard/fse/bitstream.rb +183 -0
- data/lib/omnizip/algorithms/zstandard/fse/encoder.rb +534 -0
- data/lib/omnizip/algorithms/zstandard/fse/interleaved.rb +92 -0
- data/lib/omnizip/algorithms/zstandard/fse/table.rb +188 -0
- data/lib/omnizip/algorithms/zstandard/fse/table_description.rb +203 -0
- data/lib/omnizip/algorithms/zstandard/fse.rb +53 -0
- data/lib/omnizip/algorithms/zstandard/huffman.rb +276 -0
- data/lib/omnizip/algorithms/zstandard/huffman_encoder.rb +327 -0
- data/lib/omnizip/algorithms/zstandard/ldm.rb +121 -0
- data/lib/omnizip/algorithms/zstandard/literals.rb +241 -0
- data/lib/omnizip/algorithms/zstandard/literals_encoder.rb +96 -0
- data/lib/omnizip/algorithms/zstandard/match_finder.rb +483 -0
- data/lib/omnizip/algorithms/zstandard/sequences.rb +350 -0
- data/lib/omnizip/algorithms/zstandard/sequences_encoder.rb +333 -0
- data/lib/omnizip/algorithms/zstandard/xxhash.rb +159 -0
- data/lib/omnizip/algorithms/zstandard.rb +210 -0
- data/lib/omnizip/algorithms.rb +35 -0
- data/lib/omnizip/archive/builder.rb +48 -0
- data/lib/omnizip/archive/reader_session.rb +67 -0
- data/lib/omnizip/archive.rb +86 -0
- data/lib/omnizip/archive_handler.rb +82 -0
- data/lib/omnizip/archive_handlers/cpio_handler.rb +47 -0
- data/lib/omnizip/archive_handlers/iso_handler.rb +54 -0
- data/lib/omnizip/archive_handlers/ole_handler.rb +37 -0
- data/lib/omnizip/archive_handlers/rar_handler.rb +96 -0
- data/lib/omnizip/archive_handlers/rpm_handler.rb +45 -0
- data/lib/omnizip/archive_handlers/seven_zip_handler.rb +89 -0
- data/lib/omnizip/archive_handlers/tar_handler.rb +75 -0
- data/lib/omnizip/archive_handlers/xar_handler.rb +49 -0
- data/lib/omnizip/archive_handlers/zip_handler.rb +115 -0
- data/lib/omnizip/archive_handlers.rb +18 -0
- data/lib/omnizip/backends.rb +160 -0
- data/lib/omnizip/buffer/memory_archive.rb +246 -0
- data/lib/omnizip/buffer/memory_extractor.rb +234 -0
- data/lib/omnizip/buffer/seven_zip_bridge.rb +171 -0
- data/lib/omnizip/buffer.rb +187 -0
- data/lib/omnizip/checksum_registry.rb +41 -0
- data/lib/omnizip/checksums/crc32.rb +101 -0
- data/lib/omnizip/checksums/crc64.rb +102 -0
- data/lib/omnizip/checksums/crc_base.rb +158 -0
- data/lib/omnizip/checksums/registration.rb +16 -0
- data/lib/omnizip/checksums/verifier.rb +130 -0
- data/lib/omnizip/checksums.rb +11 -0
- data/lib/omnizip/chunked/memory_manager.rb +194 -0
- data/lib/omnizip/chunked/reader.rb +78 -0
- data/lib/omnizip/chunked/writer.rb +123 -0
- data/lib/omnizip/chunked.rb +123 -0
- data/lib/omnizip/cli/output_formatter.rb +112 -0
- data/lib/omnizip/cli.rb +604 -0
- data/lib/omnizip/commands/.keep +0 -0
- data/lib/omnizip/commands/archive_create_command.rb +245 -0
- data/lib/omnizip/commands/archive_extract_command.rb +231 -0
- data/lib/omnizip/commands/archive_list_command.rb +204 -0
- data/lib/omnizip/commands/archive_repair_command.rb +129 -0
- data/lib/omnizip/commands/archive_verify_command.rb +115 -0
- data/lib/omnizip/commands/compress_command.rb +115 -0
- data/lib/omnizip/commands/decompress_command.rb +149 -0
- data/lib/omnizip/commands/list_command.rb +51 -0
- data/lib/omnizip/commands/metadata_command.rb +215 -0
- data/lib/omnizip/commands/parity_create_command.rb +114 -0
- data/lib/omnizip/commands/parity_repair_command.rb +120 -0
- data/lib/omnizip/commands/parity_verify_command.rb +122 -0
- data/lib/omnizip/commands/profile_list_command.rb +54 -0
- data/lib/omnizip/commands/profile_show_command.rb +44 -0
- data/lib/omnizip/commands.rb +21 -0
- data/lib/omnizip/convenience.rb +389 -0
- data/lib/omnizip/converter/conversion_registry.rb +50 -0
- data/lib/omnizip/converter/conversion_strategy.rb +108 -0
- data/lib/omnizip/converter/extract_repack_strategy.rb +51 -0
- data/lib/omnizip/converter/seven_zip_to_zip_strategy.rb +43 -0
- data/lib/omnizip/converter/zip_to_seven_zip_strategy.rb +54 -0
- data/lib/omnizip/converter.rb +124 -0
- data/lib/omnizip/crypto/aes256/cipher.rb +104 -0
- data/lib/omnizip/crypto/aes256/constants.rb +28 -0
- data/lib/omnizip/crypto/aes256/key_derivation.rb +100 -0
- data/lib/omnizip/crypto/aes256.rb +102 -0
- data/lib/omnizip/crypto.rb +11 -0
- data/lib/omnizip/entry.rb +44 -0
- data/lib/omnizip/error.rb +110 -0
- data/lib/omnizip/eta/exponential_smoothing_estimator.rb +95 -0
- data/lib/omnizip/eta/moving_average_estimator.rb +96 -0
- data/lib/omnizip/eta/rate_calculator.rb +104 -0
- data/lib/omnizip/eta/sample_history.rb +143 -0
- data/lib/omnizip/eta/time_estimator.rb +106 -0
- data/lib/omnizip/eta.rb +68 -0
- data/lib/omnizip/extraction/filter_chain.rb +179 -0
- data/lib/omnizip/extraction/glob_pattern.rb +140 -0
- data/lib/omnizip/extraction/pattern_matcher.rb +66 -0
- data/lib/omnizip/extraction/predicate_pattern.rb +52 -0
- data/lib/omnizip/extraction/regex_pattern.rb +50 -0
- data/lib/omnizip/extraction/selective_extractor.rb +247 -0
- data/lib/omnizip/extraction.rb +115 -0
- data/lib/omnizip/file_type/mime_classifier.rb +144 -0
- data/lib/omnizip/file_type.rb +117 -0
- data/lib/omnizip/filter.rb +141 -0
- data/lib/omnizip/filter_pipeline.rb +108 -0
- data/lib/omnizip/filter_registry.rb +113 -0
- data/lib/omnizip/filters/bcj.rb +277 -0
- data/lib/omnizip/filters/bcj2/constants.rb +53 -0
- data/lib/omnizip/filters/bcj2/decoder.rb +263 -0
- data/lib/omnizip/filters/bcj2/encoder.rb +58 -0
- data/lib/omnizip/filters/bcj2/stream_data.rb +91 -0
- data/lib/omnizip/filters/bcj2.rb +93 -0
- data/lib/omnizip/filters/bcj_arm.rb +174 -0
- data/lib/omnizip/filters/bcj_arm64.rb +242 -0
- data/lib/omnizip/filters/bcj_ia64.rb +194 -0
- data/lib/omnizip/filters/bcj_ppc.rb +188 -0
- data/lib/omnizip/filters/bcj_sparc.rb +174 -0
- data/lib/omnizip/filters/bcj_x86.rb +191 -0
- data/lib/omnizip/filters/delta.rb +195 -0
- data/lib/omnizip/filters/xz_delta.rb +258 -0
- data/lib/omnizip/filters.rb +20 -0
- data/lib/omnizip/format_detector.rb +166 -0
- data/lib/omnizip/formats/.keep +0 -0
- data/lib/omnizip/formats/bzip2_file.rb +159 -0
- data/lib/omnizip/formats/cpio/bounded_io.rb +66 -0
- data/lib/omnizip/formats/cpio/constants.rb +55 -0
- data/lib/omnizip/formats/cpio/entry.rb +389 -0
- data/lib/omnizip/formats/cpio/reader.rb +194 -0
- data/lib/omnizip/formats/cpio/writer.rb +232 -0
- data/lib/omnizip/formats/cpio.rb +132 -0
- data/lib/omnizip/formats/format_spec_loader.rb +228 -0
- data/lib/omnizip/formats/gzip.rb +236 -0
- data/lib/omnizip/formats/iso/directory_builder.rb +321 -0
- data/lib/omnizip/formats/iso/directory_record.rb +162 -0
- data/lib/omnizip/formats/iso/joliet.rb +204 -0
- data/lib/omnizip/formats/iso/path_table.rb +125 -0
- data/lib/omnizip/formats/iso/reader.rb +194 -0
- data/lib/omnizip/formats/iso/rock_ridge.rb +349 -0
- data/lib/omnizip/formats/iso/volume_builder.rb +319 -0
- data/lib/omnizip/formats/iso/volume_descriptor.rb +168 -0
- data/lib/omnizip/formats/iso/writer.rb +543 -0
- data/lib/omnizip/formats/iso.rb +133 -0
- data/lib/omnizip/formats/lzip.rb +161 -0
- data/lib/omnizip/formats/lzma_alone.rb +149 -0
- data/lib/omnizip/formats/msi/cab_extractor.rb +181 -0
- data/lib/omnizip/formats/msi/constants.rb +157 -0
- data/lib/omnizip/formats/msi/directory_resolver.rb +188 -0
- data/lib/omnizip/formats/msi/entry.rb +134 -0
- data/lib/omnizip/formats/msi/reader.rb +301 -0
- data/lib/omnizip/formats/msi/string_pool.rb +246 -0
- data/lib/omnizip/formats/msi/table_parser.rb +244 -0
- data/lib/omnizip/formats/msi.rb +73 -0
- data/lib/omnizip/formats/ole/allocation_table.rb +263 -0
- data/lib/omnizip/formats/ole/constants.rb +61 -0
- data/lib/omnizip/formats/ole/dirent.rb +439 -0
- data/lib/omnizip/formats/ole/header.rb +199 -0
- data/lib/omnizip/formats/ole/ranges_io.rb +347 -0
- data/lib/omnizip/formats/ole/storage.rb +482 -0
- data/lib/omnizip/formats/ole/types/variant.rb +338 -0
- data/lib/omnizip/formats/ole.rb +143 -0
- data/lib/omnizip/formats/rar/archive_repairer.rb +240 -0
- data/lib/omnizip/formats/rar/archive_verifier.rb +192 -0
- data/lib/omnizip/formats/rar/block_parser.rb +282 -0
- data/lib/omnizip/formats/rar/compression/bit_stream.rb +180 -0
- data/lib/omnizip/formats/rar/compression/dispatcher.rb +210 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman/decoder.rb +212 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman/encoder.rb +154 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman/huffman_builder.rb +217 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman/huffman_coder.rb +189 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman/match_finder.rb +135 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman/sliding_window.rb +165 -0
- data/lib/omnizip/formats/rar/compression/lz77_huffman.rb +25 -0
- data/lib/omnizip/formats/rar/compression/ppmd/context.rb +103 -0
- data/lib/omnizip/formats/rar/compression/ppmd/decoder.rb +238 -0
- data/lib/omnizip/formats/rar/compression/ppmd/encoder.rb +250 -0
- data/lib/omnizip/formats/rar/compression/ppmd.rb +16 -0
- data/lib/omnizip/formats/rar/compression.rb +17 -0
- data/lib/omnizip/formats/rar/compression_method_registry.rb +106 -0
- data/lib/omnizip/formats/rar/constants.rb +88 -0
- data/lib/omnizip/formats/rar/decompressor.rb +316 -0
- data/lib/omnizip/formats/rar/external_writer.rb +311 -0
- data/lib/omnizip/formats/rar/header.rb +209 -0
- data/lib/omnizip/formats/rar/license_validator.rb +111 -0
- data/lib/omnizip/formats/rar/models/rar_archive.rb +77 -0
- data/lib/omnizip/formats/rar/models/rar_entry.rb +65 -0
- data/lib/omnizip/formats/rar/models/rar_volume.rb +56 -0
- data/lib/omnizip/formats/rar/models.rb +14 -0
- data/lib/omnizip/formats/rar/parity_handler.rb +299 -0
- data/lib/omnizip/formats/rar/rar5/compression/lzma.rb +200 -0
- data/lib/omnizip/formats/rar/rar5/compression/lzss.rb +584 -0
- data/lib/omnizip/formats/rar/rar5/compression/store.rb +60 -0
- data/lib/omnizip/formats/rar/rar5/crc32.rb +39 -0
- data/lib/omnizip/formats/rar/rar5/encryption/aes256_cbc.rb +96 -0
- data/lib/omnizip/formats/rar/rar5/encryption/encryption_header.rb +114 -0
- data/lib/omnizip/formats/rar/rar5/encryption/encryption_manager.rb +162 -0
- data/lib/omnizip/formats/rar/rar5/encryption/key_derivation.rb +97 -0
- data/lib/omnizip/formats/rar/rar5/header.rb +208 -0
- data/lib/omnizip/formats/rar/rar5/models/encryption_options.rb +74 -0
- data/lib/omnizip/formats/rar/rar5/models/recovery_options.rb +63 -0
- data/lib/omnizip/formats/rar/rar5/models/solid_options.rb +63 -0
- data/lib/omnizip/formats/rar/rar5/models/volume_options.rb +74 -0
- data/lib/omnizip/formats/rar/rar5/multi_volume/ARCHITECTURE.md +290 -0
- data/lib/omnizip/formats/rar/rar5/multi_volume/volume_manager.rb +260 -0
- data/lib/omnizip/formats/rar/rar5/multi_volume/volume_splitter.rb +155 -0
- data/lib/omnizip/formats/rar/rar5/multi_volume/volume_writer.rb +176 -0
- data/lib/omnizip/formats/rar/rar5/solid/solid_encoder.rb +108 -0
- data/lib/omnizip/formats/rar/rar5/solid/solid_manager.rb +139 -0
- data/lib/omnizip/formats/rar/rar5/solid/solid_stream.rb +121 -0
- data/lib/omnizip/formats/rar/rar5/vint.rb +53 -0
- data/lib/omnizip/formats/rar/rar5/writer.rb +540 -0
- data/lib/omnizip/formats/rar/rar_format_base.rb +239 -0
- data/lib/omnizip/formats/rar/reader.rb +377 -0
- data/lib/omnizip/formats/rar/recovery_record.rb +245 -0
- data/lib/omnizip/formats/rar/volume_manager.rb +166 -0
- data/lib/omnizip/formats/rar/writer.rb +437 -0
- data/lib/omnizip/formats/rar.rb +193 -0
- data/lib/omnizip/formats/rar3/compressor.rb +71 -0
- data/lib/omnizip/formats/rar3/decompressor.rb +64 -0
- data/lib/omnizip/formats/rar3/reader.rb +107 -0
- data/lib/omnizip/formats/rar3/writer.rb +220 -0
- data/lib/omnizip/formats/rar3.rb +15 -0
- data/lib/omnizip/formats/rar5/compressor.rb +71 -0
- data/lib/omnizip/formats/rar5/decompressor.rb +64 -0
- data/lib/omnizip/formats/rar5/reader.rb +130 -0
- data/lib/omnizip/formats/rar5/writer.rb +65 -0
- data/lib/omnizip/formats/rar5.rb +15 -0
- data/lib/omnizip/formats/rpm/constants.rb +58 -0
- data/lib/omnizip/formats/rpm/entry.rb +106 -0
- data/lib/omnizip/formats/rpm/header.rb +106 -0
- data/lib/omnizip/formats/rpm/lead.rb +132 -0
- data/lib/omnizip/formats/rpm/tag.rb +228 -0
- data/lib/omnizip/formats/rpm/writer.rb +652 -0
- data/lib/omnizip/formats/rpm.rb +458 -0
- data/lib/omnizip/formats/seven_zip/bcj2_stream_decompressor.rb +274 -0
- data/lib/omnizip/formats/seven_zip/coder_chain.rb +169 -0
- data/lib/omnizip/formats/seven_zip/constants.rb +126 -0
- data/lib/omnizip/formats/seven_zip/encoded_header.rb +110 -0
- data/lib/omnizip/formats/seven_zip/encrypted_header.rb +139 -0
- data/lib/omnizip/formats/seven_zip/file_collector.rb +143 -0
- data/lib/omnizip/formats/seven_zip/header.rb +102 -0
- data/lib/omnizip/formats/seven_zip/header_encryptor.rb +132 -0
- data/lib/omnizip/formats/seven_zip/header_writer.rb +425 -0
- data/lib/omnizip/formats/seven_zip/models/coder_info.rb +30 -0
- data/lib/omnizip/formats/seven_zip/models/file_entry.rb +65 -0
- data/lib/omnizip/formats/seven_zip/models/folder.rb +67 -0
- data/lib/omnizip/formats/seven_zip/models/stream_info.rb +42 -0
- data/lib/omnizip/formats/seven_zip/models.rb +20 -0
- data/lib/omnizip/formats/seven_zip/parser.rb +671 -0
- data/lib/omnizip/formats/seven_zip/reader.rb +626 -0
- data/lib/omnizip/formats/seven_zip/split_archive_reader.rb +611 -0
- data/lib/omnizip/formats/seven_zip/split_archive_writer.rb +308 -0
- data/lib/omnizip/formats/seven_zip/stream_compressor.rb +151 -0
- data/lib/omnizip/formats/seven_zip/stream_decompressor.rb +166 -0
- data/lib/omnizip/formats/seven_zip/writer.rb +801 -0
- data/lib/omnizip/formats/seven_zip.rb +179 -0
- data/lib/omnizip/formats/tar/constants.rb +73 -0
- data/lib/omnizip/formats/tar/entry.rb +98 -0
- data/lib/omnizip/formats/tar/header.rb +206 -0
- data/lib/omnizip/formats/tar/reader.rb +119 -0
- data/lib/omnizip/formats/tar/writer.rb +212 -0
- data/lib/omnizip/formats/tar.rb +74 -0
- data/lib/omnizip/formats/xar/constants.rb +119 -0
- data/lib/omnizip/formats/xar/entry.rb +268 -0
- data/lib/omnizip/formats/xar/header.rb +223 -0
- data/lib/omnizip/formats/xar/reader.rb +400 -0
- data/lib/omnizip/formats/xar/toc.rb +570 -0
- data/lib/omnizip/formats/xar/writer.rb +461 -0
- data/lib/omnizip/formats/xar.rb +145 -0
- data/lib/omnizip/formats/xz/reader.rb +121 -0
- data/lib/omnizip/formats/xz/writer.rb +416 -0
- data/lib/omnizip/formats/xz.rb +210 -0
- data/lib/omnizip/formats/xz_const.rb +49 -0
- data/lib/omnizip/formats/xz_impl/block_decoder.rb +761 -0
- data/lib/omnizip/formats/xz_impl/block_encoder.rb +304 -0
- data/lib/omnizip/formats/xz_impl/block_header.rb +210 -0
- data/lib/omnizip/formats/xz_impl/block_header_parser.rb +182 -0
- data/lib/omnizip/formats/xz_impl/index_decoder.rb +174 -0
- data/lib/omnizip/formats/xz_impl/index_encoder.rb +120 -0
- data/lib/omnizip/formats/xz_impl/stream_decoder.rb +470 -0
- data/lib/omnizip/formats/xz_impl/stream_encoder.rb +95 -0
- data/lib/omnizip/formats/xz_impl/stream_footer.rb +79 -0
- data/lib/omnizip/formats/xz_impl/stream_footer_parser.rb +115 -0
- data/lib/omnizip/formats/xz_impl/stream_header.rb +53 -0
- data/lib/omnizip/formats/xz_impl/stream_header_parser.rb +106 -0
- data/lib/omnizip/formats/xz_impl/vli.rb +128 -0
- data/lib/omnizip/formats/xz_impl.rb +52 -0
- data/lib/omnizip/formats/zip/central_directory_header.rb +223 -0
- data/lib/omnizip/formats/zip/constants.rb +69 -0
- data/lib/omnizip/formats/zip/end_of_central_directory.rb +132 -0
- data/lib/omnizip/formats/zip/local_file_header.rb +136 -0
- data/lib/omnizip/formats/zip/reader.rb +376 -0
- data/lib/omnizip/formats/zip/unix_extra_field.rb +153 -0
- data/lib/omnizip/formats/zip/writer.rb +489 -0
- data/lib/omnizip/formats/zip/zip64_end_of_central_directory.rb +102 -0
- data/lib/omnizip/formats/zip/zip64_end_of_central_directory_locator.rb +64 -0
- data/lib/omnizip/formats/zip/zip64_extra_field.rb +112 -0
- data/lib/omnizip/formats/zip.rb +50 -0
- data/lib/omnizip/formats.rb +29 -0
- data/lib/omnizip/implementations/base/lzma2_decoder_base.rb +75 -0
- data/lib/omnizip/implementations/base/lzma2_encoder_base.rb +128 -0
- data/lib/omnizip/implementations/base/lzma_decoder_base.rb +83 -0
- data/lib/omnizip/implementations/base/lzma_encoder_base.rb +108 -0
- data/lib/omnizip/implementations/base/state_machine_base.rb +182 -0
- data/lib/omnizip/implementations/base.rb +19 -0
- data/lib/omnizip/implementations/rust/archive.rb +93 -0
- data/lib/omnizip/implementations/rust/library.rb +221 -0
- data/lib/omnizip/implementations/rust.rb +26 -0
- data/lib/omnizip/implementations/seven_zip/lzma/decoder.rb +428 -0
- data/lib/omnizip/implementations/seven_zip/lzma/encoder.rb +456 -0
- data/lib/omnizip/implementations/seven_zip/lzma/match_finder.rb +285 -0
- data/lib/omnizip/implementations/seven_zip/lzma/range_decoder.rb +197 -0
- data/lib/omnizip/implementations/seven_zip/lzma/range_encoder.rb +194 -0
- data/lib/omnizip/implementations/seven_zip/lzma/state_machine.rb +139 -0
- data/lib/omnizip/implementations/seven_zip/lzma.rb +21 -0
- data/lib/omnizip/implementations/seven_zip/lzma2/encoder.rb +56 -0
- data/lib/omnizip/implementations/seven_zip/lzma2.rb +12 -0
- data/lib/omnizip/implementations/seven_zip.rb +11 -0
- data/lib/omnizip/implementations/xz_utils/lzma2/decoder.rb +547 -0
- data/lib/omnizip/implementations/xz_utils/lzma2/encoder.rb +748 -0
- data/lib/omnizip/implementations/xz_utils/lzma2.rb +13 -0
- data/lib/omnizip/implementations/xz_utils.rb +10 -0
- data/lib/omnizip/implementations.rb +25 -0
- data/lib/omnizip/io/buffered_input.rb +147 -0
- data/lib/omnizip/io/buffered_output.rb +106 -0
- data/lib/omnizip/io/source.rb +143 -0
- data/lib/omnizip/io/stream_manager.rb +117 -0
- data/lib/omnizip/io.rb +15 -0
- data/lib/omnizip/link_handler/hard_link.rb +79 -0
- data/lib/omnizip/link_handler/symbolic_link.rb +74 -0
- data/lib/omnizip/link_handler.rb +129 -0
- data/lib/omnizip/metadata/archive_metadata.rb +114 -0
- data/lib/omnizip/metadata/entry_metadata.rb +153 -0
- data/lib/omnizip/metadata/metadata_editor.rb +169 -0
- data/lib/omnizip/metadata/metadata_registry.rb +71 -0
- data/lib/omnizip/metadata/metadata_validator.rb +101 -0
- data/lib/omnizip/metadata.rb +58 -0
- data/lib/omnizip/models/.keep +0 -0
- data/lib/omnizip/models/algorithm_metadata.rb +41 -0
- data/lib/omnizip/models/attribute_apply.rb +40 -0
- data/lib/omnizip/models/compression_options.rb +53 -0
- data/lib/omnizip/models/conversion_options.rb +79 -0
- data/lib/omnizip/models/conversion_result.rb +141 -0
- data/lib/omnizip/models/eta_result.rb +45 -0
- data/lib/omnizip/models/extraction_rule.rb +115 -0
- data/lib/omnizip/models/filter_chain.rb +142 -0
- data/lib/omnizip/models/filter_config.rb +148 -0
- data/lib/omnizip/models/match_result.rb +141 -0
- data/lib/omnizip/models/optimization_suggestion.rb +95 -0
- data/lib/omnizip/models/parallel_options.rb +116 -0
- data/lib/omnizip/models/performance_result.rb +85 -0
- data/lib/omnizip/models/profile_report.rb +116 -0
- data/lib/omnizip/models/progress_options.rb +39 -0
- data/lib/omnizip/models/split_options.rb +116 -0
- data/lib/omnizip/optimization_registry.rb +45 -0
- data/lib/omnizip/parallel/engine.rb +52 -0
- data/lib/omnizip/parallel/job_queue.rb +209 -0
- data/lib/omnizip/parallel/job_scheduler.rb +225 -0
- data/lib/omnizip/parallel/parallel_compressor.rb +326 -0
- data/lib/omnizip/parallel/parallel_extractor.rb +238 -0
- data/lib/omnizip/parallel/thread_pool.rb +60 -0
- data/lib/omnizip/parallel/worker_pool.rb +227 -0
- data/lib/omnizip/parallel.rb +156 -0
- data/lib/omnizip/parity/chunked_block_processor.rb +194 -0
- data/lib/omnizip/parity/galois16.rb +145 -0
- data/lib/omnizip/parity/models/creator_packet.rb +71 -0
- data/lib/omnizip/parity/models/file_description_packet.rb +131 -0
- data/lib/omnizip/parity/models/ifsc_packet.rb +111 -0
- data/lib/omnizip/parity/models/main_packet.rb +126 -0
- data/lib/omnizip/parity/models/packet.rb +156 -0
- data/lib/omnizip/parity/models/packet_registry.rb +102 -0
- data/lib/omnizip/parity/models/recovery_slice_packet.rb +76 -0
- data/lib/omnizip/parity/models.rb +27 -0
- data/lib/omnizip/parity/par2_creator.rb +496 -0
- data/lib/omnizip/parity/par2_repairer.rb +409 -0
- data/lib/omnizip/parity/par2_verifier.rb +373 -0
- data/lib/omnizip/parity/par2cmdline_algorithm.rb +108 -0
- data/lib/omnizip/parity/par2cmdline_coefficients.rb +78 -0
- data/lib/omnizip/parity/reed_solomon_decoder.rb +263 -0
- data/lib/omnizip/parity/reed_solomon_encoder.rb +108 -0
- data/lib/omnizip/parity/reed_solomon_matrix.rb +339 -0
- data/lib/omnizip/parity.rb +207 -0
- data/lib/omnizip/password/encryption_registry.rb +26 -0
- data/lib/omnizip/password/encryption_strategy.rb +96 -0
- data/lib/omnizip/password/password_validator.rb +129 -0
- data/lib/omnizip/password/winzip_aes_strategy.rb +190 -0
- data/lib/omnizip/password/zip_crypto_strategy.rb +135 -0
- data/lib/omnizip/password.rb +88 -0
- data/lib/omnizip/pipe/stream_compressor.rb +124 -0
- data/lib/omnizip/pipe/stream_decompressor.rb +173 -0
- data/lib/omnizip/pipe.rb +120 -0
- data/lib/omnizip/platform/ntfs_streams.rb +200 -0
- data/lib/omnizip/platform.rb +189 -0
- data/lib/omnizip/profile/archive_profile.rb +36 -0
- data/lib/omnizip/profile/balanced_profile.rb +31 -0
- data/lib/omnizip/profile/binary_profile.rb +33 -0
- data/lib/omnizip/profile/compression_profile.rb +157 -0
- data/lib/omnizip/profile/custom_profile.rb +155 -0
- data/lib/omnizip/profile/fast_profile.rb +31 -0
- data/lib/omnizip/profile/maximum_profile.rb +31 -0
- data/lib/omnizip/profile/profile_detector.rb +108 -0
- data/lib/omnizip/profile/profile_registry.rb +160 -0
- data/lib/omnizip/profile/text_profile.rb +33 -0
- data/lib/omnizip/profile.rb +261 -0
- data/lib/omnizip/profiler/memory_profiler.rb +66 -0
- data/lib/omnizip/profiler/method_profiler.rb +49 -0
- data/lib/omnizip/profiler/report_generator.rb +158 -0
- data/lib/omnizip/profiler.rb +192 -0
- data/lib/omnizip/progress/callback_reporter.rb +34 -0
- data/lib/omnizip/progress/console_reporter.rb +59 -0
- data/lib/omnizip/progress/log_reporter.rb +89 -0
- data/lib/omnizip/progress/operation_progress.rb +118 -0
- data/lib/omnizip/progress/progress_bar.rb +156 -0
- data/lib/omnizip/progress/progress_reporter.rb +40 -0
- data/lib/omnizip/progress/progress_tracker.rb +215 -0
- data/lib/omnizip/progress/silent_reporter.rb +22 -0
- data/lib/omnizip/progress.rb +131 -0
- data/lib/omnizip/registry.rb +111 -0
- data/lib/omnizip/rubyzip_compat.rb +61 -0
- data/lib/omnizip/temp/safe_extract.rb +124 -0
- data/lib/omnizip/temp/temp_file.rb +123 -0
- data/lib/omnizip/temp/temp_file_pool.rb +109 -0
- data/lib/omnizip/temp.rb +184 -0
- data/lib/omnizip/version.rb +5 -0
- data/lib/omnizip/zip/entry.rb +160 -0
- data/lib/omnizip/zip/file.rb +485 -0
- data/lib/omnizip/zip/input_stream.rb +270 -0
- data/lib/omnizip/zip/output_stream.rb +320 -0
- data/lib/omnizip/zip.rb +23 -0
- data/lib/omnizip.rb +157 -0
- data/lib/tasks/msi_test_files.rake +66 -0
- data/lib/tasks/platform_gems.rake +147 -0
- data/lib/tasks/rust_backend.rake +48 -0
- data/readme-docs/advanced-features.adoc +514 -0
- data/readme-docs/api-usage.adoc +445 -0
- data/readme-docs/architecture.adoc +450 -0
- data/readme-docs/archive-formats.adoc +479 -0
- data/readme-docs/cli-usage.adoc +222 -0
- data/readme-docs/compression-algorithms.adoc +446 -0
- data/readme-docs/compression-profiles.adoc +247 -0
- data/readme-docs/encryption-checksums.adoc +328 -0
- data/readme-docs/format-converter.adoc +316 -0
- data/readme-docs/installation.adoc +228 -0
- data/readme-docs/par2-archives.adoc +608 -0
- data/readme-docs/performance-profiler.adoc +389 -0
- data/readme-docs/preprocessing-filters.adoc +280 -0
- data/vendor/libomnizip_ffi.so +0 -0
- data/xz-file-format-1.2.1.txt +1174 -0
- metadata +768 -0
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Omnizip
|
|
4
|
+
module Metadata
|
|
5
|
+
# Validates metadata changes before applying
|
|
6
|
+
class MetadataValidator
|
|
7
|
+
# Validate entry metadata
|
|
8
|
+
# @param metadata [EntryMetadata] Metadata to validate
|
|
9
|
+
# @raise [ArgumentError] If metadata is invalid
|
|
10
|
+
def validate_entry(metadata)
|
|
11
|
+
validate_comment(metadata.comment) if metadata.comment
|
|
12
|
+
# validate_entry is public API.
|
|
13
|
+
# allowed: metadata need only expose what it validates
|
|
14
|
+
validate_time(metadata.mtime) if metadata.respond_to?(:mtime)
|
|
15
|
+
validate_permissions(metadata.unix_permissions) if metadata.unix_permissions
|
|
16
|
+
|
|
17
|
+
true
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
# Validate archive metadata
|
|
21
|
+
# @param metadata [ArchiveMetadata] Metadata to validate
|
|
22
|
+
# @raise [ArgumentError] If metadata is invalid
|
|
23
|
+
def validate_archive(metadata)
|
|
24
|
+
validate_comment(metadata.comment) if metadata.comment
|
|
25
|
+
|
|
26
|
+
true
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
# Validate comment length
|
|
30
|
+
# @param comment [String] Comment to validate
|
|
31
|
+
# @raise [ArgumentError] If comment is too long
|
|
32
|
+
def validate_comment(comment)
|
|
33
|
+
max_length = 65_535 # ZIP format limit
|
|
34
|
+
return true if comment.bytesize <= max_length
|
|
35
|
+
|
|
36
|
+
raise ArgumentError,
|
|
37
|
+
"Comment too long: #{comment.bytesize} bytes (max: #{max_length})"
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
# Validate time value
|
|
41
|
+
# @param time [Time] Time to validate
|
|
42
|
+
# @raise [ArgumentError] If time is invalid
|
|
43
|
+
def validate_time(time)
|
|
44
|
+
return true unless time
|
|
45
|
+
|
|
46
|
+
unless time.is_a?(Time)
|
|
47
|
+
raise ArgumentError, "Time must be a Time object, got #{time.class}"
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
# DOS time range: 1980-01-01 to 2107-12-31
|
|
51
|
+
min_time = Time.new(1980, 1, 1)
|
|
52
|
+
max_time = Time.new(2107, 12, 31, 23, 59, 59)
|
|
53
|
+
|
|
54
|
+
if time < min_time || time > max_time
|
|
55
|
+
raise ArgumentError, "Time out of DOS range (1980-2107): #{time}"
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
true
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
# Validate Unix permissions
|
|
62
|
+
# @param perms [Integer] Permissions to validate
|
|
63
|
+
# @raise [ArgumentError] If permissions are invalid
|
|
64
|
+
def validate_permissions(perms)
|
|
65
|
+
return true unless perms
|
|
66
|
+
|
|
67
|
+
unless perms.is_a?(Integer)
|
|
68
|
+
raise ArgumentError,
|
|
69
|
+
"Permissions must be an integer, got #{perms.class}"
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
unless (0..0o777).cover?(perms)
|
|
73
|
+
raise ArgumentError,
|
|
74
|
+
"Permissions out of range: 0#{perms.to_s(8)} (max: 0777)"
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
true
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
# Validate filename
|
|
81
|
+
# @param filename [String] Filename to validate
|
|
82
|
+
# @raise [ArgumentError] If filename is invalid
|
|
83
|
+
def validate_filename(filename)
|
|
84
|
+
return true unless filename
|
|
85
|
+
|
|
86
|
+
max_length = 65_535 # ZIP format limit
|
|
87
|
+
if filename.bytesize > max_length
|
|
88
|
+
raise ArgumentError,
|
|
89
|
+
"Filename too long: #{filename.bytesize} bytes (max: #{max_length})"
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
# Check for invalid characters
|
|
93
|
+
if filename.include?("\x00")
|
|
94
|
+
raise ArgumentError, "Filename contains null character"
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
true
|
|
98
|
+
end
|
|
99
|
+
end
|
|
100
|
+
end
|
|
101
|
+
end
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Omnizip
|
|
4
|
+
# Metadata editing module
|
|
5
|
+
# Provides in-place metadata modification without recompression
|
|
6
|
+
module Metadata
|
|
7
|
+
# Nested classes - autoloaded
|
|
8
|
+
autoload :EntryMetadata, "omnizip/metadata/entry_metadata"
|
|
9
|
+
autoload :ArchiveMetadata, "omnizip/metadata/archive_metadata"
|
|
10
|
+
autoload :MetadataValidator, "omnizip/metadata/metadata_validator"
|
|
11
|
+
autoload :MetadataRegistry, "omnizip/metadata/metadata_registry"
|
|
12
|
+
autoload :MetadataEditor, "omnizip/metadata/metadata_editor"
|
|
13
|
+
|
|
14
|
+
class << self
|
|
15
|
+
# Edit entry metadata
|
|
16
|
+
# @param entry [Omnizip::Zip::Entry] Entry to edit
|
|
17
|
+
# @yield [metadata] Block to modify metadata
|
|
18
|
+
# @return [EntryMetadata] Entry metadata object
|
|
19
|
+
def edit_entry(entry, &block)
|
|
20
|
+
metadata = EntryMetadata.new(entry)
|
|
21
|
+
yield(metadata) if block
|
|
22
|
+
metadata
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
# Edit archive metadata
|
|
26
|
+
# @param archive [Omnizip::Zip::File] Archive to edit
|
|
27
|
+
# @yield [metadata] Block to modify metadata
|
|
28
|
+
# @return [ArchiveMetadata] Archive metadata object
|
|
29
|
+
def edit_archive(archive, &block)
|
|
30
|
+
metadata = ArchiveMetadata.new(archive)
|
|
31
|
+
yield(metadata) if block
|
|
32
|
+
metadata
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
# Create a metadata editor for batch operations
|
|
36
|
+
# @param archive [Omnizip::Zip::File] Archive to edit
|
|
37
|
+
# @return [MetadataEditor] Metadata editor
|
|
38
|
+
def editor(archive)
|
|
39
|
+
MetadataEditor.new(archive)
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
# Validate metadata
|
|
43
|
+
# @param metadata [EntryMetadata, ArchiveMetadata] Metadata to validate
|
|
44
|
+
# @return [Boolean] True if valid
|
|
45
|
+
def validate(metadata)
|
|
46
|
+
validator = MetadataValidator.new
|
|
47
|
+
case metadata
|
|
48
|
+
when EntryMetadata
|
|
49
|
+
validator.validate_entry(metadata)
|
|
50
|
+
when ArchiveMetadata
|
|
51
|
+
validator.validate_archive(metadata)
|
|
52
|
+
else
|
|
53
|
+
raise ArgumentError, "Unknown metadata type: #{metadata.class}"
|
|
54
|
+
end
|
|
55
|
+
end
|
|
56
|
+
end
|
|
57
|
+
end
|
|
58
|
+
end
|
|
File without changes
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "lutaml/model"
|
|
4
|
+
|
|
5
|
+
module Omnizip
|
|
6
|
+
module Models
|
|
7
|
+
# Metadata describing a compression algorithm.
|
|
8
|
+
#
|
|
9
|
+
# Serialized via lutaml-model — no hand-rolled +to_h+ / +to_json+.
|
|
10
|
+
class AlgorithmMetadata < Lutaml::Model::Serializable
|
|
11
|
+
include AttributeApply
|
|
12
|
+
|
|
13
|
+
attribute :name, :string
|
|
14
|
+
attribute :description, :string
|
|
15
|
+
attribute :version, :string
|
|
16
|
+
attribute :author, :string
|
|
17
|
+
attribute :max_compression_level, :integer
|
|
18
|
+
attribute :min_compression_level, :integer
|
|
19
|
+
attribute :default_compression_level, :integer
|
|
20
|
+
attribute :supports_streaming, :boolean, default: false
|
|
21
|
+
attribute :supports_multithreading, :boolean, default: false
|
|
22
|
+
|
|
23
|
+
json do
|
|
24
|
+
map :name, to: :name
|
|
25
|
+
map :description, to: :description
|
|
26
|
+
map :version, to: :version
|
|
27
|
+
map :author, to: :author
|
|
28
|
+
map :max_compression_level, to: :max_compression_level
|
|
29
|
+
map :min_compression_level, to: :min_compression_level
|
|
30
|
+
map :default_compression_level, to: :default_compression_level
|
|
31
|
+
map :supports_streaming, to: :supports_streaming
|
|
32
|
+
map :supports_multithreading, to: :supports_multithreading
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
# Apply a hash of attributes (whitelisted to declared attributes).
|
|
36
|
+
#
|
|
37
|
+
# @param attributes [Hash{Symbol=>Object}]
|
|
38
|
+
# @return [self]
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
end
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
# Copyright (C) 2025 Ribose Inc.
|
|
4
|
+
#
|
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining a
|
|
6
|
+
# copy of this software and associated documentation files (the "Software"),
|
|
7
|
+
# to deal in the Software without restriction, including without limitation
|
|
8
|
+
# the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
|
9
|
+
# and/or sell copies of the Software, and to permit persons to whom the
|
|
10
|
+
# Software is furnished to do so, subject to the following conditions:
|
|
11
|
+
#
|
|
12
|
+
# The above copyright notice and this permission notice shall be included in
|
|
13
|
+
# all copies or substantial portions of the Software.
|
|
14
|
+
#
|
|
15
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
|
20
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
|
21
|
+
# DEALINGS IN THE SOFTWARE.
|
|
22
|
+
|
|
23
|
+
module Omnizip
|
|
24
|
+
module Models
|
|
25
|
+
# Shared #apply for lutaml-model Serializables: set every declared
|
|
26
|
+
# attribute present in the hash. Unknown and String keys are
|
|
27
|
+
# ignored (String keys so +to_hash+ output needs +.symbolize_keys+
|
|
28
|
+
# first — +.from_hash+ handles the round trip).
|
|
29
|
+
module AttributeApply
|
|
30
|
+
# @param attributes [Hash{Symbol=>Object}]
|
|
31
|
+
# @return [self]
|
|
32
|
+
def apply(attributes)
|
|
33
|
+
self.class.attributes.each_key do |name|
|
|
34
|
+
public_send("#{name}=", attributes[name]) if attributes.key?(name)
|
|
35
|
+
end
|
|
36
|
+
self
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
end
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "lutaml/model"
|
|
4
|
+
require "json"
|
|
5
|
+
|
|
6
|
+
module Omnizip
|
|
7
|
+
module Models
|
|
8
|
+
# Model representing compression operation options.
|
|
9
|
+
#
|
|
10
|
+
# Serialized via lutaml-model — callers should not write hand-rolled
|
|
11
|
+
# +to_h+ / +to_json+ / +from_json+ on this class. The framework
|
|
12
|
+
# provides +#to_hash+, +#to_json+, and +.from_hash+ / +.from_json+
|
|
13
|
+
# automatically from the +attribute+ declarations below.
|
|
14
|
+
class CompressionOptions < Lutaml::Model::Serializable
|
|
15
|
+
include AttributeApply
|
|
16
|
+
|
|
17
|
+
attribute :level, :integer, default: 5
|
|
18
|
+
attribute :dictionary_size, :integer
|
|
19
|
+
attribute :num_fast_bytes, :integer
|
|
20
|
+
attribute :match_finder, :string
|
|
21
|
+
attribute :num_threads, :integer, default: 1
|
|
22
|
+
attribute :solid, :boolean, default: false
|
|
23
|
+
attribute :buffer_size, :integer, default: 65_536
|
|
24
|
+
|
|
25
|
+
# JSON / hash mappings (1:1, no renames needed).
|
|
26
|
+
json do
|
|
27
|
+
map :level, to: :level
|
|
28
|
+
map :dictionary_size, to: :dictionary_size
|
|
29
|
+
map :num_fast_bytes, to: :num_fast_bytes
|
|
30
|
+
map :match_finder, to: :match_finder
|
|
31
|
+
map :num_threads, to: :num_threads
|
|
32
|
+
map :solid, to: :solid
|
|
33
|
+
map :buffer_size, to: :buffer_size
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
# Apply a hash of attributes. Only keys declared as +attribute+s
|
|
37
|
+
# above are applied; unknown keys are silently ignored.
|
|
38
|
+
#
|
|
39
|
+
# @param attributes [Hash{Symbol=>Object}]
|
|
40
|
+
# @return [self]
|
|
41
|
+
|
|
42
|
+
# Validate that all set values are within their type's domain.
|
|
43
|
+
#
|
|
44
|
+
# @raise [ArgumentError] if any value is invalid
|
|
45
|
+
# @return [Boolean] true if valid
|
|
46
|
+
def validate!
|
|
47
|
+
raise ArgumentError, "level must be 0-9" unless (0..9).cover?(level)
|
|
48
|
+
|
|
49
|
+
true
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
end
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "lutaml/model"
|
|
4
|
+
|
|
5
|
+
module Omnizip
|
|
6
|
+
module Models
|
|
7
|
+
# Options for converting between archive formats.
|
|
8
|
+
#
|
|
9
|
+
# Serialized via lutaml-model — no hand-rolled +to_h+ / +to_json+.
|
|
10
|
+
class ConversionOptions < Lutaml::Model::Serializable
|
|
11
|
+
VALID_FORMATS = %i[zip seven_zip 7z].freeze
|
|
12
|
+
|
|
13
|
+
attribute :source_format, :symbol
|
|
14
|
+
attribute :target_format, :symbol, default: :seven_zip
|
|
15
|
+
attribute :compression, :symbol
|
|
16
|
+
attribute :compression_level, :integer, default: 5
|
|
17
|
+
attribute :filter, :symbol
|
|
18
|
+
attribute :preserve_metadata, :boolean, default: true
|
|
19
|
+
attribute :temp_directory, :string
|
|
20
|
+
attribute :solid, :boolean, default: true
|
|
21
|
+
attribute :delete_source, :boolean, default: false
|
|
22
|
+
|
|
23
|
+
# Both flags on every field: render_default alone still drops a key that
|
|
24
|
+
# was explicitly assigned nil, and Converter builds this object with
|
|
25
|
+
# new(**options) straight from caller-supplied hashes.
|
|
26
|
+
key_value do
|
|
27
|
+
map "source_format", to: :source_format,
|
|
28
|
+
render_default: true, render_nil: true
|
|
29
|
+
map "target_format", to: :target_format,
|
|
30
|
+
render_default: true, render_nil: true
|
|
31
|
+
map "compression", to: :compression,
|
|
32
|
+
render_default: true, render_nil: true
|
|
33
|
+
map "compression_level", to: :compression_level,
|
|
34
|
+
render_default: true, render_nil: true
|
|
35
|
+
map "filter", to: :filter,
|
|
36
|
+
render_default: true, render_nil: true
|
|
37
|
+
map "preserve_metadata", to: :preserve_metadata,
|
|
38
|
+
render_default: true, render_nil: true
|
|
39
|
+
map "temp_directory", to: :temp_directory,
|
|
40
|
+
render_default: true, render_nil: true
|
|
41
|
+
map "solid", to: :solid,
|
|
42
|
+
render_default: true, render_nil: true
|
|
43
|
+
map "delete_source", to: :delete_source,
|
|
44
|
+
render_default: true, render_nil: true
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# Validate that formats and compression level are in range.
|
|
48
|
+
#
|
|
49
|
+
# Named +validate_options!+ rather than +validate+ so it does not
|
|
50
|
+
# shadow Lutaml::Model::Validation#validate(register:).
|
|
51
|
+
#
|
|
52
|
+
# @raise [ArgumentError] if any value is invalid
|
|
53
|
+
# @return [Boolean] true if valid
|
|
54
|
+
def validate_options!
|
|
55
|
+
validate_format(target_format, "target")
|
|
56
|
+
validate_format(source_format, "source") if source_format
|
|
57
|
+
validate_compression_level
|
|
58
|
+
|
|
59
|
+
true
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
private
|
|
63
|
+
|
|
64
|
+
def validate_format(format, type)
|
|
65
|
+
return if VALID_FORMATS.include?(format)
|
|
66
|
+
|
|
67
|
+
raise ArgumentError, "Invalid #{type} format: #{format}. " \
|
|
68
|
+
"Valid formats: #{VALID_FORMATS.join(', ')}"
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def validate_compression_level
|
|
72
|
+
return if (1..9).cover?(compression_level)
|
|
73
|
+
|
|
74
|
+
raise ArgumentError,
|
|
75
|
+
"Invalid compression level: #{compression_level}. Must be 1-9"
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
end
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "lutaml/model"
|
|
4
|
+
|
|
5
|
+
module Omnizip
|
|
6
|
+
module Models
|
|
7
|
+
# Model for format conversion results.
|
|
8
|
+
#
|
|
9
|
+
# Serialized via lutaml-model — no hand-rolled +to_h+ / +to_json+.
|
|
10
|
+
# The percentage/speed keys serialize the derived methods; the
|
|
11
|
+
# attribute names differ from the keys so the framework's
|
|
12
|
+
# generated readers do not shadow the methods.
|
|
13
|
+
class ConversionResult < Lutaml::Model::Serializable
|
|
14
|
+
attribute :source_path, :string
|
|
15
|
+
attribute :target_path, :string
|
|
16
|
+
attribute :source_format, :symbol
|
|
17
|
+
attribute :target_format, :symbol
|
|
18
|
+
attribute :source_size, :integer
|
|
19
|
+
attribute :target_size, :integer
|
|
20
|
+
attribute :duration, :double
|
|
21
|
+
attribute :entry_count, :integer
|
|
22
|
+
attribute :warnings, :string, collection: true, default: []
|
|
23
|
+
|
|
24
|
+
attribute :ratio, :double, method: :compression_ratio_value
|
|
25
|
+
attribute :reduction_pct, :double, method: :size_reduction
|
|
26
|
+
attribute :ratio_pct, :double, method: :size_ratio
|
|
27
|
+
attribute :speed, :double, method: :processing_speed
|
|
28
|
+
|
|
29
|
+
key_value do
|
|
30
|
+
map "source_path", to: :source_path,
|
|
31
|
+
render_default: true, render_nil: true
|
|
32
|
+
map "target_path", to: :target_path,
|
|
33
|
+
render_default: true, render_nil: true
|
|
34
|
+
map "source_format", to: :source_format,
|
|
35
|
+
render_default: true, render_nil: true
|
|
36
|
+
map "target_format", to: :target_format,
|
|
37
|
+
render_default: true, render_nil: true
|
|
38
|
+
map "source_size", to: :source_size,
|
|
39
|
+
render_default: true, render_nil: true
|
|
40
|
+
map "target_size", to: :target_size,
|
|
41
|
+
render_default: true, render_nil: true
|
|
42
|
+
map "size_reduction", to: :reduction_pct,
|
|
43
|
+
render_default: true, render_nil: true
|
|
44
|
+
map "size_ratio", to: :ratio_pct,
|
|
45
|
+
render_default: true, render_nil: true
|
|
46
|
+
map "duration", to: :duration,
|
|
47
|
+
render_default: true, render_nil: true
|
|
48
|
+
map "entry_count", to: :entry_count,
|
|
49
|
+
render_default: true, render_nil: true
|
|
50
|
+
map "processing_speed", to: :speed,
|
|
51
|
+
render_default: true, render_nil: true
|
|
52
|
+
map "warnings", to: :warnings,
|
|
53
|
+
render_default: true, render_nil: true
|
|
54
|
+
map "compression_ratio", to: :ratio,
|
|
55
|
+
render_default: true, render_nil: true
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
# lutaml-model 0.8.x does not render empty-string/empty-collection
|
|
59
|
+
# defaults, so they are assigned explicitly to keep every key
|
|
60
|
+
# present in the serialized shape.
|
|
61
|
+
def initialize(attrs = {})
|
|
62
|
+
super({ warnings: [] }.merge(attrs))
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
# Get size reduction percentage
|
|
66
|
+
#
|
|
67
|
+
# @return [Float] Size reduction as percentage
|
|
68
|
+
def size_reduction
|
|
69
|
+
return 0.0 if source_size.to_i.zero?
|
|
70
|
+
|
|
71
|
+
((source_size - target_size).to_f / source_size * 100).round(2)
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
# Get size ratio
|
|
75
|
+
#
|
|
76
|
+
# @return [Float] Target size as percentage of source size
|
|
77
|
+
def size_ratio
|
|
78
|
+
return 0.0 if source_size.to_i.zero?
|
|
79
|
+
|
|
80
|
+
(target_size.to_f / source_size * 100).round(2)
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
# Check if conversion resulted in smaller file
|
|
84
|
+
#
|
|
85
|
+
# @return [Boolean] True if target is smaller
|
|
86
|
+
def smaller?
|
|
87
|
+
target_size < source_size
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
# Check if conversion resulted in larger file
|
|
91
|
+
#
|
|
92
|
+
# @return [Boolean] True if target is larger
|
|
93
|
+
def larger?
|
|
94
|
+
target_size > source_size
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
# Check if there were warnings
|
|
98
|
+
#
|
|
99
|
+
# @return [Boolean] True if warnings exist
|
|
100
|
+
def warnings?
|
|
101
|
+
!warnings.empty?
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
# Get average processing speed
|
|
105
|
+
#
|
|
106
|
+
# @return [Float] MB/s processing speed
|
|
107
|
+
def processing_speed
|
|
108
|
+
return 0.0 if duration.to_f.zero? || source_size.to_i.zero?
|
|
109
|
+
|
|
110
|
+
speed = source_size / duration / 1_048_576.0
|
|
111
|
+
rounded = speed.round(2)
|
|
112
|
+
# Return actual speed if rounding would give 0 but speed is positive
|
|
113
|
+
rounded.zero? && speed.positive? ? speed : rounded
|
|
114
|
+
end
|
|
115
|
+
|
|
116
|
+
# Compression ratio (0.0-1.0 fraction saved by compression)
|
|
117
|
+
#
|
|
118
|
+
# @return [Float]
|
|
119
|
+
def compression_ratio_value
|
|
120
|
+
return 0.0 if source_size.to_i.zero?
|
|
121
|
+
|
|
122
|
+
(1.0 - (target_size.to_f / source_size)).round(4)
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
# Format as human-readable string
|
|
126
|
+
#
|
|
127
|
+
# @return [String] Formatted result
|
|
128
|
+
def to_s
|
|
129
|
+
"Converted #{source_path} (#{format_size(source_size)}) to " \
|
|
130
|
+
"#{target_path} (#{format_size(target_size)}) in #{duration.round(2)}s. " \
|
|
131
|
+
"#{size_reduction.positive? ? "Saved #{size_reduction.to_i}%" : "Increased #{(-size_reduction).to_i}%"}"
|
|
132
|
+
end
|
|
133
|
+
|
|
134
|
+
private
|
|
135
|
+
|
|
136
|
+
def format_size(bytes)
|
|
137
|
+
Omnizip::CliOutputFormatter.format_size(bytes)
|
|
138
|
+
end
|
|
139
|
+
end
|
|
140
|
+
end
|
|
141
|
+
end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
#
|
|
4
|
+
# Copyright (C) 2025 Ribose Inc.
|
|
5
|
+
#
|
|
6
|
+
|
|
7
|
+
require "lutaml/model"
|
|
8
|
+
|
|
9
|
+
module Omnizip
|
|
10
|
+
module Models
|
|
11
|
+
# Model representing an ETA (Estimated Time to Arrival) calculation result.
|
|
12
|
+
#
|
|
13
|
+
# This class encapsulates the result of ETA calculations, including
|
|
14
|
+
# seconds remaining, formatted time string, and confidence interval.
|
|
15
|
+
#
|
|
16
|
+
# Serialized via lutaml-model — no hand-rolled +to_h+ / +to_json+.
|
|
17
|
+
class ETAResult < Lutaml::Model::Serializable
|
|
18
|
+
# No mapping block: the default mapping already omits unassigned
|
|
19
|
+
# attributes, which is what the previous +to_h+ did with +.compact+.
|
|
20
|
+
attribute :seconds_remaining, :float
|
|
21
|
+
attribute :formatted, :string
|
|
22
|
+
attribute :confidence_lower, :float
|
|
23
|
+
attribute :confidence_upper, :float
|
|
24
|
+
|
|
25
|
+
# Get confidence interval as array
|
|
26
|
+
#
|
|
27
|
+
# @return [Array<Float>] [lower, upper] bounds in seconds
|
|
28
|
+
def confidence_interval
|
|
29
|
+
[confidence_lower, confidence_upper]
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
# Check if ETA is reliable (confidence interval is reasonable)
|
|
33
|
+
#
|
|
34
|
+
# @return [Boolean] true if confidence interval is within 50% of estimate
|
|
35
|
+
def reliable?
|
|
36
|
+
unless seconds_remaining && confidence_lower && confidence_upper
|
|
37
|
+
return false
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
range = confidence_upper - confidence_lower
|
|
41
|
+
range < (seconds_remaining * 0.5)
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Omnizip
|
|
4
|
+
module Models
|
|
5
|
+
# Represents a rule for extracting files from an archive
|
|
6
|
+
#
|
|
7
|
+
# Defines what files to extract and how to extract them using
|
|
8
|
+
# patterns, predicates, and options.
|
|
9
|
+
class ExtractionRule
|
|
10
|
+
attr_reader :patterns, :predicates, :options
|
|
11
|
+
|
|
12
|
+
# Initialize a new extraction rule
|
|
13
|
+
#
|
|
14
|
+
# @param patterns [Array<String, Regexp>] Patterns to match
|
|
15
|
+
# @param predicates [Array<Proc>] Custom predicates for matching
|
|
16
|
+
# @param options [Hash] Extraction options
|
|
17
|
+
# @option options [Boolean] :preserve_paths Keep directory structure
|
|
18
|
+
# @option options [Boolean] :flatten Extract all to destination root
|
|
19
|
+
# @option options [Boolean] :overwrite Overwrite existing files
|
|
20
|
+
# @option options [String] :dest_prefix Prefix for destination paths
|
|
21
|
+
def initialize(patterns: [], predicates: [], options: {})
|
|
22
|
+
@patterns = Array(patterns)
|
|
23
|
+
@predicates = Array(predicates)
|
|
24
|
+
@options = default_options.merge(options)
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
# Add a pattern to the rule
|
|
28
|
+
#
|
|
29
|
+
# @param pattern [String, Regexp] Pattern to add
|
|
30
|
+
# @return [self]
|
|
31
|
+
def add_pattern(pattern)
|
|
32
|
+
@patterns << pattern
|
|
33
|
+
self
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
# Add a predicate to the rule
|
|
37
|
+
#
|
|
38
|
+
# @param predicate [Proc] Predicate block to add
|
|
39
|
+
# @return [self]
|
|
40
|
+
def add_predicate(&predicate)
|
|
41
|
+
@predicates << predicate if predicate
|
|
42
|
+
self
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
# Check if any patterns are defined
|
|
46
|
+
#
|
|
47
|
+
# @return [Boolean]
|
|
48
|
+
def patterns?
|
|
49
|
+
!@patterns.empty?
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
# Check if any predicates are defined
|
|
53
|
+
#
|
|
54
|
+
# @return [Boolean]
|
|
55
|
+
def predicates?
|
|
56
|
+
!@predicates.empty?
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
# Check if the rule has any conditions
|
|
60
|
+
#
|
|
61
|
+
# @return [Boolean]
|
|
62
|
+
def conditions?
|
|
63
|
+
patterns? || predicates?
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
# Get option value
|
|
67
|
+
#
|
|
68
|
+
# @param key [Symbol] Option key
|
|
69
|
+
# @return [Object] Option value
|
|
70
|
+
def [](key)
|
|
71
|
+
@options[key]
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
# Set option value
|
|
75
|
+
#
|
|
76
|
+
# @param key [Symbol] Option key
|
|
77
|
+
# @param value [Object] Option value
|
|
78
|
+
def []=(key, value)
|
|
79
|
+
@options[key] = value
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
# Check if paths should be preserved
|
|
83
|
+
#
|
|
84
|
+
# @return [Boolean]
|
|
85
|
+
def preserve_paths?
|
|
86
|
+
@options[:preserve_paths]
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
# Check if paths should be flattened
|
|
90
|
+
#
|
|
91
|
+
# @return [Boolean]
|
|
92
|
+
def flatten?
|
|
93
|
+
@options[:flatten]
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
# Check if existing files should be overwritten
|
|
97
|
+
#
|
|
98
|
+
# @return [Boolean]
|
|
99
|
+
def overwrite?
|
|
100
|
+
@options[:overwrite]
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
private
|
|
104
|
+
|
|
105
|
+
def default_options
|
|
106
|
+
{
|
|
107
|
+
preserve_paths: true,
|
|
108
|
+
flatten: false,
|
|
109
|
+
overwrite: false,
|
|
110
|
+
dest_prefix: nil,
|
|
111
|
+
}
|
|
112
|
+
end
|
|
113
|
+
end
|
|
114
|
+
end
|
|
115
|
+
end
|