Skip to content

Releases: colyseus/colyseus

colyseus v0.17.9

11 Apr 00:09

Choose a tag to compare

Vite Integration

First-class Vite plugin that lets you develop and build your multiplayer game from a single config.

npm install colyseus vite

Setup — create a vite.config.ts:

import { defineConfig } from 'vite';
import { colyseus } from 'colyseus/vite';

export default defineConfig({
  plugins: [
    colyseus({
      serverEntry: '/src/server/index.ts',
      serveClient: true,
    }),
  ],
});

Server entry — define rooms, routes, and middleware in one place:

// src/server/index.ts
import { defineServer, defineRoom, createRouter, createEndpoint, monitor } from 'colyseus';
import { MyRoom } from './MyRoom';

export const server = defineServer({
  rooms: {
    my_room: defineRoom(MyRoom),
  },

  express: (app) => {
    app.use('/monitor', monitor());
  },

  routes: createRouter({
    hello: createEndpoint("/hello", { method: "GET" }, async (ctx) => {
      return { message: "Hello world!" };
    }),
  }),
});

Run npx vite — client and game server on the same port, no separate process.

Features:

  • Shares Vite's dev HTTP server — WebSocket upgrades for room connections are filtered and forwarded to the Colyseus transport, everything else stays with Vite.
  • /matchmake/* endpoints are injected as middleware — client SDK connects to the same origin, no proxy or CORS needed.
  • Hot module reloading — edit room classes and see changes immediately. Running rooms preserve state and connected clients auto-reconnect.
  • @colyseus/monitor, @colyseus/playground, and any package importing matchMaker work correctly in dev mode.
  • devMode is automatically enabled unless explicitly set to false in defineServer().

Production builds:

npx vite build --app

Produces dist/client/ (static assets) and dist/server/server.mjs (standalone Node.js entry).

When serveClient: true is set, the production server automatically serves the built client files via express.static() with SPA fallback — deploy as a single process:

node dist/server/server.mjs

Plugin options:

  • serverEntry (required) — path to your server entry module.
  • port — port for the production server (default: 2567).
  • serveClient — serve built client files in production via express.static() with SPA fallback (default: false).
  • quiet — suppress per-reload log messages during development.
  • loadWsTransport — custom transport loader (advanced).

@colyseus/ws-transport v0.17.13

11 Apr 00:09

Choose a tag to compare

  • Use MAY_TRY_RECONNECT close code (instead of FAILED_TO_RECONNECT) in devMode when a reconnection token is present but the seat hasn't been reserved yet. This allows the SDK to retry during the brief HMR reload window.

@colyseus/uwebsockets-transport v0.17.20

11 Apr 00:09

Choose a tag to compare

  • Use MAY_TRY_RECONNECT close code (instead of FAILED_TO_RECONNECT) in devMode when a reconnection token is present but the seat hasn't been reserved yet. This allows the SDK to retry during the brief HMR reload window.

@colyseus/h3-transport v0.17.10

11 Apr 00:09

Choose a tag to compare

  • Use MAY_TRY_RECONNECT close code (instead of FAILED_TO_RECONNECT) in devMode when a reconnection token is present but the seat hasn't been reserved yet. This allows the SDK to retry during the brief HMR reload window.

@colyseus/core v0.17.41

11 Apr 00:09

Choose a tag to compare

  • Export registerRoomDefinitions, unregisterRoomDefinitions, RoomDefinitions, and createNodeMatchmakingMiddleware from @colyseus/core (used by colyseus/vite plugin).
  • Silence expected ServerError("disconnecting") in default onBeforeShutdown.

DevMode:

  • fix gracefullyShutdown ordering — reject pending allowReconnection() deferreds before caching room state, so onLeave() cleanup runs first and the cached state doesn't contain stale player data.
  • fix reconnection path seat cleanup — delete _reservedSeats and _reconnections entries after successful reconnection in _onJoin, preventing stale seats from blocking room disposal.
  • _reserveSeat timeout now calls onLeave() for clients that fail to reconnect, cleaning up stale player state.
  • cache and restore the encoder's nextRefId across HMR cycles, ensuring Schema refIds increase monotonically and preventing client-side decoder refId collisions.
  • skip restoring reserved seats without a reconnectionToken (stale allowReconnection from page refresh) to prevent orphaned seats blocking room disposal.
  • use recreatedRoom.seatReservationTimeout instead of hardcoded 20s in reloadFromCache.

@colyseus/bun-websockets v0.17.13

11 Apr 00:09

Choose a tag to compare

  • Use MAY_TRY_RECONNECT close code (instead of FAILED_TO_RECONNECT) in devMode when a reconnection token is present but the seat hasn't been reserved yet. This allows the SDK to retry during the brief HMR reload window.

@colyseus/sdk v0.17.39

08 Apr 15:55

Choose a tag to compare

  • Allow swapping the fetch implementation via fetchFn option in ClientOptions. Automatically falls back to XMLHttpRequest when fetch is unavailable (e.g. Cocos Creator Native). Closes #931 - thanks @liangpei-web for reporting!

@colyseus/sdk v0.17.38

08 Apr 03:31

Choose a tag to compare

  • Fix HTTP response content-type detection using indexOf() instead of includes(), which caused non-JSON responses to be incorrectly parsed as JSON

@colyseus/bun-websockets v0.17.12

08 Apr 03:30

Choose a tag to compare

  • Fix sendBinary requires an ArrayBufferView error by ensuring raw() always passes an ArrayBufferView to Bun's sendBinary()
  • Fix shutdown() not fully releasing the port — use stop(true) to force-close the listener so a new Bun.serve() on the same port gets a fresh handler

@colyseus/core v0.17.40

07 Apr 23:25

Choose a tag to compare

  • Fix endpoints with query params returning 404 when Express app is present. bindRouterToTransport was passing req.url (including query string) to router.findRoute(), causing route mismatches. (thanks @thedomeffm for reporting - #930)
  • Internal onDrop/onLeave errors (e.g. "not joined", "disconnecting", "promise rejected") are no longer logged to stderr. They are now only logged when DEBUG=colyseus:errors is enabled. (thanks @sylvainpolletvillard for reporting)