Search code examples
c#.netsystem.io.packaging

FileShare.ReadWrite in System.IO.Packaging


I am using System.IO.Packaging to work with Package files.

But it seems Package cannot open a file with read access providing FileShare.ReadWrite. Here's the code :

 myPackage = Package.Open("fileName", FileMode.Open,  FileAccess.Read,  FileShare.ReadWrite);

When I try to load a file, the following exception is thrown:

Exception thrown: 'System.NotSupportedException' in WindowsBase.dll

Additional information: Only FileShare.Read and FileShare.None are supported.

Is there anything that can be done to get this working? I need FileShare to be set to ReadWrite.

EDIT: I am trying to work with a docx file in my code. I just want to be able to read the contents of the file without modifying it. In the meanwhile I also want it to be editable using Word. This is what I am trying to achieve. I have used DotNetZip's Ionic.Zip library with success for this purpose. But i encountered some errors while saving files using that. So I had to get back to System.IO.Packaging. Any help would be appreciated.


Solution

  • It's not clear why you want to do this, but you can try specifying options on file stream directly like this:

    using (var file = new FileStream(@"myfile", FileMode.Open, FileAccess.Read, FileShare.ReadWrite)) {
        var myPackage = Package.Open(file);
    }
    

    UPDATE to elaborate a bit more about when this might be useful. Suppose you try to do something like this:

    using (var fs1 = new FileStream("myfile", FileMode.Append, FileAccess.Write, FileShare.Read))
    using (var fs2 = new FileStream("myfile", FileMode.Open, FileAccess.Read, FileShare.Read)) {
    }
    

    So first file is opened for writing, with FileShare = Read. Then there is another attempt to open file, for reading, again with FileShare = Read. This won't work, because if file has already been opened for write, any request with FileShare = read will fail. To make this work you have to do it like this:

    using (var fs1 = new FileStream("myfile", FileMode.Append, FileAccess.Write, FileShare.Read))
    using (var fs2 = new FileStream("myfile", FileMode.Open, FileAccess.Read, FileShare.ReadWrite)) {
    }
    

    Here you request FileShare.ReadWrite which allows you to read file opened by fs1 for writing.

    Now, if writing and reading the same file concurrently is a good idea is completely dependent of what you want to achieve and if you know what you are doing. In most cases it's not a good idea, but again it depends.

    UPDATE 2. It's perfectly possible to use code above to achieve your goal (open .docx for reading while MS Word has it open for writing:

    using (var file = new FileStream(@"my.docx", FileMode.Open, FileAccess.Read, FileShare.ReadWrite)) {
        var myPackage = Package.Open(file);
        // here do what you want with your .docx
    }