Namespaces
A Namespace is a communication channel that allows you to split the logic of your application over a single shared connection.
Possible use cases:
- you want to create an admin namespace that only authorized users have access to, so the logic related to those users is separated from the rest of the application
const adminNamespace = io.of('/admin'); |
- your application has multiple tenants so you want to dynamically create one namespace per tenant
const workspaces = io.of(/^\/\w+$/); |
Default namespace
We call the default namespace /
and it’s the one Socket.IO clients connect to by default, and the one the server listens to by default.
This namespace is identified by io.sockets
or simply io
:
// the following two will emit to all the sockets connected to `/` |
Each namespace emits a connection
event that receives each Socket
instance as a parameter
io.on('connection', socket => { |
Custom namespaces
To set up a custom namespace, you can call the of
function on the server-side:
const nsp = io.of('/my-namespace'); |
On the client side, you tell Socket.IO client to connect to that namespace:
const socket = io('/my-namespace'); |
Important note: The namespace is an implementation detail of the Socket.IO protocol, and is not related to the actual URL of the underlying transport, which defaults to /socket.io/…
.
Namespace middleware
A middleware is a function that gets executed for every incoming Socket, and receives as parameters the socket and a function to optionally defer execution to the next registered middleware. A Socket.IO middleware is very similar to what you can find in Express.
// registers a middleware for the default namespace |
You can register several middleware functions for the same namespace. They will be executed sequentially:
io.use((socket, next) => { |
Handling middleware error
If the next
method is called with an Error object, the client will receive an connect_error
event.
import { io } from 'socket.io-client'; |
Compatibility with Express middleware
Most existing Express middleware modules should be compatible with Socket.IO, you just need a little wrapper function to make the method signatures match:
const wrap = middleware => (socket, next) => middleware(socket.request, {}, next); |
The middleware functions that end the request-response cycle and do not call next()
will not work though.
Example with express-session:
const session = require('express-session'); |
Example with Passport:
const session = require('express-session'); |
A complete example with Passport can be found here.