ScriptManager.RegisterStartupScript 不断添加脚本块多次

Posted

技术标签:

【中文标题】ScriptManager.RegisterStartupScript 不断添加脚本块多次【英文标题】:ScriptManager.RegisterStartupScript Keeps adding script blocks multiple times 【发布时间】:2012-09-04 20:49:09 【问题描述】:

我有一个带有计时器控件的更新面板,它设置为每分钟左右自动检查一些数据更新。

如果它看到数据更新,则设置为使用序列化的 JSON 数据调用本地脚本。

ScriptManager.RegisterStartupScript(UpdateField, GetType(HiddenField), ACTION_CheckHistoryVersion, "updateData(" & data & ");", True)

“数据”可能看起来像


   "someProperty":"foo",
   "someOtherProperty":"bar",
   "someList":[
     "prop1":"value",
     "prop2":"value", ...
   ],
   "someOtherList":[,...,]

“数据”可以变得非常大,有时只有少数项目发生变化。

我遇到的问题是这样的。每次我将此发送回客户端时,它都会作为全新的脚本块添加,并且现有块不会被删除或替换。

输出看起来像这样:

<script type="text/javascript">
  updateData(
       "someProperty":"foo",
       "someOtherProperty":"bar",
       "someList":[
         "prop1":"value",
         "prop2":"value", ...
       ],
       "someOtherList":[,...,]
    );
</script>
<script type="text/javascript">
  updateData(
       "someProperty":"foo",
       "someOtherProperty":"bar",
       "someList":[
         "prop1":"changed",
         "prop2":"val", ...
       ],
       "someOtherList":[,...,]
    );
</script>
<script type="text/javascript">
  updateData(
       "someProperty":"foos",
       "someOtherProperty":"ball",
       "someList":[
         "prop1":"changed",
         "prop2":"val", ...
       ]
    );
</script>

每次数据发生变化时都会创建一个新的脚本块。

随着时间的推移,如果我们继续添加它,浏览器上累积的数据量可能会变得非常庞大,我无法想象大多数人的浏览器会如何接受它,但我认为它不会很好。

有谁知道是否有办法只替换已发送回浏览器的代码,而不是像这样不断添加它?

【问题讨论】:

我发现了一个 hack,我已经编辑了我的问题来展示它。 可以简单的使用webservice吗? 请考虑将您的 hack 发布为答案,而不是更新您的问题,因为这是正确的协议。如果在延迟期间没有更好的结果,我们甚至鼓励您接受自己的答案。 好的,从问题中删除修复并添加为答案。当我将它添加到问题中时,我假设我无法在同一天回答我自己的问题。这曾经是这里的工作方式。也许情况发生了变化,而我没有意识到。 【参考方案1】:

我想出了一个似乎适用于我的情况的技巧。

我正在使用 jQuery 来查找我正在创建的脚本标签,并在它被调用后将其删除。

这是一个例子:

首先我生成一个 guid:

Dim guidText as string = GUID.NewGuid().ToString()

我创建了如下函数:

function RemoveThisScript(guid)

   $("script").each(function()
     var _this = $(this);
     if(_this.html().indexOf(guid)>-1)
        _this.remove();
   );


然后我将以下代码添加到我的输出字符串中:

... & " RemoveThisScript('" & guidText & "');"

这会导致 jQuery 在页面上的所有脚本中查找具有 GUID 的脚本(本质上是调用函数的脚本)并将其从 DOM 中删除。

【讨论】:

【参考方案2】:

我建议使用 web 服务和一些你将在 window.setInterval 中调用的 web 方法。在您的 webmethod 的成功处理程序中(在客户端),您可以只接受响应并使用它做任何您想做的事情。而且它不会保存在您的页面中(好吧,如果您做错了一切)。好处是您将最小化请求大小(更新面板将传递所有可能足够大的视图状态数据)并限制服务器资源的使用(更新面板导致整个页面的生命周期,假设稍微修改,但无论如何 - 所有这些 page_load, page_init 等...),并且使用 Web 服务,您将只需要您需要的东西。

Here 是一篇文章,您可以在其中了解如何在客户端创建和使用它。看起来足够好。

【讨论】:

所以,这是一个选项,确实,我已经看过 encosia.com/… ,但它需要更多的工作。在页面背后的代码中,我们的组织有许多利用页面上下文进行处理的对象,虽然我可以做很多工作来手动将它们连接到页面上下文,但我的偏好是不必这样做,因为它不是微不足道的。由于这个答案对大多数人来说都是正确的,所以我会接受它作为答案。

以上是关于ScriptManager.RegisterStartupScript 不断添加脚本块多次的主要内容,如果未能解决你的问题,请参考以下文章