@push.rocks/smartproxy 5.0.0 → 6.0.0

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.
Files changed (78) hide show
  1. package/dist_ts/00_commitinfo_data.js +1 -1
  2. package/dist_ts/classes.pp.interfaces.d.ts +23 -0
  3. package/dist_ts/classes.pp.networkproxybridge.d.ts +15 -1
  4. package/dist_ts/classes.pp.networkproxybridge.js +116 -21
  5. package/dist_ts/classes.pp.portproxy.d.ts +20 -4
  6. package/dist_ts/classes.pp.portproxy.js +321 -22
  7. package/dist_ts/index.d.ts +6 -6
  8. package/dist_ts/index.js +7 -7
  9. package/dist_ts/networkproxy/classes.np.certificatemanager.d.ts +77 -0
  10. package/dist_ts/networkproxy/classes.np.certificatemanager.js +354 -0
  11. package/dist_ts/networkproxy/classes.np.connectionpool.d.ts +47 -0
  12. package/dist_ts/networkproxy/classes.np.connectionpool.js +210 -0
  13. package/dist_ts/networkproxy/classes.np.networkproxy.d.ts +117 -0
  14. package/dist_ts/networkproxy/classes.np.networkproxy.js +375 -0
  15. package/dist_ts/networkproxy/classes.np.requesthandler.d.ts +51 -0
  16. package/dist_ts/networkproxy/classes.np.requesthandler.js +210 -0
  17. package/dist_ts/networkproxy/classes.np.types.d.ts +82 -0
  18. package/dist_ts/networkproxy/classes.np.types.js +35 -0
  19. package/dist_ts/networkproxy/classes.np.websockethandler.d.ts +38 -0
  20. package/dist_ts/networkproxy/classes.np.websockethandler.js +188 -0
  21. package/dist_ts/networkproxy/index.d.ts +6 -0
  22. package/dist_ts/networkproxy/index.js +8 -0
  23. package/dist_ts/nfttablesproxy/classes.nftablesproxy.d.ts +219 -0
  24. package/dist_ts/nfttablesproxy/classes.nftablesproxy.js +1542 -0
  25. package/dist_ts/port80handler/classes.port80handler.d.ts +260 -0
  26. package/dist_ts/port80handler/classes.port80handler.js +928 -0
  27. package/dist_ts/smartproxy/classes.pp.connectionhandler.d.ts +39 -0
  28. package/dist_ts/smartproxy/classes.pp.connectionhandler.js +754 -0
  29. package/dist_ts/smartproxy/classes.pp.connectionmanager.d.ts +78 -0
  30. package/dist_ts/smartproxy/classes.pp.connectionmanager.js +378 -0
  31. package/dist_ts/smartproxy/classes.pp.domainconfigmanager.d.ts +55 -0
  32. package/dist_ts/smartproxy/classes.pp.domainconfigmanager.js +103 -0
  33. package/dist_ts/smartproxy/classes.pp.interfaces.d.ts +133 -0
  34. package/dist_ts/smartproxy/classes.pp.interfaces.js +2 -0
  35. package/dist_ts/smartproxy/classes.pp.networkproxybridge.d.ts +57 -0
  36. package/dist_ts/smartproxy/classes.pp.networkproxybridge.js +306 -0
  37. package/dist_ts/smartproxy/classes.pp.portrangemanager.d.ts +56 -0
  38. package/dist_ts/smartproxy/classes.pp.portrangemanager.js +179 -0
  39. package/dist_ts/smartproxy/classes.pp.securitymanager.d.ts +47 -0
  40. package/dist_ts/smartproxy/classes.pp.securitymanager.js +126 -0
  41. package/dist_ts/smartproxy/classes.pp.snihandler.d.ts +153 -0
  42. package/dist_ts/smartproxy/classes.pp.snihandler.js +1053 -0
  43. package/dist_ts/smartproxy/classes.pp.timeoutmanager.d.ts +47 -0
  44. package/dist_ts/smartproxy/classes.pp.timeoutmanager.js +154 -0
  45. package/dist_ts/smartproxy/classes.pp.tlsalert.d.ts +149 -0
  46. package/dist_ts/smartproxy/classes.pp.tlsalert.js +225 -0
  47. package/dist_ts/smartproxy/classes.pp.tlsmanager.d.ts +57 -0
  48. package/dist_ts/smartproxy/classes.pp.tlsmanager.js +132 -0
  49. package/dist_ts/smartproxy/classes.smartproxy.d.ts +64 -0
  50. package/dist_ts/smartproxy/classes.smartproxy.js +567 -0
  51. package/package.json +1 -1
  52. package/readme.md +77 -27
  53. package/ts/00_commitinfo_data.ts +1 -1
  54. package/ts/index.ts +6 -6
  55. package/ts/networkproxy/classes.np.certificatemanager.ts +398 -0
  56. package/ts/networkproxy/classes.np.connectionpool.ts +241 -0
  57. package/ts/networkproxy/classes.np.networkproxy.ts +469 -0
  58. package/ts/networkproxy/classes.np.requesthandler.ts +278 -0
  59. package/ts/networkproxy/classes.np.types.ts +123 -0
  60. package/ts/networkproxy/classes.np.websockethandler.ts +226 -0
  61. package/ts/networkproxy/index.ts +7 -0
  62. package/ts/{classes.port80handler.ts → port80handler/classes.port80handler.ts} +249 -1
  63. package/ts/{classes.pp.connectionhandler.ts → smartproxy/classes.pp.connectionhandler.ts} +1 -1
  64. package/ts/{classes.pp.connectionmanager.ts → smartproxy/classes.pp.connectionmanager.ts} +1 -1
  65. package/ts/{classes.pp.domainconfigmanager.ts → smartproxy/classes.pp.domainconfigmanager.ts} +1 -1
  66. package/ts/{classes.pp.interfaces.ts → smartproxy/classes.pp.interfaces.ts} +31 -5
  67. package/ts/{classes.pp.networkproxybridge.ts → smartproxy/classes.pp.networkproxybridge.ts} +129 -28
  68. package/ts/{classes.pp.securitymanager.ts → smartproxy/classes.pp.securitymanager.ts} +1 -1
  69. package/ts/{classes.pp.tlsmanager.ts → smartproxy/classes.pp.tlsmanager.ts} +1 -1
  70. package/ts/smartproxy/classes.smartproxy.ts +679 -0
  71. package/ts/classes.networkproxy.ts +0 -1730
  72. package/ts/classes.pp.acmemanager.ts +0 -149
  73. package/ts/classes.pp.portproxy.ts +0 -344
  74. /package/ts/{classes.nftablesproxy.ts → nfttablesproxy/classes.nftablesproxy.ts} +0 -0
  75. /package/ts/{classes.pp.portrangemanager.ts → smartproxy/classes.pp.portrangemanager.ts} +0 -0
  76. /package/ts/{classes.pp.snihandler.ts → smartproxy/classes.pp.snihandler.ts} +0 -0
  77. /package/ts/{classes.pp.timeoutmanager.ts → smartproxy/classes.pp.timeoutmanager.ts} +0 -0
  78. /package/ts/{classes.pp.tlsalert.ts → smartproxy/classes.pp.tlsalert.ts} +0 -0
@@ -0,0 +1,117 @@
1
+ import * as plugins from '../plugins.js';
2
+ import { type INetworkProxyOptions, type IReverseProxyConfig } from './classes.np.types.js';
3
+ import { type IMetricsTracker } from './classes.np.requesthandler.js';
4
+ import { Port80Handler } from '../port80handler/classes.port80handler.js';
5
+ /**
6
+ * NetworkProxy provides a reverse proxy with TLS termination, WebSocket support,
7
+ * automatic certificate management, and high-performance connection pooling.
8
+ */
9
+ export declare class NetworkProxy implements IMetricsTracker {
10
+ options: INetworkProxyOptions;
11
+ proxyConfigs: IReverseProxyConfig[];
12
+ httpsServer: plugins.https.Server;
13
+ private certificateManager;
14
+ private connectionPool;
15
+ private requestHandler;
16
+ private webSocketHandler;
17
+ private router;
18
+ socketMap: plugins.lik.ObjectMap<plugins.net.Socket>;
19
+ activeContexts: Set<string>;
20
+ connectedClients: number;
21
+ startTime: number;
22
+ requestsServed: number;
23
+ failedRequests: number;
24
+ private portProxyConnections;
25
+ private tlsTerminatedConnections;
26
+ private metricsInterval;
27
+ private connectionPoolCleanupInterval;
28
+ private logger;
29
+ /**
30
+ * Creates a new NetworkProxy instance
31
+ */
32
+ constructor(optionsArg: INetworkProxyOptions);
33
+ /**
34
+ * Implements IMetricsTracker interface to increment request counters
35
+ */
36
+ incrementRequestsServed(): void;
37
+ /**
38
+ * Implements IMetricsTracker interface to increment failed request counters
39
+ */
40
+ incrementFailedRequests(): void;
41
+ /**
42
+ * Returns the port number this NetworkProxy is listening on
43
+ * Useful for PortProxy to determine where to forward connections
44
+ */
45
+ getListeningPort(): number;
46
+ /**
47
+ * Updates the server capacity settings
48
+ * @param maxConnections Maximum number of simultaneous connections
49
+ * @param keepAliveTimeout Keep-alive timeout in milliseconds
50
+ * @param connectionPoolSize Size of the connection pool per backend
51
+ */
52
+ updateCapacity(maxConnections?: number, keepAliveTimeout?: number, connectionPoolSize?: number): void;
53
+ /**
54
+ * Returns current server metrics
55
+ * Useful for PortProxy to determine which NetworkProxy to use for load balancing
56
+ */
57
+ getMetrics(): any;
58
+ /**
59
+ * Sets an external Port80Handler for certificate management
60
+ * This allows the NetworkProxy to use a centrally managed Port80Handler
61
+ * instead of creating its own
62
+ *
63
+ * @param handler The Port80Handler instance to use
64
+ */
65
+ setExternalPort80Handler(handler: Port80Handler): void;
66
+ /**
67
+ * Starts the proxy server
68
+ */
69
+ start(): Promise<void>;
70
+ /**
71
+ * Sets up tracking of TCP connections
72
+ */
73
+ private setupConnectionTracking;
74
+ /**
75
+ * Sets up metrics collection
76
+ */
77
+ private setupMetricsCollection;
78
+ /**
79
+ * Updates proxy configurations
80
+ */
81
+ updateProxyConfigs(proxyConfigsArg: plugins.tsclass.network.IReverseProxyConfig[]): Promise<void>;
82
+ /**
83
+ * Converts PortProxy domain configurations to NetworkProxy configs
84
+ * @param domainConfigs PortProxy domain configs
85
+ * @param sslKeyPair Default SSL key pair to use if not specified
86
+ * @returns Array of NetworkProxy configs
87
+ */
88
+ convertPortProxyConfigs(domainConfigs: Array<{
89
+ domains: string[];
90
+ targetIPs?: string[];
91
+ allowedIPs?: string[];
92
+ }>, sslKeyPair?: {
93
+ key: string;
94
+ cert: string;
95
+ }): plugins.tsclass.network.IReverseProxyConfig[];
96
+ /**
97
+ * Adds default headers to be included in all responses
98
+ */
99
+ addDefaultHeaders(headersArg: {
100
+ [key: string]: string;
101
+ }): Promise<void>;
102
+ /**
103
+ * Stops the proxy server
104
+ */
105
+ stop(): Promise<void>;
106
+ /**
107
+ * Requests a new certificate for a domain
108
+ * This can be used to manually trigger certificate issuance
109
+ * @param domain The domain to request a certificate for
110
+ * @returns A promise that resolves when the request is submitted (not when the certificate is issued)
111
+ */
112
+ requestCertificate(domain: string): Promise<boolean>;
113
+ /**
114
+ * Gets all proxy configurations currently in use
115
+ */
116
+ getProxyConfigs(): plugins.tsclass.network.IReverseProxyConfig[];
117
+ }
@@ -0,0 +1,375 @@
1
+ import * as plugins from '../plugins.js';
2
+ import { createLogger } from './classes.np.types.js';
3
+ import { CertificateManager } from './classes.np.certificatemanager.js';
4
+ import { ConnectionPool } from './classes.np.connectionpool.js';
5
+ import { RequestHandler } from './classes.np.requesthandler.js';
6
+ import { WebSocketHandler } from './classes.np.websockethandler.js';
7
+ import { ProxyRouter } from '../classes.router.js';
8
+ import { Port80Handler } from '../port80handler/classes.port80handler.js';
9
+ /**
10
+ * NetworkProxy provides a reverse proxy with TLS termination, WebSocket support,
11
+ * automatic certificate management, and high-performance connection pooling.
12
+ */
13
+ export class NetworkProxy {
14
+ /**
15
+ * Creates a new NetworkProxy instance
16
+ */
17
+ constructor(optionsArg) {
18
+ this.proxyConfigs = [];
19
+ this.router = new ProxyRouter();
20
+ // State tracking
21
+ this.socketMap = new plugins.lik.ObjectMap();
22
+ this.activeContexts = new Set();
23
+ this.connectedClients = 0;
24
+ this.startTime = 0;
25
+ this.requestsServed = 0;
26
+ this.failedRequests = 0;
27
+ // Tracking for PortProxy integration
28
+ this.portProxyConnections = 0;
29
+ this.tlsTerminatedConnections = 0;
30
+ // Set default options
31
+ this.options = {
32
+ port: optionsArg.port,
33
+ maxConnections: optionsArg.maxConnections || 10000,
34
+ keepAliveTimeout: optionsArg.keepAliveTimeout || 120000, // 2 minutes
35
+ headersTimeout: optionsArg.headersTimeout || 60000, // 1 minute
36
+ logLevel: optionsArg.logLevel || 'info',
37
+ cors: optionsArg.cors || {
38
+ allowOrigin: '*',
39
+ allowMethods: 'GET, POST, PUT, DELETE, OPTIONS',
40
+ allowHeaders: 'Content-Type, Authorization',
41
+ maxAge: 86400
42
+ },
43
+ // Defaults for PortProxy integration
44
+ connectionPoolSize: optionsArg.connectionPoolSize || 50,
45
+ portProxyIntegration: optionsArg.portProxyIntegration || false,
46
+ useExternalPort80Handler: optionsArg.useExternalPort80Handler || false,
47
+ // Default ACME options
48
+ acme: {
49
+ enabled: optionsArg.acme?.enabled || false,
50
+ port: optionsArg.acme?.port || 80,
51
+ contactEmail: optionsArg.acme?.contactEmail || 'admin@example.com',
52
+ useProduction: optionsArg.acme?.useProduction || false, // Default to staging for safety
53
+ renewThresholdDays: optionsArg.acme?.renewThresholdDays || 30,
54
+ autoRenew: optionsArg.acme?.autoRenew !== false, // Default to true
55
+ certificateStore: optionsArg.acme?.certificateStore || './certs',
56
+ skipConfiguredCerts: optionsArg.acme?.skipConfiguredCerts || false
57
+ }
58
+ };
59
+ // Initialize logger
60
+ this.logger = createLogger(this.options.logLevel);
61
+ // Initialize components
62
+ this.certificateManager = new CertificateManager(this.options);
63
+ this.connectionPool = new ConnectionPool(this.options);
64
+ this.requestHandler = new RequestHandler(this.options, this.connectionPool, this.router);
65
+ this.webSocketHandler = new WebSocketHandler(this.options, this.connectionPool, this.router);
66
+ // Connect request handler to this metrics tracker
67
+ this.requestHandler.setMetricsTracker(this);
68
+ }
69
+ /**
70
+ * Implements IMetricsTracker interface to increment request counters
71
+ */
72
+ incrementRequestsServed() {
73
+ this.requestsServed++;
74
+ }
75
+ /**
76
+ * Implements IMetricsTracker interface to increment failed request counters
77
+ */
78
+ incrementFailedRequests() {
79
+ this.failedRequests++;
80
+ }
81
+ /**
82
+ * Returns the port number this NetworkProxy is listening on
83
+ * Useful for PortProxy to determine where to forward connections
84
+ */
85
+ getListeningPort() {
86
+ return this.options.port;
87
+ }
88
+ /**
89
+ * Updates the server capacity settings
90
+ * @param maxConnections Maximum number of simultaneous connections
91
+ * @param keepAliveTimeout Keep-alive timeout in milliseconds
92
+ * @param connectionPoolSize Size of the connection pool per backend
93
+ */
94
+ updateCapacity(maxConnections, keepAliveTimeout, connectionPoolSize) {
95
+ if (maxConnections !== undefined) {
96
+ this.options.maxConnections = maxConnections;
97
+ this.logger.info(`Updated max connections to ${maxConnections}`);
98
+ }
99
+ if (keepAliveTimeout !== undefined) {
100
+ this.options.keepAliveTimeout = keepAliveTimeout;
101
+ if (this.httpsServer) {
102
+ this.httpsServer.keepAliveTimeout = keepAliveTimeout;
103
+ this.logger.info(`Updated keep-alive timeout to ${keepAliveTimeout}ms`);
104
+ }
105
+ }
106
+ if (connectionPoolSize !== undefined) {
107
+ this.options.connectionPoolSize = connectionPoolSize;
108
+ this.logger.info(`Updated connection pool size to ${connectionPoolSize}`);
109
+ // Clean up excess connections in the pool
110
+ this.connectionPool.cleanupConnectionPool();
111
+ }
112
+ }
113
+ /**
114
+ * Returns current server metrics
115
+ * Useful for PortProxy to determine which NetworkProxy to use for load balancing
116
+ */
117
+ getMetrics() {
118
+ return {
119
+ activeConnections: this.connectedClients,
120
+ totalRequests: this.requestsServed,
121
+ failedRequests: this.failedRequests,
122
+ portProxyConnections: this.portProxyConnections,
123
+ tlsTerminatedConnections: this.tlsTerminatedConnections,
124
+ connectionPoolSize: this.connectionPool.getPoolStatus(),
125
+ uptime: Math.floor((Date.now() - this.startTime) / 1000),
126
+ memoryUsage: process.memoryUsage(),
127
+ activeWebSockets: this.webSocketHandler.getConnectionInfo().activeConnections
128
+ };
129
+ }
130
+ /**
131
+ * Sets an external Port80Handler for certificate management
132
+ * This allows the NetworkProxy to use a centrally managed Port80Handler
133
+ * instead of creating its own
134
+ *
135
+ * @param handler The Port80Handler instance to use
136
+ */
137
+ setExternalPort80Handler(handler) {
138
+ // Connect it to the certificate manager
139
+ this.certificateManager.setExternalPort80Handler(handler);
140
+ }
141
+ /**
142
+ * Starts the proxy server
143
+ */
144
+ async start() {
145
+ this.startTime = Date.now();
146
+ // Initialize Port80Handler if enabled and not using external handler
147
+ if (this.options.acme?.enabled && !this.options.useExternalPort80Handler) {
148
+ await this.certificateManager.initializePort80Handler();
149
+ }
150
+ // Create the HTTPS server
151
+ this.httpsServer = plugins.https.createServer({
152
+ key: this.certificateManager.getDefaultCertificates().key,
153
+ cert: this.certificateManager.getDefaultCertificates().cert,
154
+ SNICallback: (domain, cb) => this.certificateManager.handleSNI(domain, cb)
155
+ }, (req, res) => this.requestHandler.handleRequest(req, res));
156
+ // Configure server timeouts
157
+ this.httpsServer.keepAliveTimeout = this.options.keepAliveTimeout;
158
+ this.httpsServer.headersTimeout = this.options.headersTimeout;
159
+ // Setup connection tracking
160
+ this.setupConnectionTracking();
161
+ // Share HTTPS server with certificate manager
162
+ this.certificateManager.setHttpsServer(this.httpsServer);
163
+ // Setup WebSocket support
164
+ this.webSocketHandler.initialize(this.httpsServer);
165
+ // Start metrics collection
166
+ this.setupMetricsCollection();
167
+ // Setup connection pool cleanup interval
168
+ this.connectionPoolCleanupInterval = this.connectionPool.setupPeriodicCleanup();
169
+ // Start the server
170
+ return new Promise((resolve) => {
171
+ this.httpsServer.listen(this.options.port, () => {
172
+ this.logger.info(`NetworkProxy started on port ${this.options.port}`);
173
+ resolve();
174
+ });
175
+ });
176
+ }
177
+ /**
178
+ * Sets up tracking of TCP connections
179
+ */
180
+ setupConnectionTracking() {
181
+ this.httpsServer.on('connection', (connection) => {
182
+ // Check if max connections reached
183
+ if (this.socketMap.getArray().length >= this.options.maxConnections) {
184
+ this.logger.warn(`Max connections (${this.options.maxConnections}) reached, rejecting new connection`);
185
+ connection.destroy();
186
+ return;
187
+ }
188
+ // Add connection to tracking
189
+ this.socketMap.add(connection);
190
+ this.connectedClients = this.socketMap.getArray().length;
191
+ // Check for connection from PortProxy by inspecting the source port
192
+ const localPort = connection.localPort || 0;
193
+ const remotePort = connection.remotePort || 0;
194
+ // If this connection is from a PortProxy (usually indicated by it coming from localhost)
195
+ if (this.options.portProxyIntegration && connection.remoteAddress?.includes('127.0.0.1')) {
196
+ this.portProxyConnections++;
197
+ this.logger.debug(`New connection from PortProxy (local: ${localPort}, remote: ${remotePort})`);
198
+ }
199
+ else {
200
+ this.logger.debug(`New direct connection (local: ${localPort}, remote: ${remotePort})`);
201
+ }
202
+ // Setup connection cleanup handlers
203
+ const cleanupConnection = () => {
204
+ if (this.socketMap.checkForObject(connection)) {
205
+ this.socketMap.remove(connection);
206
+ this.connectedClients = this.socketMap.getArray().length;
207
+ // If this was a PortProxy connection, decrement the counter
208
+ if (this.options.portProxyIntegration && connection.remoteAddress?.includes('127.0.0.1')) {
209
+ this.portProxyConnections--;
210
+ }
211
+ this.logger.debug(`Connection closed. ${this.connectedClients} connections remaining`);
212
+ }
213
+ };
214
+ connection.on('close', cleanupConnection);
215
+ connection.on('error', (err) => {
216
+ this.logger.debug('Connection error', err);
217
+ cleanupConnection();
218
+ });
219
+ connection.on('end', cleanupConnection);
220
+ });
221
+ // Track TLS handshake completions
222
+ this.httpsServer.on('secureConnection', (tlsSocket) => {
223
+ this.tlsTerminatedConnections++;
224
+ this.logger.debug('TLS handshake completed, connection secured');
225
+ });
226
+ }
227
+ /**
228
+ * Sets up metrics collection
229
+ */
230
+ setupMetricsCollection() {
231
+ this.metricsInterval = setInterval(() => {
232
+ const uptime = Math.floor((Date.now() - this.startTime) / 1000);
233
+ const metrics = {
234
+ uptime,
235
+ activeConnections: this.connectedClients,
236
+ totalRequests: this.requestsServed,
237
+ failedRequests: this.failedRequests,
238
+ portProxyConnections: this.portProxyConnections,
239
+ tlsTerminatedConnections: this.tlsTerminatedConnections,
240
+ activeWebSockets: this.webSocketHandler.getConnectionInfo().activeConnections,
241
+ memoryUsage: process.memoryUsage(),
242
+ activeContexts: Array.from(this.activeContexts),
243
+ connectionPool: this.connectionPool.getPoolStatus()
244
+ };
245
+ this.logger.debug('Proxy metrics', metrics);
246
+ }, 60000); // Log metrics every minute
247
+ // Don't keep process alive just for metrics
248
+ if (this.metricsInterval.unref) {
249
+ this.metricsInterval.unref();
250
+ }
251
+ }
252
+ /**
253
+ * Updates proxy configurations
254
+ */
255
+ async updateProxyConfigs(proxyConfigsArg) {
256
+ this.logger.info(`Updating proxy configurations (${proxyConfigsArg.length} configs)`);
257
+ // Update internal configs
258
+ this.proxyConfigs = proxyConfigsArg;
259
+ this.router.setNewProxyConfigs(proxyConfigsArg);
260
+ // Collect all hostnames for cleanup later
261
+ const currentHostNames = new Set();
262
+ // Add/update SSL contexts for each host
263
+ for (const config of proxyConfigsArg) {
264
+ currentHostNames.add(config.hostName);
265
+ try {
266
+ // Update certificate in cache
267
+ this.certificateManager.updateCertificateCache(config.hostName, config.publicKey, config.privateKey);
268
+ this.activeContexts.add(config.hostName);
269
+ }
270
+ catch (error) {
271
+ this.logger.error(`Failed to add SSL context for ${config.hostName}`, error);
272
+ }
273
+ }
274
+ // Clean up removed contexts
275
+ for (const hostname of this.activeContexts) {
276
+ if (!currentHostNames.has(hostname)) {
277
+ this.logger.info(`Hostname ${hostname} removed from configuration`);
278
+ this.activeContexts.delete(hostname);
279
+ }
280
+ }
281
+ // Register domains with Port80Handler if available
282
+ const domainsForACME = Array.from(currentHostNames)
283
+ .filter(domain => !domain.includes('*')); // Skip wildcard domains
284
+ this.certificateManager.registerDomainsWithPort80Handler(domainsForACME);
285
+ }
286
+ /**
287
+ * Converts PortProxy domain configurations to NetworkProxy configs
288
+ * @param domainConfigs PortProxy domain configs
289
+ * @param sslKeyPair Default SSL key pair to use if not specified
290
+ * @returns Array of NetworkProxy configs
291
+ */
292
+ convertPortProxyConfigs(domainConfigs, sslKeyPair) {
293
+ const proxyConfigs = [];
294
+ // Use default certificates if not provided
295
+ const defaultCerts = this.certificateManager.getDefaultCertificates();
296
+ const sslKey = sslKeyPair?.key || defaultCerts.key;
297
+ const sslCert = sslKeyPair?.cert || defaultCerts.cert;
298
+ for (const domainConfig of domainConfigs) {
299
+ // Each domain in the domains array gets its own config
300
+ for (const domain of domainConfig.domains) {
301
+ // Skip non-hostname patterns (like IP addresses)
302
+ if (domain.match(/^\d+\.\d+\.\d+\.\d+$/) || domain === '*' || domain === 'localhost') {
303
+ continue;
304
+ }
305
+ proxyConfigs.push({
306
+ hostName: domain,
307
+ destinationIps: domainConfig.targetIPs || ['localhost'],
308
+ destinationPorts: [this.options.port], // Use the NetworkProxy port
309
+ privateKey: sslKey,
310
+ publicKey: sslCert
311
+ });
312
+ }
313
+ }
314
+ this.logger.info(`Converted ${domainConfigs.length} PortProxy configs to ${proxyConfigs.length} NetworkProxy configs`);
315
+ return proxyConfigs;
316
+ }
317
+ /**
318
+ * Adds default headers to be included in all responses
319
+ */
320
+ async addDefaultHeaders(headersArg) {
321
+ this.logger.info('Adding default headers', headersArg);
322
+ this.requestHandler.setDefaultHeaders(headersArg);
323
+ }
324
+ /**
325
+ * Stops the proxy server
326
+ */
327
+ async stop() {
328
+ this.logger.info('Stopping NetworkProxy server');
329
+ // Clear intervals
330
+ if (this.metricsInterval) {
331
+ clearInterval(this.metricsInterval);
332
+ }
333
+ if (this.connectionPoolCleanupInterval) {
334
+ clearInterval(this.connectionPoolCleanupInterval);
335
+ }
336
+ // Stop WebSocket handler
337
+ this.webSocketHandler.shutdown();
338
+ // Close all tracked sockets
339
+ for (const socket of this.socketMap.getArray()) {
340
+ try {
341
+ socket.destroy();
342
+ }
343
+ catch (error) {
344
+ this.logger.error('Error destroying socket', error);
345
+ }
346
+ }
347
+ // Close all connection pool connections
348
+ this.connectionPool.closeAllConnections();
349
+ // Stop Port80Handler if internally managed
350
+ await this.certificateManager.stopPort80Handler();
351
+ // Close the HTTPS server
352
+ return new Promise((resolve) => {
353
+ this.httpsServer.close(() => {
354
+ this.logger.info('NetworkProxy server stopped successfully');
355
+ resolve();
356
+ });
357
+ });
358
+ }
359
+ /**
360
+ * Requests a new certificate for a domain
361
+ * This can be used to manually trigger certificate issuance
362
+ * @param domain The domain to request a certificate for
363
+ * @returns A promise that resolves when the request is submitted (not when the certificate is issued)
364
+ */
365
+ async requestCertificate(domain) {
366
+ return this.certificateManager.requestCertificate(domain);
367
+ }
368
+ /**
369
+ * Gets all proxy configurations currently in use
370
+ */
371
+ getProxyConfigs() {
372
+ return [...this.proxyConfigs];
373
+ }
374
+ }
375
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY2xhc3Nlcy5ucC5uZXR3b3JrcHJveHkuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi90cy9uZXR3b3JrcHJveHkvY2xhc3Nlcy5ucC5uZXR3b3JrcHJveHkudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxLQUFLLE9BQU8sTUFBTSxlQUFlLENBQUM7QUFDekMsT0FBTyxFQUEyQyxZQUFZLEVBQTRCLE1BQU0sdUJBQXVCLENBQUM7QUFDeEgsT0FBTyxFQUFFLGtCQUFrQixFQUFFLE1BQU0sb0NBQW9DLENBQUM7QUFDeEUsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLGdDQUFnQyxDQUFDO0FBQ2hFLE9BQU8sRUFBRSxjQUFjLEVBQXdCLE1BQU0sZ0NBQWdDLENBQUM7QUFDdEYsT0FBTyxFQUFFLGdCQUFnQixFQUFFLE1BQU0sa0NBQWtDLENBQUM7QUFDcEUsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBQ25ELE9BQU8sRUFBRSxhQUFhLEVBQUUsTUFBTSwyQ0FBMkMsQ0FBQztBQUUxRTs7O0dBR0c7QUFDSCxNQUFNLE9BQU8sWUFBWTtJQWtDdkI7O09BRUc7SUFDSCxZQUFZLFVBQWdDO1FBbENyQyxpQkFBWSxHQUEwQixFQUFFLENBQUM7UUFVeEMsV0FBTSxHQUFHLElBQUksV0FBVyxFQUFFLENBQUM7UUFFbkMsaUJBQWlCO1FBQ1YsY0FBUyxHQUFHLElBQUksT0FBTyxDQUFDLEdBQUcsQ0FBQyxTQUFTLEVBQXNCLENBQUM7UUFDNUQsbUJBQWMsR0FBZ0IsSUFBSSxHQUFHLEVBQUUsQ0FBQztRQUN4QyxxQkFBZ0IsR0FBVyxDQUFDLENBQUM7UUFDN0IsY0FBUyxHQUFXLENBQUMsQ0FBQztRQUN0QixtQkFBYyxHQUFXLENBQUMsQ0FBQztRQUMzQixtQkFBYyxHQUFXLENBQUMsQ0FBQztRQUVsQyxxQ0FBcUM7UUFDN0IseUJBQW9CLEdBQVcsQ0FBQyxDQUFDO1FBQ2pDLDZCQUF3QixHQUFXLENBQUMs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
@@ -0,0 +1,51 @@
1
+ import * as plugins from '../plugins.js';
2
+ import { type INetworkProxyOptions } from './classes.np.types.js';
3
+ import { ConnectionPool } from './classes.np.connectionpool.js';
4
+ import { ProxyRouter } from '../classes.router.js';
5
+ /**
6
+ * Interface for tracking metrics
7
+ */
8
+ export interface IMetricsTracker {
9
+ incrementRequestsServed(): void;
10
+ incrementFailedRequests(): void;
11
+ }
12
+ /**
13
+ * Handles HTTP request processing and proxying
14
+ */
15
+ export declare class RequestHandler {
16
+ private options;
17
+ private connectionPool;
18
+ private router;
19
+ private defaultHeaders;
20
+ private logger;
21
+ private metricsTracker;
22
+ constructor(options: INetworkProxyOptions, connectionPool: ConnectionPool, router: ProxyRouter);
23
+ /**
24
+ * Set the metrics tracker instance
25
+ */
26
+ setMetricsTracker(tracker: IMetricsTracker): void;
27
+ /**
28
+ * Set default headers to be included in all responses
29
+ */
30
+ setDefaultHeaders(headers: {
31
+ [key: string]: string;
32
+ }): void;
33
+ /**
34
+ * Get all default headers
35
+ */
36
+ getDefaultHeaders(): {
37
+ [key: string]: string;
38
+ };
39
+ /**
40
+ * Apply CORS headers to response if configured
41
+ */
42
+ private applyCorsHeaders;
43
+ /**
44
+ * Apply default headers to response
45
+ */
46
+ private applyDefaultHeaders;
47
+ /**
48
+ * Handle an HTTP request
49
+ */
50
+ handleRequest(req: plugins.http.IncomingMessage, res: plugins.http.ServerResponse): Promise<void>;
51
+ }