272 lines
		
	
	
		
			8.0 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
		
		
			
		
	
	
			272 lines
		
	
	
		
			8.0 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
|  | [](http://travis-ci.org/tjfontaine/node-dns) | ||
|  | 
 | ||
|  | native-dns -- A replacement DNS stack for node.js | ||
|  | ================================================= | ||
|  | 
 | ||
|  | Installation | ||
|  | ------------ | ||
|  | 
 | ||
|  | `npm install native-dns` and then `var dns = require('native-dns');` | ||
|  | 
 | ||
|  | Client | ||
|  | ------ | ||
|  | 
 | ||
|  | native-dns exports what should be a 1:1 mapping of the upstream node.js dns | ||
|  | module. That is to say if it's listed in the [docs](http://nodejs.org/docs/latest/api/dns.html) | ||
|  | it should behave similarly. If it doesn't please file an [issue](https://github.com/tjfontaine/node-dns/issues/new) | ||
|  | 
 | ||
|  | Request | ||
|  | ------- | ||
|  | 
 | ||
|  | Beyond matching the upstream module, native-dns also provides a method for | ||
|  | customizing queries. | ||
|  | 
 | ||
|  | ```javascript | ||
|  | var dns = require('../dns'), | ||
|  |   util = require('util'); | ||
|  | 
 | ||
|  | var question = dns.Question({ | ||
|  |   name: 'www.google.com', | ||
|  |   type: 'A', | ||
|  | }); | ||
|  | 
 | ||
|  | var start = Date.now(); | ||
|  | 
 | ||
|  | var req = dns.Request({ | ||
|  |   question: question, | ||
|  |   server: { address: '8.8.8.8', port: 53, type: 'udp' }, | ||
|  |   timeout: 1000, | ||
|  | }); | ||
|  | 
 | ||
|  | req.on('timeout', function () { | ||
|  |   console.log('Timeout in making request'); | ||
|  | }); | ||
|  | 
 | ||
|  | req.on('message', function (err, answer) { | ||
|  |   answer.answer.forEach(function (a) { | ||
|  |     console.log(a.address); | ||
|  |   }); | ||
|  | }); | ||
|  | 
 | ||
|  | req.on('end', function () { | ||
|  |   var delta = (Date.now()) - start; | ||
|  |   console.log('Finished processing request: ' + delta.toString() + 'ms'); | ||
|  | }); | ||
|  | 
 | ||
|  | req.send(); | ||
|  | ``` | ||
|  | 
 | ||
|  | Request creation takes an object with the following fields | ||
|  | 
 | ||
|  |  * `question` -- an instance of Question (required) | ||
|  |  * `server` -- defines the remote end point (required) | ||
|  |   - as an object it should be | ||
|  |     * `address` -- a string ip address (required) | ||
|  |     * `port` -- a number for the remote port (optional, default 53) | ||
|  |     * `type` -- a string indicating `udp` or `tcp` (optional, default `udp`) | ||
|  | You do not need to indicate ipv4 or ipv6, the backend will handle that | ||
|  |   - a string ip address | ||
|  |  * `timeout` -- a number in milliseconds indicating how long to wait for the | ||
|  | request to finish. (optional, default 4000) | ||
|  |  * `try_edns` -- a boolean indicating whether to use an `EDNSPacket` (optional) | ||
|  |  * `cache` -- can be false to disable caching, or implement the cache model, or | ||
|  | an instance of Cache but with a different store (optional, default | ||
|  | platform.cache) | ||
|  | 
 | ||
|  | There are only two methods | ||
|  | 
 | ||
|  |  * `send` -- sends the actual request to the remote endpoint | ||
|  |  * `cancel` -- cancels the request and ignores any responses | ||
|  | 
 | ||
|  | Request emits the following events | ||
|  | 
 | ||
|  |  * `message` -- This is where you get a response, passes `(err, answer)` where | ||
|  | answer is an instance of `Packet` | ||
|  |  * `timeout` -- Fired when the timeout is reached | ||
|  |  * `cancelled` -- Fired if the request is cancelled | ||
|  |  * `end` -- Always fired after a request finished, regardless of disposition | ||
|  | 
 | ||
|  | Platform | ||
|  | -------- | ||
|  | 
 | ||
|  | If you want to customize all `resolve` or `lookup`s with the replacement client | ||
|  | stack you can modify the platform settings accessible in the top level `platform` | ||
|  | object. | ||
|  | 
 | ||
|  | Methods: | ||
|  | 
 | ||
|  |  * `reload` -- Re-read system configuration files to populate name servers and | ||
|  | hosts | ||
|  | 
 | ||
|  | Properties: | ||
|  | 
 | ||
|  |  * `ready` -- Boolean whether requests are safe to transit, true after hosts | ||
|  | and name servers are filled | ||
|  |  * `watching` -- Boolean indicating if system configuration files are watched | ||
|  | for changes, default to false (currently can only be enabled on !win32) | ||
|  |  * `name_servers` -- An array of servers used for resolving queries against | ||
|  |   - Each entry is an object of `{ address: <string ip>, port: 53 }` | ||
|  |   - On win32 this is hard coded to be google dns until there's a sane way to get | ||
|  | the data | ||
|  |  * `search_path` -- An array of domains to try and append after a failed lookup | ||
|  |  * `attempts` -- The number of retries for a failed lookup/timeout (default: 5) | ||
|  |  * `timeout` -- The time each query is allowed to take before trying another | ||
|  | server. (in milliseconds, default: 5000 (5 seconds)) | ||
|  |  * `edns` -- Whether to try and send edns queries first (default: false) | ||
|  |  * `cache` -- The system wide cache used by default for `lookup` and `resolve`, | ||
|  | set this to false to disable caching | ||
|  | 
 | ||
|  | Events: | ||
|  | 
 | ||
|  |  * `ready` -- Emitted after hosts and name servers have been loaded | ||
|  |  * `unready` -- Emitted when hosts and name servers configuration is being | ||
|  | reloaded. | ||
|  | 
 | ||
|  | Server | ||
|  | ------ | ||
|  | 
 | ||
|  | There is also a rudimentary server implementation | ||
|  | 
 | ||
|  | ```javascript | ||
|  | var dns = require('../dns'), | ||
|  |   server = dns.createServer(); | ||
|  | 
 | ||
|  | server.on('request', function (request, response) { | ||
|  |   //console.log(request) | ||
|  |   response.answer.push(dns.A({ | ||
|  |     name: request.question[0].name, | ||
|  |     address: '127.0.0.1', | ||
|  |     ttl: 600, | ||
|  |   })); | ||
|  |   response.answer.push(dns.A({ | ||
|  |     name: request.question[0].name, | ||
|  |     address: '127.0.0.2', | ||
|  |     ttl: 600, | ||
|  |   })); | ||
|  |   response.additional.push(dns.A({ | ||
|  |     name: 'hostA.example.org', | ||
|  |     address: '127.0.0.3', | ||
|  |     ttl: 600, | ||
|  |   })); | ||
|  |   response.send(); | ||
|  | }); | ||
|  | 
 | ||
|  | server.on('error', function (err, buff, req, res) { | ||
|  |   console.log(err.stack); | ||
|  | }); | ||
|  | 
 | ||
|  | server.serve(15353); | ||
|  | ``` | ||
|  | 
 | ||
|  | Server creation | ||
|  | 
 | ||
|  |  * `createServer` and `createUDPServer` -- both create a `UDP` based server, | ||
|  | they accept an optional object for configuration, | ||
|  |   - `{ dgram_type: 'udp4' }` is the default option, the other is `udp6` | ||
|  |  * `createTCPServer` -- creates a TCP based server | ||
|  | 
 | ||
|  | Server methods | ||
|  | 
 | ||
|  |  * `serve(port, [address])` -- specify which port and optional address to listen | ||
|  | on | ||
|  |  * `close()` -- stop the server/close sockets. | ||
|  | 
 | ||
|  | Server events | ||
|  | 
 | ||
|  |  * `listening` -- emitted when underlying socket is listening | ||
|  |  * `close` -- emitted when the underlying socket is closed | ||
|  |  * `request` -- emitted when a dns message is received, and the packet was | ||
|  | successfully unpacked, passes `(request, response)` | ||
|  |   - Both `request` and `response` are instances of `Packet` when you're finished | ||
|  | creating the response, you merely need to call `.send()` and the packet will | ||
|  | DoTheRightThing | ||
|  |  * `error` -- emitted when unable to properly unpack the packet, passed `(err, msg, response)` | ||
|  |  * `socketError` -- remap of the underlying socket for the server, passes `(err, socket)` | ||
|  | 
 | ||
|  | Packet | ||
|  | ------ | ||
|  | 
 | ||
|  | Properties: | ||
|  | 
 | ||
|  |  * `header` | ||
|  |   - `id` -- request id | ||
|  |   - `qdcount` -- the number of questions (inferred from array size) | ||
|  |   - `ancount` -- the number of questions (inferred from array size) | ||
|  |   - `nscount` -- the number of questions (inferred from array size) | ||
|  |   - `arcount` -- the number of questions (inferred from array size) | ||
|  |   - `qr` -- is a query response | ||
|  |   - `opcode` | ||
|  |   - `aa` -- Authoritative Answer | ||
|  |   - `tc` -- Truncation bit | ||
|  |   - `rd` -- Recursion Desired | ||
|  |   - `ra` -- Recursion Available | ||
|  |   - `res1` -- Reserved field | ||
|  |   - `res2` -- Reserved field | ||
|  |   - `res3` -- Reserved field | ||
|  |   - `rcode` -- Response Code (see `consts.NAME_TO_RCODE`) | ||
|  |  * `question` -- array of `Question`s | ||
|  |  * `answer` -- array of `ResourceRecord`s | ||
|  |  * `authority` -- array of `ResourceRecord`s | ||
|  |  * `additional` -- array of `ResourceRecord`s | ||
|  | 
 | ||
|  | Methods: | ||
|  | 
 | ||
|  |  * `send()` -- Handles sending the packet to the right end point | ||
|  | 
 | ||
|  | Question | ||
|  | -------- | ||
|  | 
 | ||
|  | A `Question` is instantiated by passing an object like: | ||
|  | 
 | ||
|  |  * `name` -- i.e. 'www.google.com' (required) | ||
|  |  * `type` -- Either the string representation of the record type, or the integer | ||
|  | value, see `consts.NAME_TO_QTYPE` (default: 'A') | ||
|  |  * `class` -- The class of service, default to 1 meaning internet | ||
|  | 
 | ||
|  | ResourceRecord | ||
|  | -------------- | ||
|  | 
 | ||
|  | ResourceRecords are what populate `answer`, `authority`, and `additional`. | ||
|  | This is a generic type, and each derived type inherits the following properties: | ||
|  | 
 | ||
|  |  * `name` -- The name of the resource | ||
|  |  * `type` -- The numerical representation of the resource record type | ||
|  |  * `class` -- The numerical representation of the class of service (usually 1 for internet) | ||
|  |  * `ttl` -- The Time To Live for the record, in seconds | ||
|  | 
 | ||
|  | Available Types: | ||
|  | 
 | ||
|  |  * `SOA` | ||
|  |   - `primary` -- string | ||
|  |   - `admin` -- string | ||
|  |   - `serial` -- number | ||
|  |   - `refresh` -- number | ||
|  |   - `retry` -- number | ||
|  |   - `expiration` -- number | ||
|  |   - `minimum` -- number | ||
|  |  * `A` and `AAAA` | ||
|  |   - `address` -- string | ||
|  |  * `MX` | ||
|  |   - `priority` -- number | ||
|  |   - `exchange` -- string | ||
|  |  * `TXT` | ||
|  |   - `data` -- string | ||
|  |  * `SRV` | ||
|  |   - `priority` -- number | ||
|  |   - `weight` -- number | ||
|  |   - `port` -- number | ||
|  |   - `target` -- string | ||
|  |  * `NS` | ||
|  |   - `data` -- string | ||
|  |  * `CNAME` | ||
|  |   - `data` -- string | ||
|  |  * `PTR` | ||
|  |   - `data` -- string | ||
|  |  * `NAPTR` | ||
|  |   - `order` -- number | ||
|  |   - `preference` -- number | ||
|  |   - `flags` -- string | ||
|  |   - `service` -- string | ||
|  |   - `regexp` -- string | ||
|  |   - `replacement` -- string |