2013-03-15 151 views
0

我有执行长处理的页面(写一些PDF的地方),所以我有以下几点:长处理线程异步ASP.NET网页

我ArchiveDoc.aspx页: (页已经在页面指令一个标签(称为进度)和异步=“真”)

delegate void archiveFuncDelegate(int idTurnover, string serverMapPath); 
delegate void UpdateUIDelegate(string Text); 

protected void Page_Load(object sender, EventArgs e) 
{ 
    Page.AddOnPreRenderCompleteAsync(BeginTask, EndTask); 
    this.progress.Text = "0"; 
} 

private void UpdateUI(string Text) 
{ 
    this.progress.Text = Text; 
} 

private IAsyncResult BeginTask(object sender, EventArgs e, AsyncCallback cb, object state) 
{ 

    // invoke 
    archiveFuncDelegate del = asyncArchivageFacture; 
    IAsyncResult result = del.BeginInvoke(cb,null); 
    return result; 
} 

private void EndTask(IAsyncResult ar) 
{ 
    if (!ar.IsCompleted) 
    { 
     progress.Text = "Error"; 
    } 
    else 
    { 
     progress.Text = "OK"; 
    } 
} 

#region Archive (thread) 

// long processing task (exemple) 
public void asyncArchivageFacture() 
{ 
    // exemple 
    int total = 101; 
    int progress = 0; 

    for(int i=0; i<total; i++) 
    { 
     progress = i*100/total; 
     updateUi.Invoke(progress + "%"); 
     Thread.Sleep(2000); 
    } 

} 

#endregion 

当我把我的页面,该线程调用(asyncArchivageFacture()还有UpdateUI()),但网页永远不会得到更新:我在浏览器中得到了一个空白页面的加载符号,并且一旦线程完成,该页面最后显示'OK'。它不显示进度(10%.. 20%..)

任何想法有什么不对? 谢谢!

+1

HTTP是无状态的。您需要一个ajax组件来轮询进度。或者,看看SignalR。 – 2013-03-15 10:35:03

回答

1

这是因为响应(html)仅在调用EndTask方法后才发送给客户端。无论您对进度做出什么样的改变,文本都在服务器端,您只需更改服务器端变量。

+0

所以,你说我应该从asyncArchivageFacture()开始另一个线程,以便asyncArchivageFacture()立即返回? – TGI 2013-03-15 10:40:16

+0

正如David Tryon所指出的那样,由于http是无状态的,所以你不能将结果发送回客户端。客户端(浏览器/移动设备)请求此页面并期待响应(本例中为html)。直到发生(或发生错误),Tcp连接将由客户端保持活动状态。您可以使用Ajax调用在客户端显示进度,方法是重复向服务器询问进度。总之,你的问题的答案是否定的。你不能通过启动另一个线程来实现它。你应该使用重复的Ajax调用 – guruprasath 2013-03-15 10:45:03

+0

我不明白,如果页面等待EndTask()(即线程)完成,那么异步方面在哪里?它是阻塞的,而不是异步的,然后.. – TGI 2013-03-15 14:22:32

0

最后我用一个简单的

线程t =新主题(..)

没有delaring页面异步=真。