redweb 0.6.2 → 0.6.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.
@@ -1,69 +1,69 @@
1
- const express = require('express');
2
- const bodyParser = require('body-parser');
3
- const path = require('path');
4
- const cors = require('cors');
5
-
6
- /**
7
- * @typedef {'json' | 'urlencoded'} RedWebEncoding
8
- */
9
-
10
- /**
11
- * RedWeb options object.
12
- * @typedef {Object} RedWebOptions
13
- * @property {number} [port=80] - The port number to bind the server.
14
- * @property {string} [bind='0.0.0.0'] - The bind address for the server.
15
- * @property {string[]} [publicPaths=['./public']] - An array of paths to serve static files from.
16
- * @property {Array<{serviceName: string, method: string, function: Function}>} [services=[]] - An array of services with their endpoints and handlers.
17
- * @property {Function} [listenCallback] - Callback function to execute once the server starts listening.
18
- * @property {RedWebEncoding} [encoding='json'] - The encoding type for the request bodies ('json' or 'urlencoded').
19
- * @property {Object} [ssl] - SSL configuration for HTTPS server.
20
- * @property {string} [ssl.key] - Path to the SSL key file.
21
- * @property {string} [ssl.cert] - Path to the SSL certificate file.
22
- * @property {import('express').Application} [server] - Whether to automatically start listening.
23
- * @property {import('cors').CorsOptions} [corsOptions] - The CORS Options.
24
- */
25
-
26
- const ENCODINGS = { json: 'json', urlencoded: 'urlencoded' };
27
- const HTTP_OPTIONS = {
28
- port: 80,
29
- bind: '0.0.0.0',
30
- publicPaths: ['./public'],
31
- services: [],
32
- listenCallback: undefined,
33
- encoding: ENCODINGS.json,
34
- ssl: null,
35
- server: undefined,
36
- corsOptions: undefined,
37
- };
38
-
39
- /**
40
- * Base HTTP Server
41
- * @param {RedWebOptions} options - Configuration options for RedWeb.
42
- * @return {Object} Express application instance.
43
- */
44
- function BaseHttpServer(options = {}) {
45
- this.options = { ...HTTP_OPTIONS, ...options };
46
- this.app = express() || this.options.server;
47
- Object.assign(this, this.options);
48
-
49
- // Middleware to parse request bodies based on the specified encoding
50
- if (this.encoding === ENCODINGS.json) {
51
- this.app.use(bodyParser.json());
52
- } else if (this.encoding === ENCODINGS.urlencoded) {
53
- this.app.use(bodyParser.urlencoded({ extended: true }));
54
- }
55
- this.app.use(cors(this.options.corsOptions));
56
- this.publicPaths.forEach(public_path => this.app.use(express.static(path.join(process.cwd(), public_path))));
57
- const catchAll = this.services.find((service) => service.serviceName === '*');
58
- if (catchAll) this.services.splice(this.services.indexOf(catchAll), 1);
59
- this.services.forEach(service => this.app[service.method](service.serviceName, service.function));
60
- if (catchAll) this.app[catchAll.method](catchAll.serviceName, catchAll.function);
61
- return this;
62
- }
63
-
64
- module.exports = {
65
- BaseHttpServer,
66
- ENCODINGS,
67
- HTTP_OPTIONS,
68
- METHODS: {GET: 'get', POST: 'post', PUT: 'put', DELETE: 'delete'}
69
- };
1
+ const express = require('express');
2
+ const bodyParser = require('body-parser');
3
+ const path = require('path');
4
+ const cors = require('cors');
5
+
6
+ /**
7
+ * @typedef {'json' | 'urlencoded'} RedWebEncoding
8
+ */
9
+
10
+ /**
11
+ * RedWeb options object.
12
+ * @typedef {Object} RedWebOptions
13
+ * @property {number} [port=80] - The port number to bind the server.
14
+ * @property {string} [bind='0.0.0.0'] - The bind address for the server.
15
+ * @property {string[]} [publicPaths=['./public']] - An array of paths to serve static files from.
16
+ * @property {Array<{serviceName: string, method: string, function: Function}>} [services=[]] - An array of services with their endpoints and handlers.
17
+ * @property {Function} [listenCallback] - Callback function to execute once the server starts listening.
18
+ * @property {RedWebEncoding} [encoding='json'] - The encoding type for the request bodies ('json' or 'urlencoded').
19
+ * @property {Object} [ssl] - SSL configuration for HTTPS server.
20
+ * @property {string} [ssl.key] - Path to the SSL key file.
21
+ * @property {string} [ssl.cert] - Path to the SSL certificate file.
22
+ * @property {import('express').Application} [server] - Whether to automatically start listening.
23
+ * @property {import('cors').CorsOptions} [corsOptions] - The CORS Options.
24
+ */
25
+
26
+ const ENCODINGS = { json: 'json', urlencoded: 'urlencoded' };
27
+ const HTTP_OPTIONS = {
28
+ port: 80,
29
+ bind: '0.0.0.0',
30
+ publicPaths: ['./public'],
31
+ services: [],
32
+ listenCallback: undefined,
33
+ encoding: ENCODINGS.json,
34
+ ssl: null,
35
+ server: undefined,
36
+ corsOptions: undefined,
37
+ };
38
+
39
+ /**
40
+ * Base HTTP Server
41
+ * @param {RedWebOptions} options - Configuration options for RedWeb.
42
+ * @return {Object} Express application instance.
43
+ */
44
+ function BaseHttpServer(options = {}) {
45
+ this.options = { ...HTTP_OPTIONS, ...options };
46
+ this.app = express() || this.options.server;
47
+ Object.assign(this, this.options);
48
+
49
+ // Middleware to parse request bodies based on the specified encoding
50
+ if (this.encoding === ENCODINGS.json) {
51
+ this.app.use(bodyParser.json());
52
+ } else if (this.encoding === ENCODINGS.urlencoded) {
53
+ this.app.use(bodyParser.urlencoded({ extended: true }));
54
+ }
55
+ this.app.use(cors(this.options.corsOptions));
56
+ this.publicPaths.forEach(public_path => this.app.use(express.static(path.join(process.cwd(), public_path))));
57
+ const catchAll = this.services.find((service) => service.serviceName === '*');
58
+ if (catchAll) this.services.splice(this.services.indexOf(catchAll), 1);
59
+ this.services.forEach(service => this.app[service.method](service.serviceName, service.function));
60
+ if (catchAll) this.app[catchAll.method](catchAll.serviceName, catchAll.function);
61
+ return this;
62
+ }
63
+
64
+ module.exports = {
65
+ BaseHttpServer,
66
+ ENCODINGS,
67
+ HTTP_OPTIONS,
68
+ METHODS: {GET: 'get', POST: 'post', PUT: 'put', DELETE: 'delete'}
69
+ };
@@ -1,14 +1,14 @@
1
- const { BaseHttpServer } = require('./BaseHttpServer');
2
-
3
- /**
4
- * HTTP Server
5
- * @param {RedWebOptions} options - Configuration options for RedWeb.
6
- * @return {Object} Express application instance.
7
- */
8
- function HttpServer(options = {}) {
9
- BaseHttpServer.call(this, options);
10
- this.server = this.app.listen(this.port, this.listenCallback ? this.listenCallback : () => console.log(`RedWeb HttpServer listening on port ${this.port}`));
11
- return this;
12
- }
13
-
14
- module.exports = HttpServer;
1
+ const { BaseHttpServer } = require('./BaseHttpServer');
2
+
3
+ /**
4
+ * HTTP Server
5
+ * @param {RedWebOptions} options - Configuration options for RedWeb.
6
+ * @return {Object} Express application instance.
7
+ */
8
+ function HttpServer(options = {}) {
9
+ BaseHttpServer.call(this, options);
10
+ this.server = this.app.listen(this.port, this.listenCallback ? this.listenCallback : () => console.log(`RedWeb HttpServer listening on port ${this.port}`));
11
+ return this;
12
+ }
13
+
14
+ module.exports = HttpServer;
@@ -1,17 +1,17 @@
1
- const https = require('https');
2
- const { BaseHttpServer } = require('./BaseHttpServer');
3
- const loadSslConfig = require('../sslConfig');
4
-
5
- /**
6
- * HTTPS Server
7
- * @param {RedWebOptions} options - Configuration options for RedWeb.
8
- * @return {Object} Express application instance.
9
- */
10
- function HttpsServer(options = {}) {
11
- BaseHttpServer.call(this, options);
12
- const sslOptions = loadSslConfig(this.ssl);
13
- https.createServer(sslOptions, this.app).listen(this.port, this.listenCallback ? this.listenCallback : () => console.log(`RedWeb HttpsServer listening on port ${this.port}`));
14
- return this;
15
- }
16
-
17
- module.exports = HttpsServer;
1
+ const https = require('https');
2
+ const { BaseHttpServer } = require('./BaseHttpServer');
3
+ const loadSslConfig = require('../sslConfig');
4
+
5
+ /**
6
+ * HTTPS Server
7
+ * @param {RedWebOptions} options - Configuration options for RedWeb.
8
+ * @return {Object} Express application instance.
9
+ */
10
+ function HttpsServer(options = {}) {
11
+ BaseHttpServer.call(this, options);
12
+ const sslOptions = loadSslConfig(this.ssl);
13
+ https.createServer(sslOptions, this.app).listen(this.port, this.listenCallback ? this.listenCallback : () => console.log(`RedWeb HttpsServer listening on port ${this.port}`));
14
+ return this;
15
+ }
16
+
17
+ module.exports = HttpsServer;
package/src/http/index.js CHANGED
@@ -1,2 +1,2 @@
1
- const { METHODS } = require('./BaseHttpServer');
1
+ const { METHODS } = require('./BaseHttpServer');
2
2
  module.exports = { HttpServer: require('./HttpServer'), HttpsServer: require('./HttpsServer'), METHODS}
package/src/sslConfig.js CHANGED
@@ -1,20 +1,20 @@
1
- const fs = require('fs');
2
-
3
- /**
4
- * Load SSL configuration
5
- * @param {Object} sslOptions - The SSL options object containing the paths to key and cert files.
6
- * @param {string} sslOptions.key - Path to the SSL key file.
7
- * @param {string} sslOptions.cert - Path to the SSL certificate file.
8
- * @return {Object} - The loaded SSL options containing key and cert.
9
- */
10
- function loadSslConfig(sslOptions) {
11
- if (!sslOptions || !sslOptions.key || !sslOptions.cert) {
12
- throw new Error('SSL key and certificate paths must be provided');
13
- }
14
- return {
15
- key: fs.readFileSync(sslOptions.key),
16
- cert: fs.readFileSync(sslOptions.cert)
17
- };
18
- }
19
-
20
- module.exports = loadSslConfig;
1
+ const fs = require('fs');
2
+
3
+ /**
4
+ * Load SSL configuration
5
+ * @param {Object} sslOptions - The SSL options object containing the paths to key and cert files.
6
+ * @param {string} sslOptions.key - Path to the SSL key file.
7
+ * @param {string} sslOptions.cert - Path to the SSL certificate file.
8
+ * @return {Object} - The loaded SSL options containing key and cert.
9
+ */
10
+ function loadSslConfig(sslOptions) {
11
+ if (!sslOptions || !sslOptions.key || !sslOptions.cert) {
12
+ throw new Error('SSL key and certificate paths must be provided');
13
+ }
14
+ return {
15
+ key: fs.readFileSync(sslOptions.key),
16
+ cert: fs.readFileSync(sslOptions.cert)
17
+ };
18
+ }
19
+
20
+ module.exports = loadSslConfig;
@@ -1,93 +1,98 @@
1
- /**
2
- * Represents the base class for a WebSocket message handler.
3
- */
4
- class BaseHandler {
5
- /**
6
- * Creates a new handler instance.
7
- * @param {{ name: string, handlers: Record<string, (socket: WebSocket, data: object) => void> }} config
8
- * - `name`: The unique name of the handler.
9
- * - `handlers`: A dictionary of message types and their corresponding handler functions.
10
- */
11
- constructor(config) {
12
- /**
13
- * The name of the handler (used to identify this handler in the server).
14
- * @type {string}
15
- */
16
- this.name = config.name;
17
-
18
- /**
19
- * The dictionary of message handlers for this handler.
20
- * @type {Record<string, (socket: WebSocket, data: object) => void>}
21
- */
22
- this.messageHandlers = config.handlers || {};
23
-
24
- /**
25
- * The list of active WebSocket connections managed by this handler.
26
- * @type {WebSocket[]}
27
- */
28
- this.connections = [];
29
- }
30
-
31
- handleSocketMessages(socket) {
32
- socket.on('message', (message) => this.handleMessage(socket, message));
33
- }
34
-
35
- handleSocketClose(socket) {
36
- socket.on('close', () => {
37
- this.connections = this.connections.filter((conn) => conn !== socket);
38
- console.log(`Connection closed for handler "${this.name}".`);
39
- });
40
- }
41
-
42
- handleNewConnection(socket) {
43
- this.connections.push(socket);
44
- this.handleSocketMessages(socket);
45
- this.handleSocketClose(socket);
46
- socket.isAssigned = true;
47
- console.log(`New connection added to handler "${this.name}".`);
48
- }
49
-
50
- /**
51
- * Adds a new WebSocket connection and sets up message handling for this handler.
52
- * @param {WebSocket} socket - The WebSocket connection to add.
53
- */
54
- newConnection(socket, data) {
55
- console.log(`Received newConnection data ${data}`);
56
- this.handleNewConnection(socket);
57
- }
58
-
59
- /**
60
- * Handles an incoming message and routes it to the appropriate handler function.
61
- * @param {WebSocket} socket - The WebSocket connection that sent the message.
62
- * @param {string} message - The incoming message in JSON string format.
63
- */
64
- handleMessage(socket, message) {
65
- try {
66
- const parsedMessage = JSON.parse(message);
67
- const { type, ...data } = parsedMessage;
68
-
69
- if (this.messageHandlers[type]) {
70
- this.messageHandlers[type](socket, data);
71
- } else {
72
- console.warn(`Unhandled message type: "${type}" in handler "${this.name}".`);
73
- socket.close();
74
- }
75
- } catch (error) {
76
- console.error(`Error processing message in handler "${this.name}":`, error);
77
- }
78
- }
79
-
80
- /**
81
- * Broadcasts a message to all connections managed by this handler.
82
- * @param {object} message - The message to broadcast.
83
- */
84
- broadcast(message) {
85
- this.connections.forEach((socket) => {
86
- if (socket.readyState === WebSocket.OPEN) {
87
- socket.send(JSON.stringify(message));
88
- }
89
- });
90
- }
91
- }
92
-
93
- module.exports = { BaseHandler };
1
+ /**
2
+ * Represents the base class for a WebSocket message handler.
3
+ */
4
+ class BaseHandler {
5
+ /**
6
+ * Creates a new handler instance.
7
+ * @param {{ name: string, handlers: Record<string, (socket: WebSocket, data: object) => void> }} config
8
+ * - `name`: The unique name of the handler.
9
+ * - `handlers`: A dictionary of message types and their corresponding handler functions.
10
+ */
11
+ constructor(config) {
12
+ /**
13
+ * The name of the handler (used to identify this handler in the server).
14
+ * @type {string}
15
+ */
16
+ this.name = config.name;
17
+
18
+ /**
19
+ * The dictionary of message handlers for this handler.
20
+ * @type {Record<string, (socket: WebSocket, data: object) => void>}
21
+ */
22
+ this.messageHandlers = config.handlers || {};
23
+
24
+ /**
25
+ * The list of active WebSocket connections managed by this handler.
26
+ * @type {WebSocket[]}
27
+ */
28
+ this.connections = [];
29
+ }
30
+
31
+ handleSocketMessages(socket) {
32
+ socket.on('message', (message) => this.handleMessage(socket, message));
33
+ }
34
+
35
+ handleSocketClose(socket) {
36
+ socket.on('close', () => {
37
+ this.onClose(socket);
38
+ this.connections = this.connections.filter((conn) => conn !== socket);
39
+ console.log(`Connection closed for handler "${this.name}".`);
40
+ });
41
+ }
42
+
43
+ handleNewConnection(socket) {
44
+ this.connections.push(socket);
45
+ this.handleSocketMessages(socket);
46
+ this.handleSocketClose(socket);
47
+ socket.isAssigned = true;
48
+ console.log(`New connection added to handler "${this.name}".`);
49
+ }
50
+
51
+ /**
52
+ * Adds a new WebSocket connection and sets up message handling for this handler.
53
+ * @param {WebSocket} socket - The WebSocket connection to add.
54
+ */
55
+ newConnection(socket, data) {
56
+ console.log(`Received newConnection data ${JSON.stringify(data)}`);
57
+ this.handleNewConnection(socket);
58
+ }
59
+
60
+ onClose(socket) {
61
+ console.log(`Closing socket ${socket.remoteAddress}`);
62
+ }
63
+
64
+ /**
65
+ * Handles an incoming message and routes it to the appropriate handler function.
66
+ * @param {WebSocket} socket - The WebSocket connection that sent the message.
67
+ * @param {string} message - The incoming message in JSON string format.
68
+ */
69
+ handleMessage(socket, message) {
70
+ try {
71
+ const parsedMessage = JSON.parse(message);
72
+ const { type, ...data } = parsedMessage;
73
+
74
+ if (this.messageHandlers[type]) {
75
+ this.messageHandlers[type](socket, data);
76
+ } else {
77
+ console.warn(`Unhandled message type: "${type}" in handler "${this.name}".`);
78
+ socket.close();
79
+ }
80
+ } catch (error) {
81
+ console.error(`Error processing message in handler "${this.name}":`, error);
82
+ }
83
+ }
84
+
85
+ /**
86
+ * Broadcasts a message to all connections managed by this handler.
87
+ * @param {object} message - The message to broadcast.
88
+ */
89
+ broadcast(message) {
90
+ this.connections.forEach((socket) => {
91
+ if (socket.readyState === WebSocket.OPEN) {
92
+ socket.send(JSON.stringify(message));
93
+ }
94
+ });
95
+ }
96
+ }
97
+
98
+ module.exports = { BaseHandler };