18

我有一个使用 SignalR 的小项目,但是我得到了一些非常不一致的行为。

<script type="text/javascript">
    $(function () {
        var chat = $.connection.brewBattleHub;
        $.connection.hub.start().done(function () {
            $("#broadcast").click(function () {
                // Call the chat method on the server
                chat.server.roll($("#username").val(), $("#drinkname").val());
            });
            chat.server.sendMessage("SignalR loaded...");
        });
    });
</script>

当我加载页面时,有时我会看到消息“SignalR 已加载”,有时我没有。

页面上还有一些其他功能,有时这也不起作用。如果我单击按钮并使事情发生得足够多,它最终会一口气完成……从这一点开始,一切都是金色的,并且可以完美运行。

start().done()吗?不确保一切准备就绪?

=== 附录,我没有引用 jquery mobile(谷歌提到这样做时有一个错误)

4

4 回答 4

15

本周我遇到了类似的问题,只是 .done() 中的代码从未运行过。我启用了日志记录,但没有记录任何内容。检查浏览器的控制台没有错误。查看浏览器的开发工具,我可以看到调用 start() 时没有网络活动。我确认 $.connection.myhubclass 返回的代理有我所有的方法,所以我知道它可以与服务器对话并且服务器端代码设置正确。

在一遍又一遍地查看代码和文档之后,我确信我没有做错任何事情。SignalR 非常简单,如果您按照示例进行操作,很难做错。我在桌子上敲了很长时间,试图弄清楚这一点。

然后我注意到,如果我从控制台运行 SignalR 的 start 方法,它会起作用。这让我相信它试图过早地开始连接。我通过更改初始化代码解决了我的问题:

$.connection.hub.start().done(function () {
  //Do interesting stuff
});

对此:

setTimeout(function () {
    $.connection.hub.start().done(function () {
      //Do interesting stuff
    });
}, 5000);

我确信我可以将延迟从 5 秒减少到更短的时间,但额外的时间似乎是让浏览器自己准备好创建连接所需要的时间。一旦出现延迟,日志记录开始工作,连接出现,服务器端 OnConnected() 运行,并且 done() 在客户端上运行。

在弄清楚这一点后,我仔细检查了我的 javascript 加载顺序,认为我可能正在加载一些乱序的东西,但根据 SignalR 示例,顺序是正确的。我加载 jQuery、SignalR、/signalr/hubs,然后是初始化所有内容的脚本文件。

我愿意接受有关为什么需要延迟的建议。我在任何文档中都没有看到它,所以我知道这可能是我所做的。幸运的是,对于这个页面来说,在启动 SignalR 之前的轻微延迟不是问题。

于 2013-06-06T23:21:32.877 回答
12

尝试启用 SignalR 日志记录以帮助调试您的问题。您可能还想添加一个fail处理程序以防启动不成功(尽管这不太可能)。完成此操作后,您可以通过浏览器的 F12 工具查看 JS 和网络日志。

<script type="text/javascript">
    $(function () {
        $.connection.hub.logging = true;
        var chat = $.connection.brewBattleHub;
        $.connection.hub.start().done(function () {
            $("#broadcast").click(function () {
                // Call the chat method on the server
                chat.server.roll($("#username").val(), $("#drinkname").val());
            });
            chat.server.sendMessage("SignalR loaded...");
        }).fail(function (reason) {
            console.log("SignalR connection failed: " + reason);
        });
    });
</script>
于 2013-03-07T19:15:04.273 回答
3

我找到了解决方案(就我的问题而言)。我在 IE11 上加载了大约 7-8 秒的 SignalR,我尝试在控制台中“调试”它,我找到了加载延迟的原因:

[13:13:04 GMT+0200 (...)] SignalR:绑定到 iframe 的加载事件。
[13:13:09 GMT+0200 (...)] SignalR:尝试连接时,foreverFrame 超时。
[13:13:09 GMT+0200 (...)] SignalR:永远停止帧。

花了5秒。尝试加载 iframe。

巧妙的解决方案是关闭 iframe,因为 IE11 可以正常使用 longPolling:

$.connection.hub.start(({ transport: ['webSockets', 'serverSentEvents', 'longPolling'] }))
于 2014-07-21T11:19:36.547 回答
0

我有一个类似的问题,仅在断开连接后尝试重新建立连接时出现。我从断开处理程序调用 start(),然后尝试从 start.done() 发送消息。然后我收到一条错误消息,指出 SignalR 尚未准备好。

我在日志中注意到 start.done() 立即解决,所以在我的情况下,有一个从断开连接开始然后发送的呼叫。我在断开连接处理程序中添加了一个 setTimeout,以便启动和发送与断开连接分离。这为我解决了这个问题。

于 2015-05-02T20:58:34.310 回答