问题描述
我具有处理CSV文件中的数据并将日志写入数据库的功能。我还想在UI中显示通知或警报,以便我可以立即知道系统中正在发生什么。我尝试了敬酒通知和警报,但循环结束后仅显示一次。
这是我的代码:
AddLog(finalJobId,taskId,"Sending batch to Payment Gateway # of Records:" + JobCount + " from" + txtCSVFile.Text);
for (int i = 0; i < JobCount; i++)
{
var items = csvLists[i];
Page.ClientScript.RegisterStartupScript(this.GetType(),"ShowMessage",string.Format("<script type='text/javascript'>alert('{0}')</script>","The Payment is being proceed for : " + items["First Name"] + " " + items["Last Name"]));
var paymentId = items["Payment Id"];
var clientId = items["Client Id"];
var client = items["Client Name"];
var amount = items["Total Payment Amount"];
var method = items["Payment Method"];
AddLog(finalJobId,"Sending payment #" + i + "- Client: " + client + " - PaymentId: " + paymentId + " - Amount: " + amount + " - Payment Method: " + method);
//Process Actual Payment Options with Details
var task = Processpayment.Process(int.Parse(clientId),int.Parse(paymentId),serverValue);
AddLog(finalJobId,"Received Response #" + i + " - Client: " + client + " - PaymentId: " + paymentId + " - Amount: " + amount + " - Payment Method: " + method + " - Result: " + task.Result.Response);
}
AddLog(finalJobId,"Completed batch for Payment Request # of Records:" + JobCount);
我通常在CSV文件中有200多个记录,因此在付款后我必须等待一段时间。我不知道显示通知的最佳方法是什么,以便用户了解当前情况。
解决方法
好吧,最简单的方法可以解决这个问题?
好吧,当您单击按钮时,页面(回发)将发送到服务器。
您的代码运行-后面的所有代码都被阻塞,直到完成为止。(您无法从该网页进行其他调用。该网页“卡在”服务器端区域,等待代码完成。 / p>
代码最终完成后,页面将被向下发送回客户端。
因此,显然这行代码不起作用:
Page.ClientScript.RegisterStartupScript(this.GetType(),"ShowMessage" bla bla
由于上述原因,长延迟代码开始运行。仅在长时间运行的代码完成之后,然后代码存根才完成,然后将整个页面发送回客户端。 (包括以上希望运行某些js的想法-仅在将页面向下发送回客户端后才开始运行。
那么,有很多方法可以做到,就像冰淇淋口味一样,但是最简单吗?
好吧,无论他们单击哪个按钮启动您上面的代码,都只需要在回发之前向您的敬酒消息客户端显示即可。
因此,您弹出吐司,然后运行代码。我们甚至不必编写代码来消除/隐藏/关闭/删除消息,因为当页面滚动到浏览器时会回滚吗?
好吧,整个页面会在客户端重新为您加载,因此您的吐司消息将消失。
因此这是“最”容易的。但这确实意味着网页已被很大程度地阻止了交互,并且我们正在等待该网页的完整副本从服务器中缩小,直到长时间运行的代码最终完成。
所以,超级简单:
我们假设您在表单上有一个asp.net按钮。 我们假设用户将单击该按钮,然后运行您的代码。 请注意,网页将返回到服务器,然后您的代码将运行。 在该代码运行并完成之前,网页不会返回到客户端。
如前所述,我们可以利用这种效果来发挥优势。
因此,单击asp按钮可以使用OnClientClick()。这意味着客户端代码(js)将在您的服务器单击之前运行(运行后的代码)。
它也可以在回发到服务器之前运行。 (网页访问服务器)。
因此,我们用它来显示一个“ div”,或填写一个文本框,或者在您的情况下显示一些敬酒信息。
因此,按钮代码为:
<asp:Button ID="Button2" runat="server" Text="Confirm my order"
OnClientClick="GoGo2()" />
因此,以上是我们可爱的标准ASP按钮。但是,请注意“ OnClientClick”。 因此,它将同时运行客户端和服务器端事件。但是它将首先运行我们调用的客户端代码(客户端例程称为GoGo2())。
该客户端例程因此可以显示该消息。 上面调用了我们的客户端代码存根,这样说:
<script>
function GoGo2() {
$.toast({
heading: "Working",text: 'Processing order - - please wait',hideAfter: false,position: 'top-right',icon: 'info'
})
}
</script>
现在,您当然可以获取/抓取/拉取/使用文本框或其他控件(客户端)的值来创建“更好”的消息。 因此消息可能会说:
heading: "Order #" + $('#txtBoxOrderNum').val(),text: 'Processing order please wait',
或该网页上的其他内容。请注意,我们只能在网页中获取/获取/使用当前值(后面的代码中没有服务器端的值)。
所以,现在我们有了这个:
用户单击按钮。
显示以上吐司消息(我们的客户端js)。
您可以在文本框中显示(推)信息,甚至隐藏/显示“ div”,甚至不使用吐司。但是某种吐司插件就可以了。
现在该例程开始运行,显示您的消息客户端。
当网页跳至服务器时。然后,该按钮单击后面的代码开始运行。完成长时间运行的代码后,然后页面THEN会将旅程返回浏览器。
因为我们在浏览器端获得了一个全新的页面?
那么,吐司消息将被吹散(消失),因此,由于我们刚刚收到了新的网页副本,因此我们不需要代码来更新或隐藏消息!
所以上面是最简单的。
如果进程正在运行,要多说几秒钟,比如说25秒?好吧,您不想那么长时间封锁整个网页。 (所有其他(服务器端代码)和所有按钮都将被冻结。
在那种情况下?好吧,那么我们需要使用一个线程对象,并将调用移出一个单独的线程。 (这很容易做到)。
现在,单击按钮和浏览器往返将非常快。
但是,对于状态更新,我们必须在页面返回客户端之后开始运行代码。 (您可以尝试使用该脚本来注入脚本)。
但是,如果您要进行状态更新,则通常最好不要回发信息。
jQuery.AJAX调用非常简单,您可以在现有页面上调用Web方法(无需为此设置Web服务器页面(asmx)。
实际上,如果您真的要进行流程更新(例如完成百分比),或者在长时间的处理过程中显示几条消息?我们将要避免发回邮件,并避免发回邮件阻塞。一种方法是使用更新面板。但是无论如何,您的主页都必须退出长时间运行的进程,并且不要被阻塞(永远!!!)。
我可以在此页面上添加一个编辑以包括jQuery AJAX调用,但是以上内容非常简单,我认为对于此示例来说已经足够了。
这种方法非常简单-无需引入新技术,ajax调用或signalR概念。
即使您确实引入了signalR,您仍然必须花费很长的时间才能确保浏览器往返不被阻塞。
如前所述,在这些情况下(想要更新状态百分比等),那么我真的(不,但是真的)不做回发。因此,明智的做法是使用AJAX调用开始整个过程和状态更新。
并且由于我们认为在需要状态更新系统(完成百分比等)时避免回发是最实用的,所以一些简单的ajax调用工作量较小,并且无论如何都要比signalR设置容易。