mirror of
https://github.com/socketio/socket.io.git
synced 2026-01-10 07:28:06 -05:00
The ClusterAdapter class has been moved to [1], so that this adapter
only needs to implement to pub/sub mechanism.
Also, [2] should reduce the number of "timeout reached: only x
responses received out of y" errors, since the fetchSockets() requests
will now succeed even if a server leaves the cluster.
[1]: https://github.com/socketio/socket.io/tree/main/packages/socket.io-adapter
[2]: 0e23ff0cc6
183 lines
5.0 KiB
JavaScript
183 lines
5.0 KiB
JavaScript
const { createServer } = require("http");
|
|
const { Server } = require("socket.io");
|
|
const { createAdapter } = require("..");
|
|
|
|
const httpServer = createServer();
|
|
const io = new Server(httpServer);
|
|
const expect = require("expect.js");
|
|
|
|
io.adapter(createAdapter());
|
|
|
|
let serverSocket;
|
|
|
|
io.on("connection", (socket) => {
|
|
serverSocket = socket;
|
|
});
|
|
|
|
const customNamespace = io.of("/custom");
|
|
|
|
process.on("message", async (msg) => {
|
|
switch (msg) {
|
|
case "broadcasts to all clients":
|
|
io.emit("test", 1, "2", Buffer.from([3, 4]));
|
|
break;
|
|
case "broadcasts to all clients in a namespace":
|
|
customNamespace.emit("test");
|
|
break;
|
|
case "join room1":
|
|
serverSocket.join("room1");
|
|
break;
|
|
case "join room1 & room2":
|
|
serverSocket.join(["room1", "room2"]);
|
|
break;
|
|
case "join room2":
|
|
serverSocket.join("room2");
|
|
break;
|
|
case "broadcasts to all clients in a room":
|
|
io.to("room1").emit("test");
|
|
break;
|
|
case "broadcasts to all clients except in room":
|
|
io.of("/").except("room1").emit("test");
|
|
break;
|
|
case "broadcasts to local clients only":
|
|
io.local.emit("test");
|
|
break;
|
|
|
|
case "broadcasts with multiple acknowledgements": {
|
|
io.timeout(500).emit("test", (err, responses) => {
|
|
expect(err).to.be(null);
|
|
expect(responses).to.contain(1);
|
|
expect(responses).to.contain(2);
|
|
expect(responses).to.contain(3);
|
|
|
|
setTimeout(() => {
|
|
expect(io.of("/").adapter.ackRequests.size).to.eql(0);
|
|
|
|
process.send("ok");
|
|
}, 500);
|
|
});
|
|
break;
|
|
}
|
|
|
|
case "broadcasts with multiple acknowledgements (binary content)": {
|
|
io.timeout(500).emit("test", (err, responses) => {
|
|
expect(err).to.be(null);
|
|
responses.forEach((response) => {
|
|
expect(Buffer.isBuffer(response)).to.be(true);
|
|
});
|
|
|
|
process.send("ok");
|
|
});
|
|
break;
|
|
}
|
|
|
|
case "broadcasts with multiple acknowledgements (no client)": {
|
|
io
|
|
.to("abc")
|
|
.timeout(500)
|
|
.emit("test", (err, responses) => {
|
|
expect(err).to.be(null);
|
|
expect(responses).to.eql([]);
|
|
|
|
process.send("ok");
|
|
});
|
|
break;
|
|
}
|
|
|
|
case "broadcasts with multiple acknowledgements (timeout)": {
|
|
io.timeout(500).emit("test", (err, responses) => {
|
|
expect(err).to.be.an(Error);
|
|
expect(responses).to.contain(1);
|
|
expect(responses).to.contain(2);
|
|
|
|
process.send("ok");
|
|
});
|
|
break;
|
|
}
|
|
|
|
case "get rooms":
|
|
process.send(serverSocket.rooms);
|
|
break;
|
|
case "makes all socket instances join the specified room":
|
|
io.socketsJoin("room1");
|
|
break;
|
|
|
|
case "makes the matching socket instances join the specified room":
|
|
io.in("room1").socketsJoin("room2");
|
|
break;
|
|
|
|
case "makes all socket instances leave the specified room":
|
|
io.socketsLeave("room1");
|
|
break;
|
|
case "makes the matching socket instances leave the specified room":
|
|
io.in("room1").socketsLeave("room2");
|
|
break;
|
|
|
|
case "makes all socket instances disconnect":
|
|
io.disconnectSockets();
|
|
break;
|
|
|
|
case "returns all socket instances":
|
|
const sockets = await io.fetchSockets();
|
|
|
|
expect(sockets).to.be.an(Array);
|
|
expect(sockets).to.have.length(3);
|
|
expect(io.of("/").adapter.requests.size).to.eql(0); // clean up
|
|
|
|
process.send("ok");
|
|
break;
|
|
|
|
case "sends an event to other server instances":
|
|
io.serverSideEmit("hello", "world", 1, "2");
|
|
break;
|
|
case "sends an event and receives a response from the other server instances (1)":
|
|
io.serverSideEmit("hello with ack", (err, response) => {
|
|
expect(err).to.be(null);
|
|
expect(response).to.be.an(Array);
|
|
expect(response).to.contain(2);
|
|
expect(response).to.contain("3");
|
|
process.send("ok");
|
|
});
|
|
break;
|
|
case "sends an event and receives a response from the other server instances (2)":
|
|
io.on("hello with ack", (cb) => {
|
|
cb(2);
|
|
});
|
|
break;
|
|
case "sends an event and receives a response from the other server instances (3)":
|
|
io.on("hello with ack", (cb) => {
|
|
cb("3");
|
|
});
|
|
break;
|
|
case "sends an event but timeout if one server does not respond (1)":
|
|
io.serverSideEmit("hello with ack", (err, response) => {
|
|
expect(err.message).to.be(
|
|
"timeout reached: missing 1 responses"
|
|
);
|
|
expect(response).to.be.an(Array);
|
|
expect(response).to.contain(2);
|
|
process.send("ok");
|
|
});
|
|
break;
|
|
case "sends an event but timeout if one server does not respond (2)":
|
|
io.on("hello with ack", (cb) => {
|
|
cb(2);
|
|
});
|
|
break;
|
|
case "sends an event but timeout if one server does not respond (3)":
|
|
io.on("hello with ack", (cb) => {
|
|
// do nothing
|
|
});
|
|
break;
|
|
}
|
|
});
|
|
|
|
io.on("hello", (arg1, arg2, arg3) => {
|
|
expect(arg1).to.eql("world");
|
|
expect(arg2).to.eql(1);
|
|
expect(arg3).to.eql("2");
|
|
process.send("ok");
|
|
});
|
|
|
|
httpServer.listen(parseInt(process.env.PORT, 10));
|