📜  action cable nuxtjs (1)

📅  最后修改于: 2023-12-03 14:59:10.980000             🧑  作者: Mango

Action Cable + Nuxt.js

Action Cable 是 Rails 中的一项功能,它使得 WebSocket 通讯变得简单。而 Nuxt.js 则是 Vue 的一种服务端渲染框架。如何将二者结合起来,实现一个实时通讯的网站呢?

安装 Action Cable

首先,在 Ruby on Rails 项目中安装 Action Cable。打开项目的 Gemfile,在其中加入:

gem 'actioncable'

然后,在项目根目录下运行 bundle 命令,安装依赖包。

Action Cable 不会自动加入 Rails 项目。让我们手动运行安装命令:

rails action_cable:install

这将会创建 app/channels,以及修改 config/routes.rb。在 routes.rb 中已经帮我们创建了一个 mount 语句,将 Action Cable 挂在到指定的路由上。

Action Cable 还需要 redis 来作为消息队列,因此我们还需要安装并启动 redis 服务。

编写 Channel

在 Action Cable 中,Channel 用来组织 WebSocket 的消息,并将其传递给订阅的客户端。一个 Channel 负责一类消息,而可以有多个客户端订阅它。

首先,让我们为 User 创建一个 Channel。在 app/channels 目录下,创建名为 user_channel.rb 的文件,内容如下:

class UserChannel < ApplicationCable::Channel
  def subscribed
    stream_for current_user
  end
end

上述代码中,UserChannel 继承自 ApplicationCable::Channel。在 subscribed 方法中,我们定义了订阅行为。调用 stream_for 方法将 current_user 订阅到 User 的 Channel 上。

现在,我们已经为 User 创建了一个 Channel。下面,我们来测试一下:

rails console
UserChannel.broadcast_to(User.first, { message: "Hello, user!" })

你应该可以在控制台看到消息传递的结果了。

编写 Nuxt.js 中的 WebSocket

接下来,我们需要在 Nuxt.js 中编写 WebSocket 相关的代码。在实际应用中,建议把这些代码放到 Vuex 中,以便管理。我们在这里为了演示,将代码放在了页面的 mounted 钩子中。

在页面中,首先定义并初始化 WebSocket:

const WebSocket = require('websocket').w3cwebsocket

export default {
  ...
  data() {
    return {
      socket: null
    }
  },
  mounted() {
    this.socket = new WebSocket("ws://localhost:3000/cable")
    this.socket.onmessage = (message) => {
      const data = JSON.parse(message.data)
      console.log('Received message:', data)
    }
  }
  ...
}

WebSocket 的查询参数和 Rails 的 session 类似,需要传递一个 token 参数。其值可以是 cookie 等客户端唯一标识。例如,我们可以在 Nuxt.js 中将 token 保存在 Vuex 的 state 中,并在 WebSocket 初始化时将其传递。

当 WebSocket 接收到消息时,我们将消息解析为 JSON,然后打印到控制台。

最后,让我们测试一下:

rails console
UserChannel.broadcast_to(User.first, { message: "Hello, user!" })

你应该可以在控制台看到 Nuxt.js 中接收到消息的结果了。

总结

通过使用 Action Cable,我们可以轻松地在 Rails 中建立一个实时通讯的系统。而 Nuxt.js 则可以使得我们的页面服务端渲染,为我们带来更好的 SEO。将它们结合起来,我们可以创建一个功能强大的实时应用。

在实际使用中,我们可能还需要在 Channel 中处理订阅、取消订阅等事件,以及在 Nuxt.js 中建立一个心跳机制等等。不过,对于一个基本的实时通讯应用来说,以上的代码已经足够了。