[PR #1092] Add dual sync/async support for Zip headers and IsArchive async overloads #1524

Open
opened 2026-01-29 22:20:57 +00:00 by claunia · 0 comments
Owner

Original Pull Request: https://github.com/adamhathcock/sharpcompress/pull/1092

State: closed
Merged: No


Updates all Zip header classes to support both synchronous and asynchronous reading paths while maintaining backward compatibility. Adds async overloads for archive detection methods to enable proper async-only stream support.

Changes Made

Zip Headers - Dual Sync/Async Support

  • Dual abstract methods: Updated ZipHeader base class to define both Read(BinaryReader) and Read(AsyncBinaryReader) abstract methods
  • Full implementation coverage: All Zip header classes now implement both sync and async Read methods (DirectoryEndHeader, DirectoryEntryHeader, LocalEntryHeader, IgnoreHeader, SplitHeader, Zip64DirectoryEndHeader, Zip64DirectoryEndLocatorHeader)
  • Factory classes: ZipHeaderFactory and SeekableZipHeaderFactory provide both sync and async ReadHeader methods
  • Backward compatibility: Existing sync code paths (like ZipArchive.LoadEntries) continue to work unchanged
  • Code reuse: Extracted common processing logic into shared methods to avoid duplication between sync and async implementations

IsArchive Async Overloads

  • Interface extension: Added IsArchiveAsync method to IFactory interface with default implementation
  • Zip archive detection: Added IsZipFileAsync and IsZipMultiAsync methods to ZipArchive for async archive format detection
  • GZip archive detection: Added IsGZipFileAsync method to GZipArchive using ReadFullyAsync utility
  • Factory implementations: ZipFactory and GZipFactory override IsArchiveAsync to use async detection methods
  • Reader factory: Updated ReaderFactory.OpenAsync to call IsArchiveAsync instead of IsArchive for proper async-only stream support

AsyncBinaryReader

  • Simplified implementation: Removed BufferedStream wrapping as it internally uses synchronous Read operations
  • Async-only stream support: Now works correctly with streams that only support async operations
  • Existing buffering: SharpCompressStream already provides buffering with true async support

Test Fixes

  • Test update: Fixed Zip_Reader_Disposal_Test2_Async to use ReaderFactory.OpenAsync
  • TestStream fix: Added ReadAsync overrides to properly forward async calls to underlying stream

Benefits

  • Enables proper async-only stream support for archive detection
  • Reduces system calls during async read operations
  • Improves performance for small reads (bytes, uint16, uint32, etc.)
  • Maintains full backward compatibility with synchronous code paths
  • Enables future async optimization while preserving sync compatibility

The implementation provides true async support for Zip and GZip archive detection and reading, allowing the use of async-only streams throughout the library while maintaining full backward compatibility with synchronous code paths.

Original prompt

Use a buffered stream that reads async from the stream. Consider streams already implemented

The user has attached the following file paths as relevant context:

  • src/SharpCompress/Common/AsyncBinaryReader.cs

Created from VS Code.


💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.

**Original Pull Request:** https://github.com/adamhathcock/sharpcompress/pull/1092 **State:** closed **Merged:** No --- Updates all Zip header classes to support both synchronous and asynchronous reading paths while maintaining backward compatibility. Adds async overloads for archive detection methods to enable proper async-only stream support. ## Changes Made ### Zip Headers - Dual Sync/Async Support - **Dual abstract methods**: Updated `ZipHeader` base class to define both `Read(BinaryReader)` and `Read(AsyncBinaryReader)` abstract methods - **Full implementation coverage**: All Zip header classes now implement both sync and async Read methods (DirectoryEndHeader, DirectoryEntryHeader, LocalEntryHeader, IgnoreHeader, SplitHeader, Zip64DirectoryEndHeader, Zip64DirectoryEndLocatorHeader) - **Factory classes**: `ZipHeaderFactory` and `SeekableZipHeaderFactory` provide both sync and async `ReadHeader` methods - **Backward compatibility**: Existing sync code paths (like `ZipArchive.LoadEntries`) continue to work unchanged - **Code reuse**: Extracted common processing logic into shared methods to avoid duplication between sync and async implementations ### IsArchive Async Overloads - **Interface extension**: Added `IsArchiveAsync` method to `IFactory` interface with default implementation - **Zip archive detection**: Added `IsZipFileAsync` and `IsZipMultiAsync` methods to `ZipArchive` for async archive format detection - **GZip archive detection**: Added `IsGZipFileAsync` method to `GZipArchive` using `ReadFullyAsync` utility - **Factory implementations**: `ZipFactory` and `GZipFactory` override `IsArchiveAsync` to use async detection methods - **Reader factory**: Updated `ReaderFactory.OpenAsync` to call `IsArchiveAsync` instead of `IsArchive` for proper async-only stream support ### AsyncBinaryReader - **Simplified implementation**: Removed BufferedStream wrapping as it internally uses synchronous Read operations - **Async-only stream support**: Now works correctly with streams that only support async operations - **Existing buffering**: SharpCompressStream already provides buffering with true async support ### Test Fixes - **Test update**: Fixed `Zip_Reader_Disposal_Test2_Async` to use `ReaderFactory.OpenAsync` - **TestStream fix**: Added `ReadAsync` overrides to properly forward async calls to underlying stream ## Benefits - Enables proper async-only stream support for archive detection - Reduces system calls during async read operations - Improves performance for small reads (bytes, uint16, uint32, etc.) - Maintains full backward compatibility with synchronous code paths - Enables future async optimization while preserving sync compatibility The implementation provides true async support for Zip and GZip archive detection and reading, allowing the use of async-only streams throughout the library while maintaining full backward compatibility with synchronous code paths. <!-- START COPILOT ORIGINAL PROMPT --> <details> <summary>Original prompt</summary> > Use a buffered stream that reads async from the stream. Consider streams already implemented > > The user has attached the following file paths as relevant context: > - src/SharpCompress/Common/AsyncBinaryReader.cs </details> <!-- START COPILOT CODING AGENT SUFFIX --> Created from [VS Code](https://code.visualstudio.com/docs/copilot/copilot-coding-agent). <!-- START COPILOT CODING AGENT TIPS --> --- 💬 We'd love your input! Share your thoughts on Copilot coding agent in our [2 minute survey](https://gh.io/copilot-coding-agent-survey).
claunia added the pull-request label 2026-01-29 22:20:57 +00:00
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: starred/sharpcompress#1524