@push.rocks/smartproxy 25.11.24 → 25.13.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 (39) hide show
  1. package/changelog.md +16 -0
  2. package/dist_rust/rustproxy_linux_amd64 +0 -0
  3. package/dist_rust/rustproxy_linux_arm64 +0 -0
  4. package/dist_ts/00_commitinfo_data.js +2 -2
  5. package/dist_ts/core/utils/index.d.ts +0 -1
  6. package/dist_ts/core/utils/index.js +1 -2
  7. package/dist_ts/protocols/proxy/index.d.ts +1 -2
  8. package/dist_ts/protocols/proxy/index.js +2 -3
  9. package/dist_ts/protocols/proxy/types.d.ts +1 -1
  10. package/dist_ts/proxies/smart-proxy/datagram-handler-server.d.ts +46 -0
  11. package/dist_ts/proxies/smart-proxy/datagram-handler-server.js +197 -0
  12. package/dist_ts/proxies/smart-proxy/models/metrics-types.d.ts +6 -0
  13. package/dist_ts/proxies/smart-proxy/models/route-types.d.ts +63 -4
  14. package/dist_ts/proxies/smart-proxy/models/route-types.js +1 -1
  15. package/dist_ts/proxies/smart-proxy/route-preprocessor.js +7 -2
  16. package/dist_ts/proxies/smart-proxy/rust-metrics-adapter.d.ts +6 -0
  17. package/dist_ts/proxies/smart-proxy/rust-metrics-adapter.js +7 -1
  18. package/dist_ts/proxies/smart-proxy/rust-proxy-bridge.d.ts +1 -0
  19. package/dist_ts/proxies/smart-proxy/rust-proxy-bridge.js +4 -1
  20. package/dist_ts/proxies/smart-proxy/smart-proxy.d.ts +1 -0
  21. package/dist_ts/proxies/smart-proxy/smart-proxy.js +19 -1
  22. package/package.json +1 -1
  23. package/ts/00_commitinfo_data.ts +1 -1
  24. package/ts/core/utils/index.ts +0 -1
  25. package/ts/protocols/proxy/index.ts +2 -3
  26. package/ts/protocols/proxy/types.ts +1 -1
  27. package/ts/proxies/smart-proxy/datagram-handler-server.ts +239 -0
  28. package/ts/proxies/smart-proxy/models/metrics-types.ts +8 -0
  29. package/ts/proxies/smart-proxy/models/route-types.ts +83 -5
  30. package/ts/proxies/smart-proxy/route-preprocessor.ts +7 -1
  31. package/ts/proxies/smart-proxy/rust-metrics-adapter.ts +7 -0
  32. package/ts/proxies/smart-proxy/rust-proxy-bridge.ts +5 -0
  33. package/ts/proxies/smart-proxy/smart-proxy.ts +23 -0
  34. package/dist_ts/core/utils/proxy-protocol.d.ts +0 -33
  35. package/dist_ts/core/utils/proxy-protocol.js +0 -117
  36. package/dist_ts/protocols/proxy/parser.d.ts +0 -44
  37. package/dist_ts/protocols/proxy/parser.js +0 -153
  38. package/ts/core/utils/proxy-protocol.ts +0 -129
  39. package/ts/protocols/proxy/parser.ts +0 -183
@@ -1,183 +0,0 @@
1
- /**
2
- * PROXY Protocol Parser
3
- * Implementation of HAProxy PROXY protocol v1 (text format)
4
- * Spec: https://www.haproxy.org/download/1.8/doc/proxy-protocol.txt
5
- */
6
-
7
- import type { IProxyInfo, IProxyParseResult, TProxyProtocol } from './types.js';
8
-
9
- /**
10
- * PROXY protocol parser
11
- */
12
- export class ProxyProtocolParser {
13
- static readonly PROXY_V1_SIGNATURE = 'PROXY ';
14
- static readonly MAX_HEADER_LENGTH = 107; // Max length for v1 header
15
- static readonly HEADER_TERMINATOR = '\r\n';
16
-
17
- /**
18
- * Parse PROXY protocol v1 header from buffer
19
- * Returns proxy info and remaining data after header
20
- */
21
- static parse(data: Buffer): IProxyParseResult {
22
- // Check if buffer starts with PROXY signature
23
- if (!data.toString('ascii', 0, 6).startsWith(this.PROXY_V1_SIGNATURE)) {
24
- return {
25
- proxyInfo: null,
26
- remainingData: data
27
- };
28
- }
29
-
30
- // Find header terminator
31
- const headerEndIndex = data.indexOf(this.HEADER_TERMINATOR);
32
- if (headerEndIndex === -1) {
33
- // Header incomplete, need more data
34
- if (data.length > this.MAX_HEADER_LENGTH) {
35
- // Header too long, invalid
36
- throw new Error('PROXY protocol header exceeds maximum length');
37
- }
38
- return {
39
- proxyInfo: null,
40
- remainingData: data
41
- };
42
- }
43
-
44
- // Extract header line
45
- const headerLine = data.toString('ascii', 0, headerEndIndex);
46
- const remainingData = data.slice(headerEndIndex + 2); // Skip \r\n
47
-
48
- // Parse header
49
- const parts = headerLine.split(' ');
50
-
51
- if (parts.length < 2) {
52
- throw new Error(`Invalid PROXY protocol header format: ${headerLine}`);
53
- }
54
-
55
- const [signature, protocol] = parts;
56
-
57
- // Validate protocol
58
- if (!['TCP4', 'TCP6', 'UNKNOWN'].includes(protocol)) {
59
- throw new Error(`Invalid PROXY protocol: ${protocol}`);
60
- }
61
-
62
- // For UNKNOWN protocol, ignore addresses
63
- if (protocol === 'UNKNOWN') {
64
- return {
65
- proxyInfo: {
66
- protocol: 'UNKNOWN',
67
- sourceIP: '',
68
- sourcePort: 0,
69
- destinationIP: '',
70
- destinationPort: 0
71
- },
72
- remainingData
73
- };
74
- }
75
-
76
- // For TCP4/TCP6, we need all 6 parts
77
- if (parts.length !== 6) {
78
- throw new Error(`Invalid PROXY protocol header format: ${headerLine}`);
79
- }
80
-
81
- const [, , srcIP, dstIP, srcPort, dstPort] = parts;
82
-
83
- // Validate and parse ports
84
- const sourcePort = parseInt(srcPort, 10);
85
- const destinationPort = parseInt(dstPort, 10);
86
-
87
- if (isNaN(sourcePort) || sourcePort < 0 || sourcePort > 65535) {
88
- throw new Error(`Invalid source port: ${srcPort}`);
89
- }
90
-
91
- if (isNaN(destinationPort) || destinationPort < 0 || destinationPort > 65535) {
92
- throw new Error(`Invalid destination port: ${dstPort}`);
93
- }
94
-
95
- // Validate IP addresses
96
- const protocolType = protocol as TProxyProtocol;
97
- if (!this.isValidIP(srcIP, protocolType)) {
98
- throw new Error(`Invalid source IP for ${protocol}: ${srcIP}`);
99
- }
100
-
101
- if (!this.isValidIP(dstIP, protocolType)) {
102
- throw new Error(`Invalid destination IP for ${protocol}: ${dstIP}`);
103
- }
104
-
105
- return {
106
- proxyInfo: {
107
- protocol: protocolType,
108
- sourceIP: srcIP,
109
- sourcePort,
110
- destinationIP: dstIP,
111
- destinationPort
112
- },
113
- remainingData
114
- };
115
- }
116
-
117
- /**
118
- * Generate PROXY protocol v1 header
119
- */
120
- static generate(info: IProxyInfo): Buffer {
121
- if (info.protocol === 'UNKNOWN') {
122
- return Buffer.from(`PROXY UNKNOWN\r\n`, 'ascii');
123
- }
124
-
125
- const header = `PROXY ${info.protocol} ${info.sourceIP} ${info.destinationIP} ${info.sourcePort} ${info.destinationPort}\r\n`;
126
-
127
- if (header.length > this.MAX_HEADER_LENGTH) {
128
- throw new Error('Generated PROXY protocol header exceeds maximum length');
129
- }
130
-
131
- return Buffer.from(header, 'ascii');
132
- }
133
-
134
- /**
135
- * Validate IP address format
136
- */
137
- static isValidIP(ip: string, protocol: TProxyProtocol): boolean {
138
- if (protocol === 'TCP4') {
139
- return this.isIPv4(ip);
140
- } else if (protocol === 'TCP6') {
141
- return this.isIPv6(ip);
142
- }
143
- return false;
144
- }
145
-
146
- /**
147
- * Check if string is valid IPv4
148
- */
149
- static isIPv4(ip: string): boolean {
150
- const parts = ip.split('.');
151
- if (parts.length !== 4) return false;
152
-
153
- for (const part of parts) {
154
- const num = parseInt(part, 10);
155
- if (isNaN(num) || num < 0 || num > 255 || part !== num.toString()) {
156
- return false;
157
- }
158
- }
159
- return true;
160
- }
161
-
162
- /**
163
- * Check if string is valid IPv6
164
- */
165
- static isIPv6(ip: string): boolean {
166
- // Basic IPv6 validation
167
- const ipv6Regex = /^(([0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:)|fe80:(:[0-9a-fA-F]{0,4}){0,4}%[0-9a-zA-Z]{1,}|::(ffff(:0{1,4}){0,1}:){0,1}((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])|([0-9a-fA-F]{1,4}:){1,4}:((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]))$/;
168
- return ipv6Regex.test(ip);
169
- }
170
-
171
- /**
172
- * Create a connection ID string for tracking
173
- */
174
- static createConnectionId(connectionInfo: {
175
- sourceIp?: string;
176
- sourcePort?: number;
177
- destIp?: string;
178
- destPort?: number;
179
- }): string {
180
- const { sourceIp, sourcePort, destIp, destPort } = connectionInfo;
181
- return `${sourceIp}:${sourcePort}-${destIp}:${destPort}`;
182
- }
183
- }