如何在 Nuxt 3 中启动 websocket 服务器(socketIO 或其他)?与 Nuxt 2 中的工作方式不同

ahb*_*ork 7 javascript sockets websocket socket.io nuxt.js

我正在尝试将我的代码从 Nuxt 2 转换为 Nuxt 3,并且在 Nuxt 3 中创建 websocket 服务器时遇到了问题。

使用以下代码在 Nuxt 2 中运行得非常好:

// Nuxt 2: modules/socket.js
import http from 'http'
import socketIO from 'socket.io'

export default function () {
    this.nuxt.hook('render:before', () => {
        const server = http.createServer(this.nuxt.renderer.app)
        const io = socketIO(server)

        this.nuxt.server.listen = (port, host) => new Promise(resolve => server.listen(port || 3000, host || 'localhost', resolve))
        this.nuxt.hook('close', () => new Promise(server.close))

        io.on('connection', (socket) => {
            console.log("CONNECTED")
        })
    })
}
Run Code Online (Sandbox Code Playgroud)
// Nuxt 2: plugins/socket.client.js
import io from 'socket.io-client'
const socket = io('http://localhost:3000')

export default ({}, inject) => {
    inject('socket', socket)
}
Run Code Online (Sandbox Code Playgroud)
<!-- Nuxt 2: pages/index.vue -->
<template>
<div>
    <p>Check socket status in Vue devtools...</p>
</div>
</template>

<script>
export default {
    computed: {
        socket() {
            return this.$socket ? this.$socket : {};
        }
    }
}
</script>
Run Code Online (Sandbox Code Playgroud)

但是,在 Nuxt 3 中,我无法访问this.nuxt.renderer.appmodules/socket.js文件(for http.createServer(...)),并且我无法弄清楚如何renderer.app在 Nuxt3 模块中的其他地方访问正确的内容。我的 Nuxt 3 代码如下所示:

// Nuxt 3: modules/socket.js
import http from 'http'
import socketIO from 'socket.io'

export default (_, nuxt) => {
    // Note that I use the 'ready' hook here - render:before is apparently not included in Nuxt3.
    nuxt.hook('ready', renderer => {
        // nuxt.renderer is undefined, so I've tried with renderer.app instead, with no luck.
        const server = http.createServer(renderer.app)
        const io = socketIO(server)

        nuxt.server.listen = (port, host) => new Promise(resolve => server.listen(port || 3000, host || 'localhost', resolve))
        nuxt.hook('close', () => new Promise(server.close))
            
        io.on('connection', () => {
            console.log("CONNECTION")
        })
    })
}
Run Code Online (Sandbox Code Playgroud)
// Nuxt 3: plugins/socket.client.js
import io from 'socket.io-client'

export default defineNuxtPlugin(() => {
    const socket = io('http://localhost:3000')

    return {
        provide: {
            socket: socket
        }
    }
})
Run Code Online (Sandbox Code Playgroud)
<!-- Nuxt 3: app.vue -->
<template>
  <div>
      <p>Check socket status in Vue devtools...</p>
  </div>
</template>

<script setup>
    const { $socket } = useNuxtApp()    
</script>
Run Code Online (Sandbox Code Playgroud)

我会为你创建一个codesandbox链接,但每次我尝试时,它都会在我添加任何代码之前就中断。我认为它还不能正确地与 Nuxt3 一起工作。有人在 Nuxt 3 模块中成功建立了 websocket 服务器吗?或者有人能看到我缺少什么吗?

我对任何可行的解决方案都感兴趣,但不一定是socket.io

ahb*_*ork 9

我想到了!

深入研究 Nuxt 3 代码,发现他们有一个listen钩子,它提供了server我设置服务器所需的参数。不过,这些信息确实很难找到。

我还设法简化了脚本一点。

这是更新的modules/socket.js

import { Server } from 'socket.io'

export default (_, nuxt) => {
    nuxt.hook('listen', server => {
        const io = new Server(server)

        nuxt.hook('close', () => io.close())
        
        io.on('connection', () => {
            console.log("CONNECTION")
        })
    })
}
Run Code Online (Sandbox Code Playgroud)

其他一切都可以保持不变