简体   繁体   English

中止HttpWebRequest无法正常工作

[英]Abort HttpWebRequest won't working

I am using this method to get google suggest query: 我正在使用这种方法来获取谷歌建议查询:

public void GetSuggestFromGoogle(string query)
    {
        try
        {
            query = HttpUtility.UrlEncode(query);
            string targetUrl = "http://suggestqueries.google.com/complete/search?ds=yt&output=toolbar&hl=en-US&q=" + query;

            UTF8Encoding utf8 = new UTF8Encoding();
            byte[] bytes = utf8.GetBytes(targetUrl);
            targetUrl = targetUrl.ToString();

            request = HttpWebRequest.Create(new Uri(targetUrl)) as HttpWebRequest;
            request.Method = "GET";

            IsDownload = true;
            request.BeginGetResponse(new AsyncCallback(FinishWebRequest), request);
        }
        catch
        {
            IsDownload = false;
            failCallback();
        }


    }

And before i call this method i use: 在我调用此方法之前,我使用:

public void CancelGoogleRequest()
    {
        if (IsDownload)
        {
            request.Abort();
            IsDownload = false;
        }
    }

and this is the Finish Request Method: 这是完成请求方法:

private void FinishWebRequest(IAsyncResult result)
    {
        try
        {
            HttpWebResponse wResponse = (result.AsyncState as HttpWebRequest).EndGetResponse(result) as HttpWebResponse;
            Stream stream = wResponse.GetResponseStream();

            StreamReader reader = new StreamReader(stream);
            string xml = reader.ReadToEnd();

            List<string> list = this.ParseXml(xml);
            finishCallback(list);
            IsDownload = false;
        }
        catch//(Exception erere)
        {
            IsDownload = false;
            failCallback();
        }
    }

And my issue is with the Abort of HttpWebRequest , even if i am aborting request before calling a new one the FinishWebRequest method is execute, It is possible to cancel it? 我的问题是HttpWebRequest的中止,即使我在调用新的FinishWebRequest方法执行之前中止请求,也可以取消它吗?

From the Remarks section in HttpWebRequest.Abort : HttpWebRequest.Abort的“备注”部分中:

The Abort method will synchronously execute the callback specified to the BeginGetRequestStream or BeginGetResponse methods if the Abort method is called while either of these operations are outstanding. 如果在任何一个操作未完成时调用Abort方法,则Abort方法将同步执行为BeginGetRequestStream或BeginGetResponse方法指定的回调。

So you can't avoid the call. 因此,您无法避免拨打电话。 But you already have your IsDownload flag and could use it this way: 但是您已经有了IsDownload标志,可以通过以下方式使用它:

private void FinishWebRequest(IAsyncResult result)
{
    if (IsDownload)
    {
        // handle response
    }
}

when you change the Cancel method like this: 当您像这样更改Cancel方法时:

public void CancelGoogleRequest()
{
    if (IsDownload)
    {
        IsDownload = false; // set before Abort
        request.Abort();
    }
}

UPDATE: In case you can't use the IsDownload flag you could simply rely on the following (also from the Remarks): 更新:如果您不能使用IsDownload标志,则可以简单地依赖以下内容(同样来自备注):

The Abort method cancels a request to a resource. Abort方法取消对资源的请求。 After a request is canceled, calling the GetResponse, BeginGetResponse, EndGetResponse, GetRequestStream, BeginGetRequestStream, or EndGetRequestStream method causes a WebException with the Status property set to RequestCanceled 取消请求后,调用GetResponse,BeginGetResponse,EndGetResponse,GetRequestStream,BeginGetRequestStream或EndGetRequestStream方法会导致WebException,其Status属性设置为RequestCanceled

As you already have a try block around your response handling code, everything should be ok. 由于您已经在响应处理代码周围有了一个try块,因此一切正常。 However you shouldn't set IsDownload = false in the exception handler when a new request has already been started, at least not when the WebException Status is RequestCanceled : 然而,你不应该设置IsDownload = false的,当一个新的请求已经启动的异常处理程序,至少不会在引发WebException状态是RequestCanceled

private void FinishWebRequest(IAsyncResult result)
{
    try
    {
        // handle response
    }
    catch (WebException webEx)
    {
        if (webEx.Status != WebExceptionStatus.RequestCanceled)
        {
            IsDownload = false;
            failCallback();
        }
    }
    catch
    {
        IsDownload = false;
        failCallback();
    }

}

Another idea. 另一个想法。 As Abort calls the FinishWebRequest callback synchronously, you may use an IsAborted flag like this: Abort同步调用FinishWebRequest回调时,您可以使用IsAborted标志,如下所示:

public void CancelGoogleRequest()
{
    if (IsDownload)
    {
        IsDownload = false; // set before Abort
        IsAborting = true;
        request.Abort();
        IsAborting = false;
    }
}

with a callback like this: 像这样的回调:

private void FinishWebRequest(IAsyncResult result)
{
    if (!IsAborting)
    {
        // handle response
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM