@colyseus/tools 0.16.0-preview.2 → 0.16.0-preview.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -5
- package/build/index.d.ts +1 -1
- package/build/index.js +42 -38
- package/build/index.js.map +3 -3
- package/build/index.mjs +42 -38
- package/build/index.mjs.map +2 -2
- package/package.json +28 -13
- package/pm2/post-deploy-agent.js +315 -0
- package/pm2/shared.js +73 -0
- package/post-deploy.js +97 -94
- package/report-stats.js +178 -0
- package/system-boot.js +89 -35
package/README.md
CHANGED
|
@@ -7,19 +7,19 @@
|
|
|
7
7
|
<a href="https://npmjs.com/package/colyseus">
|
|
8
8
|
<img src="https://img.shields.io/npm/dm/colyseus.svg?style=for-the-badge&logo=data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAQAAAC1+jfqAAAABGdBTUEAALGPC/xhBQAAACBjSFJNAAB6JgAAgIQAAPoAAACA6AAAdTAAAOpgAAA6mAAAF3CculE8AAAAAmJLR0QAAKqNIzIAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAHdElNRQfjAgETESWYxR33AAAAtElEQVQoz4WQMQrCQBRE38Z0QoTcwF4Qg1h4BO0sxGOk80iCtViksrIQRRBTewWxMI1mbELYjYu+4rPMDPtn12ChMT3gavb4US5Jym0tcBIta3oDHv4Gwmr7nC4QAxBrCdzM2q6XqUnm9m9r59h7Rc0n2pFv24k4ttGMUXW+sGELTJjSr7QDKuqLS6UKFChVWWuFkZw9Z2AAvAirKT+JTlppIRnd6XgaP4goefI2Shj++OnjB3tBmHYK8z9zAAAAJXRFWHRkYXRlOmNyZWF0ZQAyMDE5LTAyLTAxVDE4OjE3OjM3KzAxOjAwGQQixQAAACV0RVh0ZGF0ZTptb2RpZnkAMjAxOS0wMi0wMVQxODoxNzozNyswMTowMGhZmnkAAAAZdEVYdFNvZnR3YXJlAHd3dy5pbmtzY2FwZS5vcmeb7jwaAAAAAElFTkSuQmCC">
|
|
9
9
|
</a>
|
|
10
|
-
<a href="http://chat.colyseus.io">
|
|
11
|
-
<img src="https://img.shields.io/discord/525739117951320081.svg?style=for-the-badge&colorB=7581dc&logo=discord&logoColor=white">
|
|
12
|
-
</a>
|
|
13
10
|
<a href="https://github.com/colyseus/colyseus/discussions" title="Discuss on Forum">
|
|
14
11
|
<img src="https://img.shields.io/badge/discuss-on%20forum-brightgreen.svg?style=for-the-badge&colorB=0069b8&logo=data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAQAAAC1+jfqAAAABGdBTUEAALGPC/xhBQAAACBjSFJNAAB6JgAAgIQAAPoAAACA6AAAdTAAAOpgAAA6mAAAF3CculE8AAAAAmJLR0QAAKqNIzIAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAHdElNRQfjAgETDROxCNUzAAABB0lEQVQoz4WRvyvEARjGP193CnWRH+dHQmGwKZtFGcSmxHAL400GN95ktIpV2dzlLzDJgsGgGNRdDAzoQueS/PgY3HXHyT3T+/Y87/s89UANBKXBdoZo5J6L4K1K5ZxHfnjnlQUf3bKvkgy57a0r9hS3cXfMO1kWJMza++tj3Ac7/LY343x1NA9cNmYMwnSS/SP8JVFuSJmr44iFqvtmpjhmhBCrOOazCesq6H4P3bPBjFoIBydOk2bUA17I080Es+wSZ51B4DIA2zgjSpYcEe44Js01G0XjRcCU+y4ZMrDeLmfc9EnVd5M/o0VMeu6nJZxWJivLmhyw1WHTvrr2b4+2OFqra+ALwouTMDcqmjMAAAAldEVYdGRhdGU6Y3JlYXRlADIwMTktMDItMDFUMTg6MTM6MTkrMDE6MDAC9f6fAAAAJXRFWHRkYXRlOm1vZGlmeQAyMDE5LTAyLTAxVDE4OjEzOjE5KzAxOjAwc6hGIwAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAAASUVORK5CYII=" alt="Discussion forum" />
|
|
15
12
|
</a>
|
|
13
|
+
<a href="http://chat.colyseus.io">
|
|
14
|
+
<img src="https://img.shields.io/discord/525739117951320081.svg?style=for-the-badge&colorB=7581dc&logo=discord&logoColor=white">
|
|
15
|
+
</a>
|
|
16
16
|
<h3>
|
|
17
17
|
Multiplayer Framework for Node.js. <br /><a href="https://docs.colyseus.io/">View documentation</a>
|
|
18
18
|
</h3>
|
|
19
19
|
</div>
|
|
20
20
|
|
|
21
|
-
Colyseus is an Authoritative Multiplayer Framework for Node.js, with
|
|
22
|
-
available for the Web,
|
|
21
|
+
Colyseus is an Authoritative Multiplayer Framework for Node.js, with clients
|
|
22
|
+
available for the Web, Unity3d, Defold, Haxe, and Cocos. ([See official clients](#%EF%B8%8F-official-client-integration))
|
|
23
23
|
|
|
24
24
|
The project focuses on providing synchronizable data structures for realtime and
|
|
25
25
|
turn-based games, matchmaking, and ease of usage both on the server-side and
|
package/build/index.d.ts
CHANGED
|
@@ -16,5 +16,5 @@ export default function (options: ConfigOptions): ConfigOptions;
|
|
|
16
16
|
* @param options Application options
|
|
17
17
|
* @param port Port number to bind Colyseus + Express
|
|
18
18
|
*/
|
|
19
|
-
export declare function listen(options: ConfigOptions, port?: number): Promise<Server>;
|
|
19
|
+
export declare function listen(options: ConfigOptions | Server, port?: number): Promise<Server>;
|
|
20
20
|
export declare function getTransport(options: ConfigOptions): Promise<Transport>;
|
package/build/index.js
CHANGED
|
@@ -34,10 +34,11 @@ __export(src_exports, {
|
|
|
34
34
|
module.exports = __toCommonJS(src_exports);
|
|
35
35
|
var import_loadenv = require("./loadenv.js");
|
|
36
36
|
var import_os = __toESM(require("os"));
|
|
37
|
+
var import_fs = __toESM(require("fs"));
|
|
38
|
+
var import_net = __toESM(require("net"));
|
|
37
39
|
var import_http = __toESM(require("http"));
|
|
38
40
|
var import_cors = __toESM(require("cors"));
|
|
39
41
|
var import_express = __toESM(require("express"));
|
|
40
|
-
var import_node_os_utils = __toESM(require("node-os-utils"));
|
|
41
42
|
var import_core = require("@colyseus/core");
|
|
42
43
|
var import_ws_transport = require("@colyseus/ws-transport");
|
|
43
44
|
let BunWebSockets = void 0;
|
|
@@ -64,13 +65,40 @@ function src_default(options) {
|
|
|
64
65
|
return options;
|
|
65
66
|
}
|
|
66
67
|
async function listen(options, port = Number(process.env.PORT || 2567)) {
|
|
67
|
-
const serverOptions = options.options || {};
|
|
68
|
-
options.displayLogs = options.displayLogs ?? true;
|
|
69
68
|
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
70
69
|
port = 2567;
|
|
71
70
|
}
|
|
72
71
|
const processNumber = Number(process.env.NODE_APP_INSTANCE || "0");
|
|
73
72
|
port += processNumber;
|
|
73
|
+
let gameServer;
|
|
74
|
+
let displayLogs = true;
|
|
75
|
+
if (options instanceof import_core.Server) {
|
|
76
|
+
gameServer = options;
|
|
77
|
+
} else {
|
|
78
|
+
gameServer = await buildServerFromOptions(options, port);
|
|
79
|
+
displayLogs = options.displayLogs;
|
|
80
|
+
await options.initializeGameServer?.(gameServer);
|
|
81
|
+
await import_core.matchMaker.onReady;
|
|
82
|
+
await options.beforeListen?.();
|
|
83
|
+
}
|
|
84
|
+
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
85
|
+
const socketPath = `/run/colyseus/${port}.sock`;
|
|
86
|
+
await checkInactiveSocketFile(socketPath);
|
|
87
|
+
await gameServer.listen(socketPath);
|
|
88
|
+
} else {
|
|
89
|
+
await gameServer.listen(port);
|
|
90
|
+
}
|
|
91
|
+
if (typeof process.send === "function") {
|
|
92
|
+
process.send("ready");
|
|
93
|
+
}
|
|
94
|
+
if (displayLogs) {
|
|
95
|
+
import_core.logger.info(`\u2694\uFE0F Listening on http://localhost:${port}`);
|
|
96
|
+
}
|
|
97
|
+
return gameServer;
|
|
98
|
+
}
|
|
99
|
+
async function buildServerFromOptions(options, port) {
|
|
100
|
+
const serverOptions = options.options || {};
|
|
101
|
+
options.displayLogs = options.displayLogs ?? true;
|
|
74
102
|
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
75
103
|
const useRedisConfig = import_os.default.cpus().length > 1 || process.env.REDIS_URI !== void 0;
|
|
76
104
|
if (!serverOptions.driver && useRedisConfig) {
|
|
@@ -103,25 +131,10 @@ async function listen(options, port = Number(process.env.PORT || 2567)) {
|
|
|
103
131
|
}
|
|
104
132
|
}
|
|
105
133
|
const transport = await getTransport(options);
|
|
106
|
-
|
|
134
|
+
return new import_core.Server({
|
|
107
135
|
...serverOptions,
|
|
108
136
|
transport
|
|
109
137
|
});
|
|
110
|
-
await options.initializeGameServer?.(gameServer);
|
|
111
|
-
await import_core.matchMaker.onReady;
|
|
112
|
-
await options.beforeListen?.();
|
|
113
|
-
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
114
|
-
await gameServer.listen(`/run/colyseus/${port}.sock`);
|
|
115
|
-
} else {
|
|
116
|
-
await gameServer.listen(port);
|
|
117
|
-
}
|
|
118
|
-
if (typeof process.send === "function") {
|
|
119
|
-
process.send("ready");
|
|
120
|
-
}
|
|
121
|
-
if (options.displayLogs) {
|
|
122
|
-
import_core.logger.info(`\u2694\uFE0F Listening on http://localhost:${port}`);
|
|
123
|
-
}
|
|
124
|
-
return gameServer;
|
|
125
138
|
}
|
|
126
139
|
async function getTransport(options) {
|
|
127
140
|
let transport;
|
|
@@ -147,31 +160,22 @@ async function getTransport(options) {
|
|
|
147
160
|
app.get("/__healthcheck", (req, res) => {
|
|
148
161
|
res.status(200).end();
|
|
149
162
|
});
|
|
150
|
-
app.get("/__cloudstats", async (req, res) => {
|
|
151
|
-
if (process.env.CLOUD_SECRET && req.headers.authorization !== process.env.CLOUD_SECRET) {
|
|
152
|
-
res.status(401).end();
|
|
153
|
-
return;
|
|
154
|
-
}
|
|
155
|
-
const rooms = (await import_core.matchMaker.stats.fetchAll()).reduce((prev, curr) => {
|
|
156
|
-
return prev + curr.roomCount;
|
|
157
|
-
}, 0);
|
|
158
|
-
const ccu = await import_core.matchMaker.stats.getGlobalCCU();
|
|
159
|
-
const mem = await import_node_os_utils.default.mem.used();
|
|
160
|
-
const cpu = await import_node_os_utils.default.cpu.usage() / 100;
|
|
161
|
-
res.json({
|
|
162
|
-
version: 1,
|
|
163
|
-
mem: mem.usedMemMb / mem.totalMemMb,
|
|
164
|
-
cpu,
|
|
165
|
-
ccu,
|
|
166
|
-
rooms
|
|
167
|
-
});
|
|
168
|
-
});
|
|
169
163
|
if (options.displayLogs) {
|
|
170
164
|
import_core.logger.info("\u2705 Express initialized");
|
|
171
165
|
}
|
|
172
166
|
}
|
|
173
167
|
return transport;
|
|
174
168
|
}
|
|
169
|
+
function checkInactiveSocketFile(sockFilePath) {
|
|
170
|
+
return new Promise((resolve, reject) => {
|
|
171
|
+
const client = import_net.default.createConnection({ path: sockFilePath }).on("connect", () => {
|
|
172
|
+
client.end();
|
|
173
|
+
throw new Error(`EADDRINUSE: Already listening on '${sockFilePath}'`);
|
|
174
|
+
}).on("error", () => {
|
|
175
|
+
import_fs.default.unlink(sockFilePath, () => resolve(true));
|
|
176
|
+
});
|
|
177
|
+
});
|
|
178
|
+
}
|
|
175
179
|
// Annotate the CommonJS export names for ESM import in node:
|
|
176
180
|
0 && (module.exports = {
|
|
177
181
|
getTransport,
|
package/build/index.js.map
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../src/index.ts"],
|
|
4
|
-
"sourcesContent": ["import './loadenv.js';\nimport os from 'os';\nimport http from 'http';\nimport cors from 'cors';\nimport express from 'express';\nimport
|
|
5
|
-
"mappings": ";;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,qBAAO;AACP,gBAAe;AACf,kBAAiB;AACjB,kBAAiB;AACjB,qBAAoB;AACpB,
|
|
6
|
-
"names": ["module", "os", "options", "express", "http", "cors", "
|
|
4
|
+
"sourcesContent": ["import './loadenv.js';\nimport os from 'os';\nimport fs from \"fs\";\nimport net from \"net\";\nimport http from 'http';\nimport cors from 'cors';\nimport express from 'express';\nimport { logger, Server, ServerOptions, Transport, matchMaker } from '@colyseus/core';\nimport { WebSocketTransport } from '@colyseus/ws-transport';\n\nlet BunWebSockets: any = undefined;\n\n// @ts-ignore\nimport('@colyseus/bun-websockets')\n .then((module) => BunWebSockets = module)\n .catch(() => { });\n\nexport interface ConfigOptions {\n options?: ServerOptions,\n displayLogs?: boolean,\n getId?: () => string,\n initializeTransport?: (options: any) => Transport,\n initializeExpress?: (app: express.Express) => void,\n initializeGameServer?: (app: Server) => void,\n beforeListen?: () => void,\n}\n\nconst ALLOWED_KEYS: { [key in keyof ConfigOptions]: string } = {\n 'displayLogs': \"boolean\",\n 'options': \"object\",\n 'getId': \"function\",\n 'initializeTransport': \"function\",\n 'initializeExpress': \"function\",\n 'initializeGameServer': \"function\",\n 'beforeListen': \"function\"\n};\n\nexport default function (options: ConfigOptions) {\n for (const option in options) {\n if (!ALLOWED_KEYS[option]) {\n throw new Error(`\u274C Invalid option '${option}'. Allowed options are: ${Object.keys(ALLOWED_KEYS).join(\", \")}`);\n }\n if(options[option] !== undefined && typeof(options[option]) !== ALLOWED_KEYS[option]) {\n throw new Error(`\u274C Invalid type for ${option}: please provide a ${ALLOWED_KEYS[option]} value.`);\n }\n }\n\n return options;\n}\n\n/**\n * Listen on your development environment\n * @param options Application options\n * @param port Port number to bind Colyseus + Express\n */\nexport async function listen(\n options: ConfigOptions | Server,\n port: number = Number(process.env.PORT || 2567),\n) {\n // Force 2567 port on Colyseus Cloud\n if (process.env.COLYSEUS_CLOUD !== undefined) {\n port = 2567;\n }\n\n //\n // Handling multiple processes\n // Use NODE_APP_INSTANCE to play nicely with pm2\n //\n const processNumber = Number(process.env.NODE_APP_INSTANCE || \"0\");\n port += processNumber;\n\n let gameServer: Server;\n let displayLogs = true;\n\n if (options instanceof Server) {\n gameServer = options;\n\n } else {\n gameServer = await buildServerFromOptions(options, port);\n displayLogs = options.displayLogs;\n\n await options.initializeGameServer?.(gameServer);\n await matchMaker.onReady;\n await options.beforeListen?.();\n }\n\n if (process.env.COLYSEUS_CLOUD !== undefined) {\n // listening on socket\n const socketPath: any = `/run/colyseus/${port}.sock`;\n\n // check if .sock file is active\n // (fixes \"ADDRINUSE\" issue when restarting the server)\n await checkInactiveSocketFile(socketPath);\n\n await gameServer.listen(socketPath);\n\n } else {\n // listening on port\n await gameServer.listen(port);\n }\n\n // notify process manager (production)\n if (typeof(process.send) === \"function\") {\n process.send('ready');\n }\n\n if (displayLogs) {\n logger.info(`\u2694\uFE0F Listening on http://localhost:${port}`);\n }\n\n return gameServer;\n}\n\nasync function buildServerFromOptions(options: ConfigOptions, port: number) {\n const serverOptions = options.options || {};\n options.displayLogs = options.displayLogs ?? true;\n\n // automatically configure for production under Colyseus Cloud\n if (process.env.COLYSEUS_CLOUD !== undefined) {\n\n // special configuration is required when using multiple processes\n const useRedisConfig = (os.cpus().length > 1) || (process.env.REDIS_URI !== undefined);\n\n if (!serverOptions.driver && useRedisConfig) {\n let RedisDriver: any = undefined;\n try {\n RedisDriver = require('@colyseus/redis-driver').RedisDriver;\n serverOptions.driver = new RedisDriver(process.env.REDIS_URI);\n } catch (e) {\n logger.warn(\"\");\n logger.warn(\"\u274C could not initialize RedisDriver.\");\n logger.warn(\"\uD83D\uDC49 npm install --save @colyseus/redis-driver\");\n logger.warn(\"\");\n }\n }\n\n if (!serverOptions.presence && useRedisConfig) {\n let RedisPresence: any = undefined;\n try {\n RedisPresence = require('@colyseus/redis-presence').RedisPresence;\n serverOptions.presence = new RedisPresence(process.env.REDIS_URI);\n } catch (e) {\n logger.warn(\"\");\n logger.warn(\"\u274C could not initialize RedisPresence.\");\n logger.warn(\"\uD83D\uDC49 npm install --save @colyseus/redis-presence\");\n logger.warn(\"\");\n }\n }\n\n if (useRedisConfig) {\n // force \"publicAddress\" when more than 1 process is available\n serverOptions.publicAddress = process.env.SUBDOMAIN + \".\" + process.env.SERVER_NAME;\n\n // nginx is responsible for forwarding /{port}/ to this process\n serverOptions.publicAddress += \"/\" + port;\n }\n }\n\n const transport = await getTransport(options);\n return new Server({\n ...serverOptions,\n transport,\n });\n}\n\nexport async function getTransport(options: ConfigOptions) {\n let transport: Transport;\n\n if (!options.initializeTransport) {\n if (BunWebSockets !== undefined) {\n // @colyseus/bun-websockets\n options.initializeTransport = (options: any) => new BunWebSockets.BunWebSockets(options);\n\n } else {\n // use WebSocketTransport by default\n options.initializeTransport = (options: any) => new WebSocketTransport(options);\n }\n }\n\n let app: express.Express | undefined = express();\n let server = http.createServer(app);\n\n transport = await options.initializeTransport({ server, app });\n\n //\n // TODO: refactor me!\n // BunWebSockets: There's no need to instantiate \"app\" and \"server\" above\n //\n if (transport['expressApp']) {\n app = transport['expressApp'];\n }\n\n if (app) {\n // Enable CORS\n app.use(cors({ origin: true, credentials: true, }));\n\n // Enable JSON parsing.\n app.use(express.json());\n\n if (options.initializeExpress) {\n await options.initializeExpress(app);\n }\n\n // health check for load balancers\n app.get(\"/__healthcheck\", (req, res) => {\n res.status(200).end();\n });\n\n if (options.displayLogs) {\n logger.info(\"\u2705 Express initialized\");\n }\n }\n\n return transport;\n}\n\n/**\n * Check if a socket file is active and remove it if it's not.\n */\nfunction checkInactiveSocketFile(sockFilePath: string) {\n return new Promise((resolve, reject) => {\n const client = net.createConnection({ path: sockFilePath })\n .on('connect', () => {\n // socket file is active, close the connection\n client.end();\n throw new Error(`EADDRINUSE: Already listening on '${sockFilePath}'`);\n })\n .on('error', () => {\n // socket file is inactive, remove it\n fs.unlink(sockFilePath, () => resolve(true));\n });\n });\n}"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["module", "os", "options", "express", "http", "cors", "net", "fs"]
|
|
7
7
|
}
|
package/build/index.mjs
CHANGED
|
@@ -8,10 +8,11 @@ var __require = /* @__PURE__ */ ((x) => typeof require !== "undefined" ? require
|
|
|
8
8
|
// packages/tools/src/index.ts
|
|
9
9
|
import "./loadenv.mjs";
|
|
10
10
|
import os from "os";
|
|
11
|
+
import fs from "fs";
|
|
12
|
+
import net from "net";
|
|
11
13
|
import http from "http";
|
|
12
14
|
import cors from "cors";
|
|
13
15
|
import express from "express";
|
|
14
|
-
import osUtils from "node-os-utils";
|
|
15
16
|
import { logger, Server, matchMaker } from "@colyseus/core";
|
|
16
17
|
import { WebSocketTransport } from "@colyseus/ws-transport";
|
|
17
18
|
var BunWebSockets = void 0;
|
|
@@ -38,13 +39,40 @@ function src_default(options) {
|
|
|
38
39
|
return options;
|
|
39
40
|
}
|
|
40
41
|
async function listen(options, port = Number(process.env.PORT || 2567)) {
|
|
41
|
-
const serverOptions = options.options || {};
|
|
42
|
-
options.displayLogs = options.displayLogs ?? true;
|
|
43
42
|
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
44
43
|
port = 2567;
|
|
45
44
|
}
|
|
46
45
|
const processNumber = Number(process.env.NODE_APP_INSTANCE || "0");
|
|
47
46
|
port += processNumber;
|
|
47
|
+
let gameServer;
|
|
48
|
+
let displayLogs = true;
|
|
49
|
+
if (options instanceof Server) {
|
|
50
|
+
gameServer = options;
|
|
51
|
+
} else {
|
|
52
|
+
gameServer = await buildServerFromOptions(options, port);
|
|
53
|
+
displayLogs = options.displayLogs;
|
|
54
|
+
await options.initializeGameServer?.(gameServer);
|
|
55
|
+
await matchMaker.onReady;
|
|
56
|
+
await options.beforeListen?.();
|
|
57
|
+
}
|
|
58
|
+
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
59
|
+
const socketPath = `/run/colyseus/${port}.sock`;
|
|
60
|
+
await checkInactiveSocketFile(socketPath);
|
|
61
|
+
await gameServer.listen(socketPath);
|
|
62
|
+
} else {
|
|
63
|
+
await gameServer.listen(port);
|
|
64
|
+
}
|
|
65
|
+
if (typeof process.send === "function") {
|
|
66
|
+
process.send("ready");
|
|
67
|
+
}
|
|
68
|
+
if (displayLogs) {
|
|
69
|
+
logger.info(`\u2694\uFE0F Listening on http://localhost:${port}`);
|
|
70
|
+
}
|
|
71
|
+
return gameServer;
|
|
72
|
+
}
|
|
73
|
+
async function buildServerFromOptions(options, port) {
|
|
74
|
+
const serverOptions = options.options || {};
|
|
75
|
+
options.displayLogs = options.displayLogs ?? true;
|
|
48
76
|
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
49
77
|
const useRedisConfig = os.cpus().length > 1 || process.env.REDIS_URI !== void 0;
|
|
50
78
|
if (!serverOptions.driver && useRedisConfig) {
|
|
@@ -77,25 +105,10 @@ async function listen(options, port = Number(process.env.PORT || 2567)) {
|
|
|
77
105
|
}
|
|
78
106
|
}
|
|
79
107
|
const transport = await getTransport(options);
|
|
80
|
-
|
|
108
|
+
return new Server({
|
|
81
109
|
...serverOptions,
|
|
82
110
|
transport
|
|
83
111
|
});
|
|
84
|
-
await options.initializeGameServer?.(gameServer);
|
|
85
|
-
await matchMaker.onReady;
|
|
86
|
-
await options.beforeListen?.();
|
|
87
|
-
if (process.env.COLYSEUS_CLOUD !== void 0) {
|
|
88
|
-
await gameServer.listen(`/run/colyseus/${port}.sock`);
|
|
89
|
-
} else {
|
|
90
|
-
await gameServer.listen(port);
|
|
91
|
-
}
|
|
92
|
-
if (typeof process.send === "function") {
|
|
93
|
-
process.send("ready");
|
|
94
|
-
}
|
|
95
|
-
if (options.displayLogs) {
|
|
96
|
-
logger.info(`\u2694\uFE0F Listening on http://localhost:${port}`);
|
|
97
|
-
}
|
|
98
|
-
return gameServer;
|
|
99
112
|
}
|
|
100
113
|
async function getTransport(options) {
|
|
101
114
|
let transport;
|
|
@@ -121,31 +134,22 @@ async function getTransport(options) {
|
|
|
121
134
|
app.get("/__healthcheck", (req, res) => {
|
|
122
135
|
res.status(200).end();
|
|
123
136
|
});
|
|
124
|
-
app.get("/__cloudstats", async (req, res) => {
|
|
125
|
-
if (process.env.CLOUD_SECRET && req.headers.authorization !== process.env.CLOUD_SECRET) {
|
|
126
|
-
res.status(401).end();
|
|
127
|
-
return;
|
|
128
|
-
}
|
|
129
|
-
const rooms = (await matchMaker.stats.fetchAll()).reduce((prev, curr) => {
|
|
130
|
-
return prev + curr.roomCount;
|
|
131
|
-
}, 0);
|
|
132
|
-
const ccu = await matchMaker.stats.getGlobalCCU();
|
|
133
|
-
const mem = await osUtils.mem.used();
|
|
134
|
-
const cpu = await osUtils.cpu.usage() / 100;
|
|
135
|
-
res.json({
|
|
136
|
-
version: 1,
|
|
137
|
-
mem: mem.usedMemMb / mem.totalMemMb,
|
|
138
|
-
cpu,
|
|
139
|
-
ccu,
|
|
140
|
-
rooms
|
|
141
|
-
});
|
|
142
|
-
});
|
|
143
137
|
if (options.displayLogs) {
|
|
144
138
|
logger.info("\u2705 Express initialized");
|
|
145
139
|
}
|
|
146
140
|
}
|
|
147
141
|
return transport;
|
|
148
142
|
}
|
|
143
|
+
function checkInactiveSocketFile(sockFilePath) {
|
|
144
|
+
return new Promise((resolve, reject) => {
|
|
145
|
+
const client = net.createConnection({ path: sockFilePath }).on("connect", () => {
|
|
146
|
+
client.end();
|
|
147
|
+
throw new Error(`EADDRINUSE: Already listening on '${sockFilePath}'`);
|
|
148
|
+
}).on("error", () => {
|
|
149
|
+
fs.unlink(sockFilePath, () => resolve(true));
|
|
150
|
+
});
|
|
151
|
+
});
|
|
152
|
+
}
|
|
149
153
|
export {
|
|
150
154
|
src_default as default,
|
|
151
155
|
getTransport,
|
package/build/index.mjs.map
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../src/index.ts"],
|
|
4
|
-
"sourcesContent": ["import './loadenv.js';\nimport os from 'os';\nimport http from 'http';\nimport cors from 'cors';\nimport express from 'express';\nimport
|
|
5
|
-
"mappings": ";;;;;;;;AAAA,OAAO;AACP,OAAO,QAAQ;AACf,OAAO,
|
|
4
|
+
"sourcesContent": ["import './loadenv.js';\nimport os from 'os';\nimport fs from \"fs\";\nimport net from \"net\";\nimport http from 'http';\nimport cors from 'cors';\nimport express from 'express';\nimport { logger, Server, ServerOptions, Transport, matchMaker } from '@colyseus/core';\nimport { WebSocketTransport } from '@colyseus/ws-transport';\n\nlet BunWebSockets: any = undefined;\n\n// @ts-ignore\nimport('@colyseus/bun-websockets')\n .then((module) => BunWebSockets = module)\n .catch(() => { });\n\nexport interface ConfigOptions {\n options?: ServerOptions,\n displayLogs?: boolean,\n getId?: () => string,\n initializeTransport?: (options: any) => Transport,\n initializeExpress?: (app: express.Express) => void,\n initializeGameServer?: (app: Server) => void,\n beforeListen?: () => void,\n}\n\nconst ALLOWED_KEYS: { [key in keyof ConfigOptions]: string } = {\n 'displayLogs': \"boolean\",\n 'options': \"object\",\n 'getId': \"function\",\n 'initializeTransport': \"function\",\n 'initializeExpress': \"function\",\n 'initializeGameServer': \"function\",\n 'beforeListen': \"function\"\n};\n\nexport default function (options: ConfigOptions) {\n for (const option in options) {\n if (!ALLOWED_KEYS[option]) {\n throw new Error(`\u274C Invalid option '${option}'. Allowed options are: ${Object.keys(ALLOWED_KEYS).join(\", \")}`);\n }\n if(options[option] !== undefined && typeof(options[option]) !== ALLOWED_KEYS[option]) {\n throw new Error(`\u274C Invalid type for ${option}: please provide a ${ALLOWED_KEYS[option]} value.`);\n }\n }\n\n return options;\n}\n\n/**\n * Listen on your development environment\n * @param options Application options\n * @param port Port number to bind Colyseus + Express\n */\nexport async function listen(\n options: ConfigOptions | Server,\n port: number = Number(process.env.PORT || 2567),\n) {\n // Force 2567 port on Colyseus Cloud\n if (process.env.COLYSEUS_CLOUD !== undefined) {\n port = 2567;\n }\n\n //\n // Handling multiple processes\n // Use NODE_APP_INSTANCE to play nicely with pm2\n //\n const processNumber = Number(process.env.NODE_APP_INSTANCE || \"0\");\n port += processNumber;\n\n let gameServer: Server;\n let displayLogs = true;\n\n if (options instanceof Server) {\n gameServer = options;\n\n } else {\n gameServer = await buildServerFromOptions(options, port);\n displayLogs = options.displayLogs;\n\n await options.initializeGameServer?.(gameServer);\n await matchMaker.onReady;\n await options.beforeListen?.();\n }\n\n if (process.env.COLYSEUS_CLOUD !== undefined) {\n // listening on socket\n const socketPath: any = `/run/colyseus/${port}.sock`;\n\n // check if .sock file is active\n // (fixes \"ADDRINUSE\" issue when restarting the server)\n await checkInactiveSocketFile(socketPath);\n\n await gameServer.listen(socketPath);\n\n } else {\n // listening on port\n await gameServer.listen(port);\n }\n\n // notify process manager (production)\n if (typeof(process.send) === \"function\") {\n process.send('ready');\n }\n\n if (displayLogs) {\n logger.info(`\u2694\uFE0F Listening on http://localhost:${port}`);\n }\n\n return gameServer;\n}\n\nasync function buildServerFromOptions(options: ConfigOptions, port: number) {\n const serverOptions = options.options || {};\n options.displayLogs = options.displayLogs ?? true;\n\n // automatically configure for production under Colyseus Cloud\n if (process.env.COLYSEUS_CLOUD !== undefined) {\n\n // special configuration is required when using multiple processes\n const useRedisConfig = (os.cpus().length > 1) || (process.env.REDIS_URI !== undefined);\n\n if (!serverOptions.driver && useRedisConfig) {\n let RedisDriver: any = undefined;\n try {\n RedisDriver = require('@colyseus/redis-driver').RedisDriver;\n serverOptions.driver = new RedisDriver(process.env.REDIS_URI);\n } catch (e) {\n logger.warn(\"\");\n logger.warn(\"\u274C could not initialize RedisDriver.\");\n logger.warn(\"\uD83D\uDC49 npm install --save @colyseus/redis-driver\");\n logger.warn(\"\");\n }\n }\n\n if (!serverOptions.presence && useRedisConfig) {\n let RedisPresence: any = undefined;\n try {\n RedisPresence = require('@colyseus/redis-presence').RedisPresence;\n serverOptions.presence = new RedisPresence(process.env.REDIS_URI);\n } catch (e) {\n logger.warn(\"\");\n logger.warn(\"\u274C could not initialize RedisPresence.\");\n logger.warn(\"\uD83D\uDC49 npm install --save @colyseus/redis-presence\");\n logger.warn(\"\");\n }\n }\n\n if (useRedisConfig) {\n // force \"publicAddress\" when more than 1 process is available\n serverOptions.publicAddress = process.env.SUBDOMAIN + \".\" + process.env.SERVER_NAME;\n\n // nginx is responsible for forwarding /{port}/ to this process\n serverOptions.publicAddress += \"/\" + port;\n }\n }\n\n const transport = await getTransport(options);\n return new Server({\n ...serverOptions,\n transport,\n });\n}\n\nexport async function getTransport(options: ConfigOptions) {\n let transport: Transport;\n\n if (!options.initializeTransport) {\n if (BunWebSockets !== undefined) {\n // @colyseus/bun-websockets\n options.initializeTransport = (options: any) => new BunWebSockets.BunWebSockets(options);\n\n } else {\n // use WebSocketTransport by default\n options.initializeTransport = (options: any) => new WebSocketTransport(options);\n }\n }\n\n let app: express.Express | undefined = express();\n let server = http.createServer(app);\n\n transport = await options.initializeTransport({ server, app });\n\n //\n // TODO: refactor me!\n // BunWebSockets: There's no need to instantiate \"app\" and \"server\" above\n //\n if (transport['expressApp']) {\n app = transport['expressApp'];\n }\n\n if (app) {\n // Enable CORS\n app.use(cors({ origin: true, credentials: true, }));\n\n // Enable JSON parsing.\n app.use(express.json());\n\n if (options.initializeExpress) {\n await options.initializeExpress(app);\n }\n\n // health check for load balancers\n app.get(\"/__healthcheck\", (req, res) => {\n res.status(200).end();\n });\n\n if (options.displayLogs) {\n logger.info(\"\u2705 Express initialized\");\n }\n }\n\n return transport;\n}\n\n/**\n * Check if a socket file is active and remove it if it's not.\n */\nfunction checkInactiveSocketFile(sockFilePath: string) {\n return new Promise((resolve, reject) => {\n const client = net.createConnection({ path: sockFilePath })\n .on('connect', () => {\n // socket file is active, close the connection\n client.end();\n throw new Error(`EADDRINUSE: Already listening on '${sockFilePath}'`);\n })\n .on('error', () => {\n // socket file is inactive, remove it\n fs.unlink(sockFilePath, () => resolve(true));\n });\n });\n}"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": ["options"]
|
|
7
7
|
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@colyseus/tools",
|
|
3
|
-
"version": "0.16.0-preview.
|
|
4
|
-
"description": "
|
|
3
|
+
"version": "0.16.0-preview.4",
|
|
4
|
+
"description": "Simplify the development and production settings for your Colyseus project.",
|
|
5
5
|
"input": "./src/index.ts",
|
|
6
6
|
"main": "./build/index.js",
|
|
7
7
|
"module": "./build/index.mjs",
|
|
@@ -14,7 +14,8 @@
|
|
|
14
14
|
},
|
|
15
15
|
"bin": {
|
|
16
16
|
"colyseus-system-boot": "system-boot.js",
|
|
17
|
-
"colyseus-post-deploy": "post-deploy.js"
|
|
17
|
+
"colyseus-post-deploy": "post-deploy.js",
|
|
18
|
+
"colyseus-report-stats": "report-stats.js"
|
|
18
19
|
},
|
|
19
20
|
"repository": {
|
|
20
21
|
"type": "git",
|
|
@@ -31,29 +32,43 @@
|
|
|
31
32
|
"url": "https://github.com/colyseus/colyseus/issues"
|
|
32
33
|
},
|
|
33
34
|
"files": [
|
|
35
|
+
"pm2",
|
|
34
36
|
"html",
|
|
35
37
|
"build",
|
|
36
38
|
"LICENSE",
|
|
37
39
|
"README.md"
|
|
38
40
|
],
|
|
39
|
-
"homepage": "https
|
|
41
|
+
"homepage": "https://colyseus.io",
|
|
42
|
+
"dependencies": {
|
|
43
|
+
"@pm2/io": "^6.0.1",
|
|
44
|
+
"cors": "^2.8.5",
|
|
45
|
+
"dotenv": "^8.2.0",
|
|
46
|
+
"express": "^4.16.2"
|
|
47
|
+
},
|
|
40
48
|
"devDependencies": {
|
|
41
49
|
"@types/cors": "^2.8.10",
|
|
42
50
|
"@types/dotenv": "^8.2.0",
|
|
43
|
-
"uwebsockets-express": "^1.1.10"
|
|
51
|
+
"uwebsockets-express": "^1.1.10",
|
|
52
|
+
"@colyseus/core": "^0.16.0-preview.36",
|
|
53
|
+
"@colyseus/ws-transport": "^0.16.0-preview.8",
|
|
54
|
+
"@colyseus/uwebsockets-transport": "^0.16.0-preview.13"
|
|
44
55
|
},
|
|
45
|
-
"
|
|
46
|
-
"
|
|
47
|
-
"
|
|
48
|
-
"dotenv": "^8.2.0",
|
|
49
|
-
"express": "^4.16.2",
|
|
50
|
-
"@colyseus/core": "^0.16.0-preview.30",
|
|
51
|
-
"@colyseus/ws-transport": "^0.16.0-preview.7"
|
|
56
|
+
"peerDependencies": {
|
|
57
|
+
"@colyseus/core": "0.15.x",
|
|
58
|
+
"@colyseus/ws-transport": "0.15.x"
|
|
52
59
|
},
|
|
53
60
|
"publishConfig": {
|
|
54
61
|
"access": "public"
|
|
55
62
|
},
|
|
63
|
+
"apps": [
|
|
64
|
+
{
|
|
65
|
+
"merge_logs": true,
|
|
66
|
+
"max_memory_restart": "256M",
|
|
67
|
+
"script": "./pm2/post-deploy-agent.js",
|
|
68
|
+
"instance_var": "INSTANCE_ID"
|
|
69
|
+
}
|
|
70
|
+
],
|
|
56
71
|
"scripts": {
|
|
57
|
-
"start": "
|
|
72
|
+
"start": "tsx example/app.ts"
|
|
58
73
|
}
|
|
59
74
|
}
|