我有一个提供实时监控的网页。 基本上,页面每秒通过调用一个实际返回带有更新数据的xml的webform来刷新其内容的一部分。这种方式非常简单,但对我来说听起来并不整齐。
js代码:
setInterval(function () {
GetAgents(responseId);
}, 1000);
//get Agents from b64 encoded xml
function AgentsHtml(b64) {
var html = "<div style=\"float: left; width: 45%; margin: 5px; padding: 5px; background: rgb(255, 255, 255); border-radius: 1px; box-shadow: " +
"4px 4px 6px rgba(0, 0, 0, 0.07); border-color: rgb(186,186,186); border-width: 1px; border-style: solid;\">\r\n@@agentdata@@\r\n</div>\r\n";
var xml = "";
var retVal = "";
try {
xml = decode64(b64);
if (xml != " ") {
var xmlDoc = $($.parseXML(xml));
var Agents = xmlDoc.find("WcfAgent");
Agents.each(function () {
var ActiveState = $(this).find('ActiveState').text();
var ActivityToken = "" + $(this).find('ActivityToken').text();
var Avalabilty = $(this).find('Avalabilty').text();
var Name = $(this).find('Name').text();
var SipUri = $(this).find('SipUri').text();
var StateColor = $(this).find('StateColor').text();
var pic = "/extensions/utsi001/images/dispo55x55.jpg";
if (ActivityToken != "" && ActivityToken != "off-work") {
pic = "/extensions/utsi001/images/conv55x55.jpg";
}
if (ActivityToken == "" && ActiveState == "UnavailableForIncomingCall" &&
(Avalabilty == "DoNotDisturb" ||
Avalabilty == "Busy")) {
pic = "/extensions/utsi001/images/pausa55x55.jpg";
}
if (ActivityToken == "" && Avalabilty == "Offline") {
pic = "/extensions/utsi001/images/off55x55.png";
}
var agent =
" <div style=\"float: left; width: 79%\">\r\n" +
" <p>" + Name + "</p>\r\n" +
" <p style=\"font-size: 12px; padding-left: 3px; margin-bottom: 3px; color: rgb(160,160,160);\">" + SipUri + "</p>\r\n" +
" <div style=\"height: 12px; background-color:" + StateColor + "; border:solid 1px rgb(186,186,186)\"></div>\r\n" +
" </div>\r\n" +
" <div style=\"float: right; width: 20%; margin-top: 5px\">\r\n" +
" <img alt=\"\" src=\"" + pic + "\" />\r\n" +
" </div>"
agent = html.replace("@@agentdata@@", agent);
retVal += agent;
});
}
else {
retVal = "";
}
}
catch (err) {
retVal = b64 + "<br />" + err;
}
return retVal;
}
//return agents ajax call
function GetAgents(responseId) {
link = "/somewhere/agents.aspx";
$.ajax({
type: "POST",
url: link,
data: "",
dataType: "text",
cache: false,
success: function (b64) {
var res = document.getElementById(responseId);
if (res != null && res != undefined) {
res.innerHTML = AgentsHtml(b64);
}
},
error: function (e) {
var res = document.getElementById(responseId);
if (res != null && res != undefined) {
res.innerHTML = e.responseText;
}
}
});
}
我之所以对网络表单进行ajax调用是因为我从自托管的wcf服务中获取数据,而这些服务无法使用javascript直接调用跨域。
请。以上面的代码为例。在我的页面中,我不需要只有一个数据更新..有几个..代理(上面),来电,呼叫队列状态等。
从这一点开始,这是一个新的编辑
感谢Avner的评论,我用SignalR做了一些测试,几乎解决了我的问题。 要清楚问题是:“找到一种方法来避免使用setInterval以任何给定的秒数激活ajax调用”
在提供WCF服务的Windows服务中,我添加了一个SignalR webapp(hub),似乎工作正常。
这是集线器类代码,因为我的需求实际上是在我的服务器服务中发生某些事件后将信息推送到连接的Web客户端:
public class MyHub : Hub
{
//content will be a base64String containing a xml sheet
public void CallRefreshAgents(String content)
{
Clients.All.refreshAgents(content);
}
//...
// others methods just like the above
private static IHubContext _context = null;
public static IHubContext HubContext
{
get
{
if (_context == null)
_context = GlobalHost.ConnectionManager.GetHubContext<MyHub>();
return _context;
}
}
}
因此只需处理代理商存在的变化,我就可以通过简单的电话推送信息:
//pushVal it's a base64String containing a xml sheet
MyHub.HubContext.Clients.All.refreshAgents(pushVal);
在我的Asp.Net Web应用程序中,我只添加了对jquery.signalr.js的引用,在监视页面中,js客户端非常简单:
<head>
<script .... Al references needed .... </script>
<!-- service auto published js code -->
<script src="http://mySignalSelfHostedEndPoint/signalr/hubs"></script>
</head>
<body>
<script type="text/javascript">
var hub = null;
$(function () {
$.connection.hub.url = "http://mySignalSelfHostedEndPoint/signalr";
hub = $.connection.myHub;
$.connection.hub.start().done();
});
</script>
....
<script type="text/javascript">
//for initialization only during load/reload of the page
$(document).ready(
GetAgents("<%=DivIds.sections%>"));
$(function () {
hub.client.refreshAgents = function (b64) {
document.getElementById("<%=DivIds.sections%>").innerHTML = AgentsHtml(b64);
};
});
</script>
MyHub类是否已经很好地实现了? 我真的不需要可以调用“CallRefreshAgents”的客户端,毕竟我想禁止发生这种呼叫
答案 0 :(得分:0)
我刚刚更改了我的集线器课程。
public class MyHub : Hub
{
internal static void RefreshAgents(String pushVal)
{
HubContext.Clients.All.refreshAgents(pushVal);
}
//other methods like the one above
//..
private static IHubContext _context = null;
private static IHubContext HubContext
{
get
{
if (_context == null)
_context = GlobalHost.ConnectionManager.GetHubContext<MyHub>();
return _context;
}
}
}
现在听起来不错。 因此,只有在服务中的命名空间内,我才能调用MyHub.RefreshAgents(&#34; ....&#34;);或者其他......
正如所料,一切正常,客户方也无需进行任何更改。