stride3d/stride · error · InvalidOperationException

Stream cannot be written

Error message

Stream cannot be written

What it means

ExtractFile decompresses an entry into the supplied destination stream, which must be writable. Passing a read-only stream would make every write fail mid-extraction, so it is rejected upfront with InvalidOperationException.

Solutions

  1. Open the destination with FileAccess.Write / FileMode.Create
  2. If you only need entry data in memory, pass a new MemoryStream() instead
  3. Check stream.CanWrite before calling

Example fix

// before
using var dst = File.OpenRead(path);
zip.ExtractFile(entry, dst);
// after
using var dst = File.Create(path);
zip.ExtractFile(entry, dst);
Defensive patterns

Strategy: validation

Validate before calling

if (!stream.CanWrite) throw new ArgumentException("Destination stream must be writable", nameof(stream));

Type guard

static bool IsWritable(Stream s) => s.CanWrite;

Try / catch

try { zip.ExtractFile(entry, stream); }
catch (InvalidOperationException ex) { throw new IOException("Destination stream is not writable", ex); }

Prevention

When it happens

Trigger: Calling ExtractFile(entry, stream) with a FileStream opened with FileAccess.Read, a MemoryStream created over a read-only buffer via new MemoryStream(byte[]), or any readonly wrapper stream.

Common situations: Extracting into a file opened for reading to 'check' it, writing back to the same stream used for reading the archive.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of stride3d/stride@96fad776d2 (2026-09-14). Data as JSON: /api/errors/e732a13b307ec36a. Report an issue: GitHub.

Appendix: source

Thrown at sources/core/Stride.Core.IO/System.IO.Compression.Zip/ZipFile.cs:325

        /// Copy the contents of a stored file into an opened stream
        /// </summary>
        /// <param name="zfe">
        /// Entry information of file to extract
        /// </param>
        /// <param name="stream">
        /// Stream to store the uncompressed data
        /// </param>
        /// <returns>
        /// True if success, false if not.
        /// </returns>
        /// <remarks>
        /// Unique compression methods are Store and Deflate
        /// </remarks>
        public bool ExtractFile(ZipFileEntry zfe, Stream stream)
        {
            if (!stream.CanWrite)
            {
                throw new InvalidOperationException("Stream cannot be written");
            }

            // check signature
            var signature = new byte[4];
            this.zipFileStream.Seek(zfe.HeaderOffset, SeekOrigin.Begin);
            this.zipFileStream.Read(signature, 0, 4);
            if (BitConverter.ToUInt32(signature, 0) != 0x04034b50)
            {
                return false;
            }

            // Select input stream for inflating or just reading
            Stream inStream = this.GetZipStream(zfe);
            if (inStream == null)
            {
                return false;
            }

View on GitHub (pinned to 96fad776d2)