New Research: Supply Chain Attack on Axios Pulls Malicious Dependency from npm.Details →
Socket
Book a DemoSign in
Socket

nuxt-ws

Package Overview
Dependencies
Maintainers
0
Versions
3
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

nuxt-ws

A Nuxt module aimed to simplify the use of WebSockets.

latest
Source
npmnpm
Version
0.0.3
Version published
Maintainers
0
Created
Source

Nuxt WebSocket

npm version npm downloads License Nuxt

A Nuxt module aimed to simplify real-time communication with built-in automatic topic subscriptions, reactive shared state management, and type safety.

Features

  • useWS (demo): A WebSocket implementation with built-in shared state management, topic subscriptions, and type safety.
  • defineWSHandler: wraps Nitro's defineWebSocketHandler to provide additional configuration, hooks and automatic topic subscription.

Quick Setup

Install the module to your Nuxt application with one command:

npx nuxi module add nuxt-ws

Ideally you should set your default path, based on where you will place your WebSocket api handlers:

export default defineNuxtConfig({
  modules: ['nuxt-ws'],

  ws: {
    path: '/_ws', // default undefined
  }
})

Real-time Remote State Management

A WebSocket implementation with built-in shared state management, topic subscriptions, and type safety.

  • 🔄 Automatic reconnection
  • 📦 Built-in shared state management per-topic
  • 🤖 Build-in validation with Standard Schema
  • 🔐 Type-safe messages and topics
  • 📢 Hooking system to trigger messages globaly
  • ⛓️ Integrates easily with other Nuxt modules

Take in example the following setup:

// nuxt.config.ts
export default defineNuxtConfig({
  modules: ['nuxt-ws'],
  ws: {
    route: '/_ws',             // WebSocket endpoint to auto-connect
    topics: {
      defaults: ['session'],   // Auto-subscribed topics
    }
  }
})

Client-Side (pages/chat.client.vue):

<template>
  <div>
    <div v-if="status === 'OPEN'">
      Connected, Users: {{ states['session'].users }}
    </div>
    <div v-else>
      Disconnected
    </div>
    <div v-for="({ user, text }, key) in states['chat']" :key>
      {{ user }}: {{ text }}
    </div>
    <input v-model="textRef" @keyup.enter="sendMessage()">
  </div>
</template>

<script setup lang="ts">
const textRef = ref('')
const { states, status, send } = useWS<{
  chat: {
    user?: string
    text: string
  }[]
  session: {
    users: number
  }
}>(['chat'])

function sendMessage() {
  send('publish', 'chat', {
    text: textRef.value,
  })
  textRef.value = ''
}
</script>

Server-Side (server/routes/_ws.ts):

import * as v from 'valibot'

export default defineWSHandler({
  async open(peer) {
    // Update peer with 'chat' data from storage
    const chat = await useStorage('ws').getItem('chat')
    if (chat)
      peer.send(JSON.stringify({
        topic: 'chat',
        payload: chat,
      }), { compress: true })

    // Update everyone's session metadata
    const payload = JSON.stringify({ topic: 'session', payload: { users: peer.peers.size } })
    peer.send(payload, { compress: true })
    peer.publish('session', payload, { compress: true })
  },

  async message(peer, message) {
    // Validate the incoming chat message
    const parsedMessage = await wsValidateMessage( // built-in validation util
      v.object({
        type: v.literal('publish'),
        topic: v.literal('chat'),
        payload: v.object({ text: v.string() }),
      }),
      message,
    )

    // Update chat data in storage
    const mem = useStorage('ws')
    const { topic, payload } = parsedMessage
    const _chat = await mem.getItem<Array<{ user: string, text: string }>>('chat') || []
    const newChat = [..._chat, { ...payload, user: peer.id }]
    await mem.setItem(topic, newChat)

    // Broadcast the updated chat to everyone
    peer.send(JSON.stringify({ topic, payload: newChat }), { compress: true })
    peer.publish(topic, JSON.stringify({ topic, payload: newChat }), { compress: true })
  },

  close(peer) {
    // Update everyone's session metadata
    peer.publish(
      'session',
      JSON.stringify({
        topic: 'session',
        payload: {
          users: peer.peers.size,
        },
      }),
      { compress: true },
    )
  },
})

Contribution

Local development
# Install dependencies
pnpm install

# Generate type stubs
pnpm run dev:prepare

# Develop with the playground
pnpm run dev

# Build the playground
pnpm run dev:build

# Run ESLint
pnpm run lint

# Run Vitest
pnpm run test
pnpm run test:watch

License

Published under the MIT license.

FAQs

Package last updated on 16 Mar 2025

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts