OneDrive / onedrive-sdk-csharp

OneDrive SDK for C#! https://dev.onedrive.com
Other
295 stars 145 forks source link

Streams causing exceptions with AddAsync() in a UWP app #204

Open nlebeck opened 7 years ago

nlebeck commented 7 years ago

I am attempting to write a simple UWP app that uses the OneDrive SDK to create a new file in its app folder on the user's OneDrive account. I've tried multiple ways of obtaining a Stream object to provide to the AddAsync() call, but each of the Streams throws a different exception.

First, I tried using a MemoryStream to specify the contents of the new file directly:

Stream stream = new MemoryStream();
StreamWriter streamWriter = new StreamWriter(stream);
streamWriter.Write("Hello world");

Item testFile = new Item
{
    Name = "testfile.txt",
    File = new Microsoft.OneDrive.Sdk.File(),
    Content = stream
};
await client.Drive.Special.AppRoot.Children.Request().AddAsync(testFile);

This code failed with the exception "Error getting value from 'ReadTimeout' on 'System.IO.MemoryStream'." The inner exception was "Timeouts are not supported on this stream."

Next, I tried obtaining a StorageFile object using a file picker and getting the Stream from that object:

Windows.Storage.Pickers.FileOpenPicker picker = new Windows.Storage.Pickers.FileOpenPicker();
picker.FileTypeFilter.Add("*");
StorageFile file = await picker.PickSingleFileAsync();
Stream stream = await file.OpenStreamForReadAsync();

I used the same code as in the previous example to call AddAsync. This time, I got the exception "Error getting value from 'CanRead' on 'System.IO.BufferedStream'." The inner exception was "The API 'System.IO.BufferedStream.get_CanRead()' cannot be used on the current platform. See http://go.microsoft.com/fwlink/?LinkId=248273 for more information."

It seems like each of the two Stream types failed due to a specific quirk of how the underlying Stream is implemented in the UWP runtime, and how that implementation interacts with the OneDrive SDK's requirements. If this is the case, how can I obtain a Stream inside a UWP app that I can actually use to upload a new file to OneDrive? If not, am I doing something wrong creating either of these streams?

Thanks!

nlebeck commented 7 years ago

To add some more information: I thought the problem just had to do with the UWP implementation of Streams, so I wrote a WPF version of my app. Using a MemoryStream in the WPF version resulted in the same timeout exception as in the UWP version, and using a Windows.Forms.OpenFileDialog to obtain a stream of an existing file resulted in that timeout exception as well. Also, just to clarify, the outer exception in the timeout case is a Newtonsoft.Json.JsonSerializationException.