From b187da507b1b01a4922b6930a78938a8a3f8d875 Mon Sep 17 00:00:00 2001 From: Philipp Kunz Date: Wed, 28 May 2025 19:26:52 +0000 Subject: [PATCH] feat(manual socket handling): Add comprehensive manual socket handling documentation for advanced DNS server use cases --- changelog.md | 7 ++ readme.md | 213 +++++++++++++++++++++++++++++++++++++++ ts/00_commitinfo_data.ts | 2 +- 3 files changed, 221 insertions(+), 1 deletion(-) diff --git a/changelog.md b/changelog.md index 2445a13..44eefc3 100644 --- a/changelog.md +++ b/changelog.md @@ -1,5 +1,12 @@ # Changelog +## 2025-05-28 - 7.4.0 - feat(manual socket handling) +Add comprehensive manual socket handling documentation for advanced DNS server use cases + +- Introduced detailed examples for configuring manual UDP and HTTPS socket handling +- Provided sample code for load balancing, clustering, custom transport protocols, and multi-interface binding +- Updated performance and best practices sections to reflect manual socket handling benefits + ## 2025-05-28 - 7.3.0 - feat(dnsserver) Add manual socket mode support to enable external socket control for the DNS server. diff --git a/readme.md b/readme.md index 1c0bb2b..e168471 100644 --- a/readme.md +++ b/readme.md @@ -306,6 +306,215 @@ await dnsServer.start(); console.log('DNS Server with Let\'s Encrypt SSL started!'); ``` +### Manual Socket Handling + +The DNS server supports manual socket handling for advanced use cases like clustering, load balancing, and custom transport implementations. You can control UDP and HTTPS socket handling independently. + +#### Configuration Options + +```typescript +export interface IDnsServerOptions { + // ... standard options ... + manualUdpMode?: boolean; // Handle UDP sockets manually + manualHttpsMode?: boolean; // Handle HTTPS sockets manually +} +``` + +#### Basic Manual Socket Usage + +```typescript +import { DnsServer } from '@push.rocks/smartdns/server'; +import * as dgram from 'dgram'; +import * as net from 'net'; + +// Create server with manual UDP mode +const dnsServer = new DnsServer({ + httpsKey: '...', + httpsCert: '...', + httpsPort: 853, + udpPort: 53, + dnssecZone: 'example.com', + manualUdpMode: true // UDP manual, HTTPS automatic +}); + +await dnsServer.start(); // HTTPS binds, UDP doesn't + +// Create your own UDP socket +const udpSocket = dgram.createSocket('udp4'); + +// Handle incoming UDP messages +udpSocket.on('message', (msg, rinfo) => { + dnsServer.handleUdpMessage(msg, rinfo, (response, responseRinfo) => { + // Send response using your socket + udpSocket.send(response, responseRinfo.port, responseRinfo.address); + }); +}); + +// Bind to custom port or multiple interfaces +udpSocket.bind(5353, '0.0.0.0'); +``` + +#### Manual HTTPS Socket Handling + +```typescript +// Create server with manual HTTPS mode +const dnsServer = new DnsServer({ + httpsKey: '...', + httpsCert: '...', + httpsPort: 853, + udpPort: 53, + dnssecZone: 'example.com', + manualHttpsMode: true // HTTPS manual, UDP automatic +}); + +await dnsServer.start(); // UDP binds, HTTPS doesn't + +// Create your own TCP server +const tcpServer = net.createServer((socket) => { + // Pass TCP sockets to DNS server + dnsServer.handleHttpsSocket(socket); +}); + +tcpServer.listen(8853, '0.0.0.0'); +``` + +#### Full Manual Mode + +Control both protocols manually for complete flexibility: + +```typescript +const dnsServer = new DnsServer({ + httpsKey: '...', + httpsCert: '...', + httpsPort: 853, + udpPort: 53, + dnssecZone: 'example.com', + manualUdpMode: true, + manualHttpsMode: true +}); + +await dnsServer.start(); // Neither protocol binds + +// Set up your own socket handling for both protocols +// Perfect for custom routing, load balancing, or clustering +``` + +#### Advanced Use Cases + +##### Load Balancing Across Multiple UDP Sockets + +```typescript +// Create multiple UDP sockets for different CPU cores +const sockets = []; +const numCPUs = require('os').cpus().length; + +for (let i = 0; i < numCPUs; i++) { + const socket = dgram.createSocket({ + type: 'udp4', + reuseAddr: true // Allow multiple sockets on same port + }); + + socket.on('message', (msg, rinfo) => { + dnsServer.handleUdpMessage(msg, rinfo, (response, rinfo) => { + socket.send(response, rinfo.port, rinfo.address); + }); + }); + + socket.bind(53); + sockets.push(socket); +} +``` + +##### Clustering with Worker Processes + +```typescript +import cluster from 'cluster'; +import { DnsServer } from '@push.rocks/smartdns/server'; + +if (cluster.isPrimary) { + // Master process accepts connections + const server = net.createServer({ pauseOnConnect: true }); + + // Distribute connections to workers + server.on('connection', (socket) => { + const worker = getNextWorker(); // Round-robin or custom logic + worker.send('socket', socket); + }); + + server.listen(853); +} else { + // Worker process handles DNS + const dnsServer = new DnsServer({ + httpsKey: '...', + httpsCert: '...', + httpsPort: 853, + udpPort: 53, + dnssecZone: 'example.com', + manualHttpsMode: true + }); + + process.on('message', (msg, socket) => { + if (msg === 'socket') { + dnsServer.handleHttpsSocket(socket); + } + }); + + await dnsServer.start(); +} +``` + +##### Custom Transport Protocol + +```typescript +// Use DNS server with custom transport (e.g., WebSocket) +import WebSocket from 'ws'; + +const wss = new WebSocket.Server({ port: 8080 }); +const dnsServer = new DnsServer({ + httpsKey: '...', + httpsCert: '...', + httpsPort: 853, + udpPort: 53, + dnssecZone: 'example.com', + manualUdpMode: true, + manualHttpsMode: true +}); + +await dnsServer.start(); + +wss.on('connection', (ws) => { + ws.on('message', (data) => { + // Process DNS query from WebSocket + const response = dnsServer.processRawDnsPacket(Buffer.from(data)); + ws.send(response); + }); +}); +``` + +##### Multi-Interface Binding + +```typescript +// Bind to multiple network interfaces manually +const interfaces = [ + { address: '192.168.1.100', type: 'udp4' }, + { address: '10.0.0.50', type: 'udp4' }, + { address: '::1', type: 'udp6' } +]; + +interfaces.forEach(({ address, type }) => { + const socket = dgram.createSocket(type); + + socket.on('message', (msg, rinfo) => { + console.log(`Query received on ${address}`); + dnsServer.handleUdpMessage(msg, rinfo, (response, rinfo) => { + socket.send(response, rinfo.port, rinfo.address); + }); + }); + + socket.bind(53, address); +}); +``` + ### Handling Different Protocols #### UDP DNS Server @@ -573,6 +782,7 @@ await tap.start(); 5. **Monitoring**: Log DNS queries for debugging and analytics 6. **Rate Limiting**: Implement rate limiting for public DNS servers 7. **Caching**: Respect TTL values and implement proper caching +8. **Manual Sockets**: Use manual socket handling for clustering and load balancing ### Performance Considerations @@ -580,6 +790,7 @@ await tap.start(); - The DNS server handles concurrent UDP and HTTPS requests efficiently - DNSSEC signatures are generated on-demand to reduce memory usage - Pattern matching uses caching for improved performance +- Manual socket handling enables horizontal scaling across CPU cores ### Security Considerations @@ -589,6 +800,8 @@ await tap.start(); - Implement access controls for DNS server handlers - Use Let's Encrypt for automatic SSL certificate management - Never expose internal network information through DNS +- Bind to specific interfaces in production environments +- Use manual socket handling for custom security layers This comprehensive library provides everything needed for both DNS client operations and running production-grade DNS servers with modern security features in TypeScript. diff --git a/ts/00_commitinfo_data.ts b/ts/00_commitinfo_data.ts index 96e0f94..03ea310 100644 --- a/ts/00_commitinfo_data.ts +++ b/ts/00_commitinfo_data.ts @@ -3,6 +3,6 @@ */ export const commitinfo = { name: '@push.rocks/smartdns', - version: '7.3.0', + version: '7.4.0', description: 'A robust TypeScript library providing advanced DNS management and resolution capabilities including support for DNSSEC, custom DNS servers, and integration with various DNS providers.' }