# DNS
~~~
稳定度: 3 - 稳定
~~~
使用 `require('dns')` 引入此模块。dns 模块中的所有方法都使用了 C-Ares,除了 `dns.lookup` 使用了线程池中的 `getaddrinfo(3)`。C-Ares 比 `getaddrinfo` 要快得多,但系统解析器相对于其它程序的操作要更固定。当一个用户使用 `net.connect(80, 'google.com')` 或 `http.get({ host: 'google.com' })` 时会使用 `dns.lookup` 方法。如果用户需要进行大量的快速查询,则最好使用 C-Ares 提供的方法。
下面是一个解析 `'www.google.com'` 并反向解析所返回 IP 地址的例子。
~~~
console.log('反向解析 ' + a + ': ' + JSON.stringify(domains));
});
});
});
~~~
### dns.lookup(domain, [family], callback)
将一个域名(比如 `'google.com'`)解析为第一个找到的 A 记录(IPv4)或 AAAA 记录(IPv6)。地址族 `family` 可以是数字 `4` 或 `6`,缺省为 `null` 表示同时允许 IPv4 和 IPv6 地址族。
回调参数为 `(err, address, family)`。地址 `address` 参数为一个代表 IPv4 或 IPv6 地址的字符串。地址族 `family` 参数为数字 4 或 6,地表 `address` 的地址族(不一定是之前传入 `lookup` 的值)。
当错误发生时,`err` 为一个 `Error` 对象,其中 `err.code` 为错误代码。请记住 `err.code` 被设定为 `'ENOENT'` 的情况不仅是域名不存在,也可能是查询在其它途径出错,比如没有可用文件描述符时。
### dns.resolve(domain, [rrtype], callback)
将一个域名(比如 `'google.com'`)解析为一个 `rrtype` 指定记录类型的数组。有效 `rrtypes` 取值有 `'A'`(IPv4 地址,缺省)、`'AAAA'`(IPv6 地址)、`'MX'`(邮件交换记录)、`'TXT'`(文本记录)、`'SRV'`(SRV 记录)、`'PTR'`(用于 IP 反向查找)、`'NS'`(域名服务器记录)和 `'CNAME'`(别名记录)。
回调参数为 `(err, addresses)`。其中 `addresses` 中每一项的类型取决于记录类型,详见下文对应的查找方法。
当出错时,`err` 参数为一个 `Error` 对象,其中 `err.code` 为下文所列出的错误代码之一。
### dns.resolve4(domain, callback)
于 `dns.resolve()` 一样,但只用于查询 IPv4(`A` 记录)。`addresses` 是一个 IPv4 地址的数组(比如 `['74.125.79.104', '74.125.79.105', '74.125.79.106']`)。
### dns.resolve6(domain, callback)
类似于 `dns.resolve4()`,但用于 IPv6(`AAAA`)查询。
### dns.resolveMx(domain, callback)
类似于 `dns.resolve()`,但用于邮件交换查询(`MX` 记录)。
`addresses` 为一个 MX 记录的数组,每一项包含优先级和交换属性(比如 `[{'priority': 10, 'exchange': 'mx.example.com'},...]`)。
### dns.resolveTxt(domain, callback)
与 `dns.resolve()` 相似,但用于文本查询(`TXT` 记录)。`addresses` 为 `domain` 可用文本记录的数组(比如 `['v=spf1 ip4:0.0.0.0 ~all']`)。
### dns.resolveSrv(domain, callback)
查询 SRV 记录,与 `dns.resolve()` 相似。 `addresses` 是域名 `domain` 可用的 SRV 记录数组, 每一条记录都包含优先级(priority)、权重(weight)、端口号(port)、服务名称(name)等属性 (比如: `[{'priority': 10, {'weight': 5, 'port': 21223, 'name': 'service.example.com'}, ...]`)。
### dns.resolveNs(domain, callback)
查询 NS 记录,与 `dns.resolve()` 相似。 `addresses` 是域名 `domain` 可用的 NS 记录数组, (比如: `['ns1.example.com', 'ns2.example.com']`).
### dns.resolveCname(domain, callback)
查询 CNAME 记录,与 `dns.resolve()` 相似。 `addresses` 是域名 `domain` 可用的 CNAME 记录数组, (比如: `['bar.example.com']`).
### dns.reverse(ip, callback)
反向解析 IP 地址,返回指向该 IP 地址的域名数组。
回调函数接收两个参数: `(err, domains)`.
当出错时,`err` 参数为一个 `Error` 对象,其中 `err.code` 为下文所列出的错误代码之一。
### dns.getServers()
已字符串返回一个当前用于解析的 IP 地址的数组。
### dns.setServers(servers)
指定一个 IP 地址字符串数组,将它们作为解析所用的服务器。
如果您在地址中指定了端口,则端口会被忽略,因为底层库并不支持。
如果您传入无效参数,则会抛出异常。
### 错误代码
每个 DNS 查询都可能返回下列错误代码之一:
- `dns.NODATA`: DNS 服务器返回无数据应答。
- `dns.FORMERR`: DNS 声称查询格式错误。
- `dns.SERVFAIL`: DNS 服务器返回一般失败。
- `dns.NOTFOUND`: 域名未找到。
- `dns.NOTIMP`: DNS 服务器未实现所请求操作。
- `dns.REFUSED`: DNS 服务器拒绝查询。
- `dns.BADQUERY`: DNS 查询格式错误。
- `dns.BADNAME`: 域名格式错误。
- `dns.BADFAMILY`: 不支持的地址类型。
- `dns.BADRESP`: DNS 答复格式错误。
- `dns.CONNREFUSED`: 无法联系 DNS 服务器。
- `dns.TIMEOUT`: 联系 DNS 服务器超时。
- `dns.EOF`: 文件末端。
- `dns.FILE`: 读取文件错误。
- `dns.NOMEM`: 超出内存。
- `dns.DESTRUCTION`: 通道正在被销毁。
- `dns.BADSTR`: 字符串格式错误。
- `dns.BADFLAGS`: 指定了非法标记。
- `dns.NONAME`: 所给主机名非数字。
- `dns.BADHINTS`: 指定了非法提示标记。
- `dns.NOTINITIALIZED`: c-ares 库初始化尚未进行。
- `dns.LOADIPHLPAPI`: 加载 iphlpapi.dll 出错。
- `dns.ADDRGETNETWORKPARAMS`: 无法找到 GetNetworkParams 函数。
- `dns.CANCELLED`: DNS 查询取消。