HttpWebRequest.BeginGetResponse(AsyncCallback, Object) 方法
定义
重要
一些信息与预发行产品相关,相应产品在发行之前可能会进行重大修改。 对于此处提供的信息,Microsoft 不作任何明示或暗示的担保。
开始对 Internet 资源的异步请求。
public:
override IAsyncResult ^ BeginGetResponse(AsyncCallback ^ callback, System::Object ^ state);
public override IAsyncResult BeginGetResponse(AsyncCallback callback, object state);
public override IAsyncResult BeginGetResponse(AsyncCallback? callback, object? state);
override this.BeginGetResponse : AsyncCallback * obj -> IAsyncResult
Public Overrides Function BeginGetResponse (callback As AsyncCallback, state As Object) As IAsyncResult
参数
- callback
- AsyncCallback
AsyncCallback 委托。
- state
- Object
此请求的状态对象。
返回
引用响应异步请求的 IAsyncResult。
例外
上一次调用 BeginGetResponse(AsyncCallback, Object) 时,流已使用
-或-
TransferEncoding 设置为值,SendChunkedfalse
。
-或-
线程池已耗尽线程。
Method 为 GET 或 HEAD,ContentLength 大于零或 SendChunkedtrue
。
-或-
KeepAlive 是 true
,AllowWriteStreamBuffering 是 false
,ContentLength 为 -1,SendChunked 为 false
,Method 为 POST 或 PUT。
-或-
HttpWebRequest 具有实体正文,但调用 BeginGetResponse(AsyncCallback, Object) 方法而不调用 BeginGetRequestStream(AsyncCallback, Object) 方法。
-或-
ContentLength 大于零,但应用程序不会写入所有承诺的数据。
以前调用 Abort()。
示例
下面的代码示例使用 BeginGetResponse 方法为 Internet 资源发出异步请求。
注意
对于异步请求,客户端应用程序负责实现其自己的超时机制。 下面的代码示例演示如何执行此操作。
using System;
using System.Net;
using System.IO;
using System.Text;
using System.Threading;
public static class WebRequestAPMSample
{
private const int BufferSize = 1024;
private class RequestState
{
public StringBuilder ResponseBuilder { get; }
public byte[] ReadBuffer { get; }
public WebRequest Request { get; }
public WebResponse Response { get; set; }
public Stream ResponseStream { get; set; }
public RequestState(WebRequest request)
{
ReadBuffer = new byte[BufferSize];
ResponseBuilder = new StringBuilder();
Request = request;
}
public void OnResponseBytesRead(int read) => ResponseBuilder.Append(Encoding.UTF8.GetString(ReadBuffer, 0, read));
}
public static ManualResetEvent allDone = new ManualResetEvent(false);
public static void Main()
{
try
{
// Create a WebRequest object to the desired URL.
WebRequest webRequest = WebRequest.Create("http://www.contoso.com");
webRequest.Timeout = 10_000; // Set 10sec timeout.
// Create an instance of the RequestState and assign the previous myHttpWebRequest
// object to its request field.
RequestState requestState = new RequestState(webRequest);
// Start the asynchronous request.
IAsyncResult result = webRequest.BeginGetResponse(new AsyncCallback(ResponseCallback), requestState);
// Wait for the response or for failure. The processing happens in the callback.
allDone.WaitOne();
// Release the WebResponse resources.
requestState.Response?.Close();
}
catch (WebException e)
{
Console.WriteLine("\nMain(): WebException raised!");
Console.WriteLine("\nMessage:{0}", e.Message);
Console.WriteLine("\nStatus:{0}", e.Status);
Console.WriteLine("Press any key to continue..........");
Console.Read();
}
catch (Exception e)
{
Console.WriteLine("\nMain(): Exception raised!");
Console.WriteLine("Source :{0} ", e.Source);
Console.WriteLine("Message :{0} ", e.Message);
Console.WriteLine("Press any key to continue..........");
Console.Read();
}
}
private static void HandleSyncResponseReadCompletion(IAsyncResult asyncResult)
{
RequestState requestState = (RequestState)asyncResult.AsyncState;
Stream responseStream = requestState.ResponseStream;
bool readComplete = false;
while (asyncResult.CompletedSynchronously && !readComplete)
{
int read = responseStream.EndRead(asyncResult);
if (read > 0)
{
requestState.OnResponseBytesRead(read);
asyncResult = responseStream.BeginRead(requestState.ReadBuffer, 0, BufferSize, new AsyncCallback(ReadCallBack), requestState);
}
else
{
readComplete = true;
HandleReadCompletion(requestState);
}
}
}
private static void ResponseCallback(IAsyncResult asynchronousResult)
{
try
{
// AsyncState is an instance of RequestState.
RequestState requestState = (RequestState)asynchronousResult.AsyncState;
WebRequest request = requestState.Request;
requestState.Response = request.EndGetResponse(asynchronousResult);
// Read the response into a Stream.
Stream responseStream = requestState.Response.GetResponseStream();
requestState.ResponseStream = responseStream;
// Begin the Reading of the contents of the HTML page and print it to the console.
IAsyncResult asynchronousReadResult = responseStream.BeginRead(requestState.ReadBuffer, 0, BufferSize, new AsyncCallback(ReadCallBack), requestState);
HandleSyncResponseReadCompletion(asynchronousReadResult);
}
catch (WebException e)
{
Console.WriteLine("\nRespCallback(): Exception raised!");
Console.WriteLine("\nMessage:{0}", e.Message);
Console.WriteLine("\nStatus:{0}", e.Status);
allDone.Set();
}
}
// Print the webpage to the standard output, close the stream and signal completion.
private static void HandleReadCompletion(RequestState requestState)
{
Console.WriteLine("\nThe contents of the Html page are : ");
if (requestState.ResponseBuilder.Length > 1)
{
string stringContent;
stringContent = requestState.ResponseBuilder.ToString();
Console.WriteLine(stringContent);
}
Console.WriteLine("Press any key to continue..........");
Console.ReadLine();
requestState.ResponseStream.Close();
allDone.Set();
}
private static void ReadCallBack(IAsyncResult asyncResult)
{
if (asyncResult.CompletedSynchronously)
{
// To avoid recursive synchronous calls into ReadCallBack,
// synchronous completion is handled at the BeginRead call-site.
return;
}
try
{
RequestState requestState = (RequestState)asyncResult.AsyncState;
Stream responseStream = requestState.ResponseStream;
int read = responseStream.EndRead(asyncResult);
// Read the HTML page and then print it to the console.
if (read > 0)
{
requestState.OnResponseBytesRead(read);
IAsyncResult asynchronousResult = responseStream.BeginRead(requestState.ReadBuffer, 0, BufferSize, new AsyncCallback(ReadCallBack), requestState);
HandleSyncResponseReadCompletion(asynchronousResult);
}
else
{
HandleReadCompletion(requestState);
}
}
catch (WebException e)
{
Console.WriteLine("\nReadCallBack(): Exception raised!");
Console.WriteLine("\nMessage:{0}", e.Message);
Console.WriteLine("\nStatus:{0}", e.Status);
allDone.Set();
}
}
}
注解
谨慎
WebRequest
、HttpWebRequest
、ServicePoint
和 WebClient
已过时,不应将其用于新开发。 请改用 HttpClient。
BeginGetResponse 方法启动来自 Internet 资源的响应的异步请求。 异步回调方法使用 EndGetResponse 方法返回实际 WebResponse。
当 HttpWebRequest 类上设置的属性冲突时,会引发 ProtocolViolationException。 如果应用程序将 ContentLength 属性和 SendChunked 属性设置为 true
,然后发送 HTTP GET 请求,则会发生此异常。 如果应用程序尝试将分块发送到仅支持 HTTP 1.0 协议的服务器(其中不支持此协议),则会发生此异常。 如果应用程序尝试在不设置 ContentLength 属性的情况下发送数据,或者在禁用缓冲和保持连接(KeepAlive 属性为 true
)时 false
SendChunked,则会发生此异常.
如果引发 WebException,请使用异常的 Response 和 Status 属性来确定来自服务器的响应。
BeginGetResponse 方法要求完成一些同步安装任务(例如 DNS 解析、代理检测和 TCP 套接字连接),然后此方法才变为异步。 因此,不应在用户界面(UI)线程上调用此方法,因为它可能需要相当长的时间(最多几分钟,具体取决于网络设置)才能完成初始同步设置任务,然后引发错误异常或方法成功。
若要详细了解线程池,请参阅 托管线程池。
注意
应用程序无法混合特定请求的同步和异步方法。 如果调用 BeginGetRequestStream 方法,则必须使用 BeginGetResponse 方法来检索响应。
注意
在应用程序中启用网络跟踪时,此成员将输出跟踪信息。 有关详细信息,请参阅 .NET Framework中的