2
votes

I have a WCF service and Im looking to stream some files from server to client.

I have had this working when I hard code the filename of the file to stream into the code.

I am trying to change the code so that the getStream method returns a Dictionary so I can return a collection of filenames and the stream associated with the filename and then process each stream at the client side.

I am getting the following exception on the client side when trying to call the getStream method: An error occurred while receiving the HTTP response to http://localhost:8082/. This could be due to the service endpoint binding not using the HTTP protocol. This could also be due to an HTTP request context being aborted by the server (possibly due to the service shutting down). See server logs for more details.

After researching this on the net it looks like this is a false exception so I turned on tracing and this is the exceptionn message fromt eh trace log:

There was an error while trying to serialize parameter http://tempuri.org/:GetStreamResult. The InnerException message was 'Type 'System.IO.FileStream' with data contract name 'FileStream:http://schemas.datacontract.org/2004/07/System.IO' is not expected. Consider using a DataContractResolver or add any types not known statically to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding them to the list of known types passed to DataContractSerializer.'. Please see InnerException for more details.

Here is the Server side code:

public Dictionary<String, Stream> GetStream()
    {
        Dictionary<String, Stream> retDic = new Dictionary<string, Stream>();          

        string[] fileEntries = Directory.GetFiles(@"C:\Users\Ash\Desktop\FrontendPluginsServer");
        foreach (string fileName in fileEntries)
        {
             //do something with fileName
            retDic.Add(fileName, File.OpenRead(fileName));
        }
        //return File.OpenRead(@"C:\Users\Ash\Desktop\FrontendPluginsServer\OptekImporterFrontend.dll");

        return retDic;
    }

Here is the client side code:

ModuleDownloader.ModuleDownloaderClient moo = new ModuleDownloader.ModuleDownloaderClient();
        Dictionary<String, Stream> dic = moo.GetStream();

        foreach (String key in dic.Keys)
        {
            using (Stream file = File.OpenWrite(@"C:\Users\Ash\Desktop\FrontEndPluginsClient\" + key)) { CopyStream(dic[key], file); }
        }

Please let me know if you need anymore information.

Kind Regards

Ash

1
any final solution with full source code ?Kiquenet

1 Answers

6
votes

There is no way you can do this.

  • FileStream is not serialisable. The reason it tries to serialise it is that it does not follow WCF streaming conventions.
  • WCF restrictions on streaming defines that you have to have a single Stream in the method signature and nothing else if you wanna use WCF Streaming.

At any time, you can only send a single stream.

Read more here.