snakeia-server 1.1.5 → 1.2.1

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/Player.js ADDED
@@ -0,0 +1,132 @@
1
+ /*
2
+ * Copyright (C) 2020-2025 Eliastik (eliastiksofts.com)
3
+ *
4
+ * This file is part of "SnakeIA Server".
5
+ *
6
+ * "SnakeIA Server" is free software: you can redistribute it and/or modify
7
+ * it under the terms of the GNU General Public License as published by
8
+ * the Free Software Foundation, either version 3 of the License, or
9
+ * (at your option) any later version.
10
+ *
11
+ * "SnakeIA Server" is distributed in the hope that it will be useful,
12
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
+ * GNU General Public License for more details.
15
+ *
16
+ * You should have received a copy of the GNU General Public License
17
+ * along with "SnakeIA Server". If not, see <http://www.gnu.org/licenses/>.
18
+ */
19
+ class Player {
20
+ constructor(token, id, snake, ready, version) {
21
+ this.token = token;
22
+ this.id = id;
23
+ this.snake = snake;
24
+ this.ready = ready;
25
+ this.version = version;
26
+ }
27
+
28
+ get username() {
29
+ return Player.getUsername(this);
30
+ }
31
+
32
+ static getPlayer(array, id) {
33
+ for (let i = 0; i < array.length; i++) {
34
+ if (array[i] != null && array[i].id == id) {
35
+ return array[i];
36
+ }
37
+ }
38
+
39
+ return null;
40
+ }
41
+
42
+ static getPlayerAllGames(id, games) {
43
+ const keys = Object.keys(games);
44
+
45
+ for (let i = 0; i < keys.length; i++) {
46
+ const game = games[keys[i]];
47
+
48
+ if (game) {
49
+ const p = this.getPlayer(game.players, id);
50
+ const p2 = this.getPlayer(game.spectators, id);
51
+ if (p) return p;
52
+ if (p2) return p2;
53
+ }
54
+ }
55
+
56
+ return null;
57
+ }
58
+
59
+ static getPlayerToken(array, token) {
60
+ if (!token) return null;
61
+ for (let i = 0; i < array.length; i++) {
62
+ if (array[i] != null && array[i].token == token) {
63
+ return array[i];
64
+ }
65
+ }
66
+
67
+ return null;
68
+ }
69
+
70
+ static getPlayerAllGamesToken(token, games) {
71
+ if (!token) return null;
72
+ const keys = Object.keys(games);
73
+
74
+ for (let i = 0; i < keys.length; i++) {
75
+ const game = games[keys[i]];
76
+
77
+ if (game) {
78
+ const p = this.getPlayerToken(game.players, token);
79
+ const p2 = this.getPlayerToken(game.spectators, token);
80
+ if (p) return p;
81
+ if (p2) return p2;
82
+ }
83
+ }
84
+
85
+ return null;
86
+ }
87
+
88
+ static containsId(array, id) {
89
+ return Player.getPlayer(array, id) != null;
90
+ }
91
+
92
+ static containsToken(array, token) {
93
+ return Player.getPlayerToken(array, token) != null;
94
+ }
95
+
96
+ static containsIdAllGames(id, games) {
97
+ return Player.getPlayerAllGames(id, games) != null;
98
+ }
99
+
100
+ static containsTokenAllGames(token, games) {
101
+ return Player.getPlayerAllGamesToken(token, games) != null;
102
+ }
103
+
104
+ static getUsername(player) {
105
+ try {
106
+ const decoded_token = jwt.verify(player.token, jsonWebTokenSecretKey);
107
+ return decoded_token && decoded_token.username
108
+ ? decoded_token.username
109
+ : null;
110
+ } catch (e) {
111
+ return null;
112
+ }
113
+ }
114
+
115
+ static getUsernameSocket(socket) {
116
+ try {
117
+ const decoded_token = jwt.verify(
118
+ socket.handshake.auth.token ||
119
+ socket.handshake.query.token ||
120
+ socket.request.cookies.token,
121
+ jsonWebTokenSecretKey
122
+ );
123
+ return decoded_token && decoded_token.username
124
+ ? decoded_token.username
125
+ : null;
126
+ } catch (e) {
127
+ return null;
128
+ }
129
+ }
130
+ }
131
+
132
+ module.exports = Player;
package/README.md CHANGED
@@ -8,7 +8,7 @@ A server for my [SnakeIA](https://github.com/Eliastik/snakeia) game, written in
8
8
 
9
9
  ## About this server
10
10
 
11
- * Version 1.1.5 (6/18/2025)
11
+ * Version 1.2.1 (10/7/2025)
12
12
  * Made in France by Eliastik - [eliastiksofts.com](http://eliastiksofts.com) - Contact : [eliastiksofts.com/contact](http://eliastiksofts.com/contact)
13
13
  * License: GNU GPLv3 (see LICENCE.txt file)
14
14
 
@@ -74,7 +74,7 @@ You can create another configuration file in the **config** directory named **lo
74
74
  ````
75
75
  {
76
76
  "ServerConfig": {
77
- "version": "1.1.5", // The server version
77
+ "version": "1.2.1", // The server version
78
78
  "port": 3000, // The port where the server runs
79
79
  "proxyMode": false, // Sets this value to true if your server is behind a proxy - defaults to false
80
80
  "numberOfProxies": 1, // Sets the number of reverse proxies in front of the server. Default to 1. See: https://expressjs.com/en/guide/behind-proxies.html / https://express-rate-limit.mintlify.app/guides/troubleshooting-proxy-issues
@@ -86,6 +86,9 @@ You can create another configuration file in the **config** directory named **lo
86
86
  "minSpeed": 1, // The minimum speed
87
87
  "maxSpeed": 100, // The maximum speed
88
88
  "enableAI": false, // Disable or enable AIs
89
+ "aiUltraAPIURL": "https://www.eliastiksofts.com/snakeia/models/", // URL to the API listing the Ultra AI models. The game engine will use this API to load the default model
90
+ "aiUltraModelID": null, // ID of the model (as returned by the API at the URL above) to load for the Ultra AI. Can be left empty; in that case, the default model provided by the API will be loaded
91
+ "aiUltraCustomModelURL": null, // A URL pointing to a custom AI model to load. Must be a TensorFlow.js model trained for the Ultra AI. If there's an issue, game initialization will fail when Ultra AIs are present in the game
89
92
  "playerWaitTime": 45000, // The time while waiting for players to join a room (ms)
90
93
  "enableMaxTimeGame": true, // Enable time limit for each game
91
94
  "maxTimeGame": 300000, // The time limit for each game (ms)
@@ -120,6 +123,21 @@ You can create another configuration file in the **config** directory named **lo
120
123
 
121
124
  ## Changelog
122
125
 
126
+ * Version 1.2.1 (10/7/2025):
127
+ - Fixed a bug where the game could get stuck on the "Loading..." screen when restarting.
128
+
129
+ * Version 1.2.0 (10/5/2025):
130
+ - Adaptation to version 3.0.0 of SnakeIA and implementation of Ultra AI
131
+ - Bug fixes
132
+ - Updated dependencies
133
+
134
+ * Version 1.1.7 (7/8/2025):
135
+ - Fixed loop authentication problems (using a Socket.io v4 client)
136
+
137
+ * Version 1.1.6 (7/7/2025):
138
+ - Fix random crashs due to token checking (when using Socket.io client v4)
139
+ - Updated dependencies
140
+
123
141
  * Version 1.1.5 (6/18/2025):
124
142
  - Fixed "Error: invalid CSRF token" occurring during certain actions in the administrator panel
125
143
 
@@ -188,7 +206,7 @@ Un serveur pour mon jeu [SnakeIA](https://github.com/Eliastik/snakeia), écrit e
188
206
 
189
207
  ## À propos de ce serveur
190
208
 
191
- * Version 1.1.5 (18/06/2025)
209
+ * Version 1.2.1 (07/10/2025)
192
210
  * Made in France by Eliastik - [eliastiksofts.com](http://eliastiksofts.com) - Contact : [eliastiksofts.com/contact](http://eliastiksofts.com/contact)
193
211
  * Licence : GNU GPLv3 (voir le fichier LICENCE.txt)
194
212
 
@@ -254,7 +272,7 @@ Vous pouvez créer un fichier de configuration **local.json** dans le dossier **
254
272
  ````
255
273
  {
256
274
  "ServerConfig": {
257
- "version": "1.1.5", // La version du serveur
275
+ "version": "1.2.1", // La version du serveur
258
276
  "port": 3000, // Le port sur lequel lancer le server
259
277
  "proxyMode": false, // Mettez à true si votre serveur est derrière un proxy - par défaut false
260
278
  "numberOfProxies": 1, // Configure le nombre de proxies devant votre serveur. Par défaut 1. Voir : https://expressjs.com/en/guide/behind-proxies.html / https://express-rate-limit.mintlify.app/guides/troubleshooting-proxy-issues
@@ -266,6 +284,9 @@ Vous pouvez créer un fichier de configuration **local.json** dans le dossier **
266
284
  "minSpeed": 1, // La vitesse minimale
267
285
  "maxSpeed": 100, // La vitesse maximale
268
286
  "enableAI": false, // Désactiver ou activer les IA
287
+ "aiUltraAPIURL": "https://www.eliastiksofts.com/snakeia/models/", // URL vers l'API listant les modèles de l'IA Ultra. Le moteur du jeu se basera sur cette API pour charger le modèle par défaut
288
+ "aiUltraModelID": null, // ID du modèle (tel que retourné par l'API à l'URL du dessus) à charger pour l'IA Ultra. Peut rester vide, dans ce cas, le modèle par défaut fourni par l'API sera chargé
289
+ "aiUltraCustomModelURL": null, // Une URL pointant vers un modèle d'IA à charger. Doit être un modèle Tensorflow.js entraîné pour l'IA Ultra. En cas de soucis, l'initialisation du jeu plantera quand des IA Ultra seront dans la partie
269
290
  "playerWaitTime": 45000, // Le temps durant lequel attendre la connexion d'autres joueurs à la salle (ms)
270
291
  "enableMaxTimeGame": true, // Activer la limite de temps pour chaque partie
271
292
  "maxTimeGame": 300000, // La limite de temps pour chaque partie (ms)
@@ -300,6 +321,21 @@ Vous pouvez créer un fichier de configuration **local.json** dans le dossier **
300
321
 
301
322
  ## Journal des changements
302
323
 
324
+ * Version 1.2.1 (07/10/2025):
325
+ - Correction d'un bug où le jeu restait bloqué sur le message "Chargement..." lorsque la partie était recommencée
326
+
327
+ * Version 1.2.0 (05/10/2025) :
328
+ - Adaptation à la version 3.0.0 de SnakeIA et à la mise en place de l'IA Ultra
329
+ - Correction de bugs
330
+ - Mise à jour des dépendences
331
+
332
+ * Version 1.1.7 (08/07/2025):
333
+ - Correction de problèmes d'authentification en boucle (en utilisant un client Socket.io v4)
334
+
335
+ * Version 1.1.6 (07/07/2025):
336
+ - Correction de crashs aléatoires lors de la vérification des tokens (en utilisant Socket.io v4)
337
+ - Mise à jour des dépendences
338
+
303
339
  * Version 1.1.5 (18/06/2025) :
304
340
  - Correction de l’erreur "Error: invalid CSRF token" lors de certaines actions dans le panneau d’administration
305
341
 
@@ -0,0 +1,103 @@
1
+ /*
2
+ * Copyright (C) 2019-2025 Eliastik (eliastiksofts.com)
3
+ *
4
+ * This file is part of "SnakeIA".
5
+ *
6
+ * "SnakeIA" is free software: you can redistribute it and/or modify
7
+ * it under the terms of the GNU General Public License as published by
8
+ * the Free Software Foundation, either version 3 of the License, or
9
+ * (at your option) any later version.
10
+ *
11
+ * "SnakeIA" is distributed in the hope that it will be useful,
12
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
+ * GNU General Public License for more details.
15
+ *
16
+ * You should have received a copy of the GNU General Public License
17
+ * along with "SnakeIA". If not, see <http://www.gnu.org/licenses/>.
18
+ */
19
+
20
+ body.dark {
21
+ background-color: #130F0E;
22
+ color: #a6bbd4;
23
+ }
24
+
25
+ body.dark .btn-info:not(:disabled):not(:hover):not(:active) {
26
+ background-color: #246a99;
27
+ }
28
+
29
+ body.dark .btn-primary:not(:disabled):not(:hover):not(:active) {
30
+ background-color: #15997f;
31
+ }
32
+
33
+ body.dark .btn-warning:not(:disabled):not(:hover):not(:active) {
34
+ background-color: #b4920b;
35
+ }
36
+
37
+ body.dark .btn-danger:not(:disabled):not(:hover):not(:active) {
38
+ background-color: #b43b2f;
39
+ }
40
+
41
+ body.dark .btn-success:not(:disabled):not(:hover):not(:active) {
42
+ background-color: #239955;
43
+ }
44
+
45
+ body.dark .btn-default:not(:hover):not(:active) {
46
+ color: white;
47
+ background-color: #8d9396;
48
+ }
49
+
50
+ body.dark select, body.dark input {
51
+ color: #a6bbd4;
52
+ background-color: #1b1817;
53
+ border-color: #4b4746;
54
+ }
55
+
56
+ body.dark select:active, body.dark input:active, body.dark select:focus, body.dark input:focus {
57
+ color: #a6bbd4;
58
+ background-color: #1b1817;
59
+ border-color: #4b8246;
60
+ }
61
+
62
+ body.dark .custom-control.custom-checkbox .custom-control-label:before {
63
+ background-color: #1b1817;
64
+ border-color: #4b4746;
65
+ }
66
+
67
+ body.dark .custom-control-input:checked~.custom-control-label:before {
68
+ background-color: #005cbf;
69
+ border-color: #005cbf;
70
+ }
71
+
72
+ body.dark .custom-control-input:disabled~.custom-control-label:before {
73
+ background-color: #534a47;
74
+ border-color: #4b4746;
75
+ }
76
+
77
+ body.dark .card {
78
+ background-color: #181615;
79
+ border: 1px solid rgba(255, 255, 255, .125);
80
+ }
81
+
82
+ body.dark .card-header {
83
+ background-color: rgba(255, 255, 255, .03);
84
+ border: 1px solid rgba(255, 255, 255, .125);
85
+ }
86
+
87
+ body.dark .list-group-item {
88
+ background-color: #181615;
89
+ color: white;
90
+ border-color: rgba(255, 255, 255, .125);
91
+ }
92
+
93
+ body.dark .list-group-item:hover {
94
+ background-color: #1d1b19;
95
+ }
96
+
97
+ body.dark .modal-content {
98
+ background-color: #130F0E;
99
+ }
100
+
101
+ body.dark .modal-header {
102
+ background-color: rgba(255, 255, 255, .05);
103
+ }
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "ServerConfig": {
3
- "version": "1.1.5",
3
+ "version": "1.2.1",
4
4
  "port": 3000,
5
5
  "proxyMode": false,
6
6
  "numberOfProxies": 1,
@@ -12,6 +12,9 @@
12
12
  "minSpeed": 1,
13
13
  "maxSpeed": 100,
14
14
  "enableAI": true,
15
+ "aiUltraAPIURL": "https://www.eliastiksofts.com/snakeia/models/",
16
+ "aiUltraModelID": null,
17
+ "aiUltraCustomModelURL": null,
15
18
  "playerWaitTime": 60000,
16
19
  "enableMaxTimeGame": true,
17
20
  "maxTimeGame": 300000,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "snakeia-server",
3
- "version": "1.1.5",
3
+ "version": "1.2.1",
4
4
  "description": "Server for multiplaying in SnakeIA (https://github.com/Eliastik/snakeia)",
5
5
  "main": "server.js",
6
6
  "scripts": {
@@ -19,20 +19,20 @@
19
19
  "homepage": "https://github.com/Eliastik/snakeia-server#readme",
20
20
  "dependencies": {
21
21
  "body-parser": "^2.2.0",
22
- "config": "^4.0.0",
22
+ "config": "^4.1.1",
23
23
  "cookie-parser": "^1.4.7",
24
24
  "csrf-csrf": "^4.0.3",
25
25
  "ejs": "^3.1.10",
26
26
  "express": "^5.1.0",
27
- "express-rate-limit": "^7.5.0",
27
+ "express-rate-limit": "^8.1.0",
28
28
  "html-entities": "^2.6.0",
29
- "i18n": "^0.15.1",
29
+ "i18n": "^0.15.2",
30
30
  "jsonwebtoken": "^9.0.2",
31
31
  "node-fetch": "^3.3.2",
32
32
  "seedrandom": "^3.0.5",
33
- "snakeia": "^2.2.0-0",
33
+ "snakeia": "^3.0.0",
34
34
  "socket.io": "^4.8.1",
35
35
  "socket.io-cookie-parser": "^1.0.0",
36
- "winston": "^3.17.0"
36
+ "winston": "^3.18.3"
37
37
  }
38
38
  }