Rails 3.1 - JS - Socket.Io-emit in *.js.erb不被执行,并阻止jQuery-Fu

Rails 3.1 - JS - Socket.io-emit in *.js.erb gets not executed and prevents execution of jQuery-Function

本文关键字:执行 jQuery-Fu erb js JS Socket Io-emit in Rails      更新时间:2023-09-26

我想使用node.js与我的rails项目提供异步io。我不想使用神像,faye或类似的东西,因为我需要干净的连接与web-socket,服务器发送的事件和spdy没有替代品。我第一次尝试使用node.js现在是使用Socket。使用JavaScript将数据提供给node.js模块。但它根本不起作用。

我的application.js是这样的

// This is a manifest file that'll be compiled into including all the files listed below.
// Add new JavaScript/Coffee code in separate files in this directory and they'll automatically
// be included in the compiled file accessible from http://example.com/assets/application.js
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// the compiled file.
//
//= require jquery
//= require jquery_ujs
//= require_tree .
window.socket = io.connect('http://localhost:8080/');

在我的application.html.erb:

中正确加载io的要求
 <%= javascript_include_tag "application", "http://localhost:8080/socket.io/socket.io.js" %>

现在我想使用套接字发出一个事件发送到所有监听的客户端,就像在create.js.erb中:

$(function() {
  window.socket.emit('message', <%= @message =>);
};
$("#new_article")[0].reset();

消息是这样在ArticlesCrontroller中创建的:

def create
  @article = current_user.articles.build(params[:article])
  if @article.save
    msg = {:data => @article.to_json}
    @message = msg.to_json
  end
end

我在另一个名为index.js.erb的视图中监听这个事件,方法如下:

$(function() {
  window.socket.on('message', function (msg) {
    $("#articles").prepend(<%= escape_javascript render(Article.new.from_json(msg.data)) %>);
  });
});

套接字。IO看起来像这样:

var io = require('socket.io').listen(8080);
io.sockets.on('connection', function (socket) {
  socket.on('message', function () { });
  socket.on('disconnect', function () { });
});

和似乎工作正确,因为它告诉我如何正确地服务所请求的js-File:

info  - socket.io started
debug - served static /socket.io.js

但是它根本不起作用,尽管create.js.erb会在没有错误的情况下呈现:

Rendered articles/create.js.erb (0.5ms)
Completed 200 OK in 268ms (Views: 70.0ms | ActiveRecord: 14.6ms)

甚至用于重置表单的jQuery-Function也没有执行,如果没有尝试发出套接字事件,它就可以工作。文章被正确地保存到数据库中,所以这不是问题。谁能告诉我问题出在哪里吗?

更新:我通过使用chrome的javascript调试器发现,问题始于窗口的定义。Socket 在application.js中。错误码是:

Uncaught ReferenceError: io is not defined
  (anonymous function)

但是io是在我的application.html.erb中加载的socket.io.js-File中定义的。我为application.js做了一个变通:

$.getScript('http://localhost:8080/socket.io/socket.io.js', function(){
  window.socket = io.connect('http://localhost:8080/');
});

现在的问题是:为什么我必须以这种方式获取脚本,尽管它是在application.html.erb中加载的?但是,尽管有这种解决方法,create.js.erb仍然不能工作。我会在睡一会儿后尝试解决这个问题。

我通常在相关的清单中包含依赖项(在本例中是application.js)。

Rails能够识别许多不同的资产路径,所有这些路径在编译之前都会被检查。我倾向于将(例如socket.io.js)放在vendor/assets/javascripts中,并在清单中添加额外的一行,如下所示:

//= require jquery
//= require jquery_ujs
//= require socket.io
//= require_tree .