如何将PageAsyncTask与WebRequest一起用于多个请求?

时间:2011-11-21 15:46:44

标签: asp.net

我的目标是使用单个字符串参数的Web服务。 按照计划,我想从我的数据库中为100个值启动对该Web服务的大约100次调用。 为了优化过程,我认为我需要异步进行WebRequest调用。 我在各种博客上看到了以下代码示例,但无法弄清楚如何调整以满足我的要求。 如何在foreach循环中包装RegisterAsyncTask,通过uri解析BeginAsyncOperation中的WebRequest.Create()?

using System;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Net;
using System.IO;
using System.Text;
using System.Text.RegularExpressions;

public partial class AsyncPageTask : System.Web.UI.Page
{
    private WebRequest _request;

    protected void Page_Load(object sender, EventArgs e)
    {
        PageAsyncTask task = new PageAsyncTask(
            new BeginEventHandler(BeginAsyncOperation),
            new EndEventHandler(EndAsyncOperation),
            new EndEventHandler(TimeoutAsyncOperation),
            null
        );
        RegisterAsyncTask(task);
    }

    IAsyncResult BeginAsyncOperation(object sender, EventArgs e, 
        AsyncCallback cb, object state)
    {
        _request = WebRequest.Create("http://msdn.microsoft.com");
        return _request.BeginGetResponse(cb, state);
    }

    void EndAsyncOperation(IAsyncResult ar)
    {
        string text;
        using (WebResponse response = _request.EndGetResponse(ar))
        {
            using (StreamReader reader = 
                new StreamReader(response.GetResponseStream()))
            {
                text = reader.ReadToEnd();
            }
        }

        Output.Text = text;
    }

    void TimeoutAsyncOperation(IAsyncResult ar)
    {
        Output.Text = "Data temporarily unavailable";
    }
}

我的目的是将响应字符串写回数据库。感谢这是一个额外的问题但是,有没有理由不在EndAsyncOperation方法中包含插入方法调用?

Q&A暗示了我的主要问题,但第四个论点是什么?

1 个答案:

答案 0 :(得分:2)

首先,您需要将其添加到Web.config文件中(默认只有2个):

<configuration>
    <system.net>
        <connectionManagement>
            <add address="*" maxconnection="100" />
        </connectionManagement>
    <system.net>
<configuration>

然后您需要在页面中添加async指令:<%@ Page Async="true" %>

protected void Page_Load(object sender, EventArgs e)
{
    //...first get UriStringArray from db, and then:
    foreach(string uri in UriStringArray)
    {
        var task = new PageAsyncTask(
            new BeginEventHandler(BeginAsyncOperation),
            new EndEventHandler(EndAsyncOperation),
            new EndEventHandler(TimeoutAsyncOperation),
            uri,
            true; //run in parallel
        );
        RegisterAsyncTask(task);
    }
}

IAsyncResult BeginAsyncOperation(object sender, EventArgs e, AsyncCallback cb, object state)
{
    var request = (HttpWebRequest)WebRequest.Create((string)state);
    return request.BeginGetResponse(cb, request);
}

void EndAsyncOperation(IAsyncResult ar)
{
    string text;
    var request = (HttpWebRequest)ar.State;
    using(WebResponse response = request.EndGetResponse(ar))
    {
        using(StreamReader reader = new StreamReader(response.GetResponseStream()))
            text = reader.ReadToEnd();
    }
    //yes, you can insert in db here, even as a new PageAsyncTask - but then must call ExecuteRegisteredAsyncTasks() manually...
}