WebRequest BeginGetResponse/EndGetResponse throws

2019-04-02 09:23发布

I try to asyncify the POST operation to a REST web service using the WebRequest.

So from what I know already, I need to use the Task.Factory.FromAsync<T>(BeginXyz, EndXyz, null), seems like its working for the GetRequestStream pair methods, since I get no exception and the byte[] is filled with values.

Stream requestStream = await Task.Factory.FromAsync<Stream>(
                        request.BeginGetRequestStream, request.EndGetRequestStream, null);
byte[] postBytes = Encoding.UTF8.GetBytes(requestData);
await requestStream.WriteAsync(postBytes, 0, postBytes.Length);

Fine, the above code is working, and the next part throwing the exception.

WebResponse webResponse = await Task.Factory.FromAsync<WebResponse>(
                        request.BeginGetResponse, request.EndGetResponse, null);

The exception I get to every request.

System.NotSupportedException: Specified method is not supported.

StackTrace:

at System.Net.Browser.AsyncHelper.BeginOnUI(SendOrPostCallback beginMethod, Object state) at System.Net.Browser.ClientHttpWebRequest.EndGetResponse(IAsyncResult asyncResult) at System.Func`2.Invoke(T arg) at System.Threading.Tasks.TaskFactory`1.FromAsyncCoreLogic(IAsyncResult iar, Func`2 endFunction, Action`1 endAction, Task`1 promise, Boolean requiresSynchronization) --- End of stack trace from previous location where exception was thrown --- at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task) at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task) at System.Runtime.CompilerServices.TaskAwaiter`1.GetResult() at Gtas.Core.ServiceRepository.d__8.MoveNext()

InnerException StackTrace: at System.Net.Browser.ClientHttpWebRequest.InternalEndGetResponse(IAsyncResult asyncResult) at System.Net.Browser.ClientHttpWebRequest.<>c__DisplayClasse.b__d(Object sendState) at System.Net.Browser.AsyncHelper.<>c__DisplayClass1.b__0(Object sendState)

A full code to execute the request should be like that:

Stream requestStream = await Task.Factory.FromAsync<Stream>(
                        request.BeginGetRequestStream, request.EndGetRequestStream, null);
byte[] postBytes = Encoding.UTF8.GetBytes(requestData);
await requestStream.WriteAsync(postBytes, 0, postBytes.Length);


WebResponse webResponse = await Task.Factory.FromAsync<WebResponse>(
                        request.BeginGetResponse, request.EndGetResponse, null);
Stream streamResponse = webResponse.GetResponseStream();
StreamReader streamRead = new StreamReader(streamResponse);
string responseString = await streamRead.ReadToEndAsync();
// ... Do something with the result data

I don't quite understand what the error is.

I tried several implementation from stackoverflow and some MSDN posts. Nothing seems to working.

Using callbacks working fine. But it's good to know why I can't make it work.

Any thoughts how to accomplish this?

2条回答
叼着烟拽天下
2楼-- · 2019-04-02 09:47
  1. try surround the requestStream with using or call requestStream.Close() after requestStream.WriteAsync
  2. check the request.Method = "POST"; is not missing.
查看更多
爱情/是我丢掉的垃圾
3楼-- · 2019-04-02 10:03

Not sure for memory leak but

WebResponse response = null;
using (var stream = await 
Task<Stream>.Factory.FromAsync(request.BeginGetResponse, result =>
{
    response = request.EndGetResponse(result);
    return response.GetResponseStream();
}, request))
{
    // TODO
}
response.Dispose();
查看更多
登录 后发表回答