Node.js v18.16.0 文档


目录

DNS#

稳定性: 2 - 稳定

源代码: lib/dns.js

node:dns 模块启用了名称解析。 例如,使用它来查找主机名的 IP 地址。

虽然以 域名系统 (DNS) 命名,但它并不总是使用 DNS 协议进行查找。 dns.lookup() 使用操作系统工具来执行名称解析。 它可能不需要执行任何网络通信。 要像同一系统上的其他应用程序那样执行名称解析,则使用 dns.lookup()

const dns = require('node:dns');

dns.lookup('example.org', (err, address, family) => {
  console.log('address: %j family: IPv%s', address, family);
});
// address: "93.184.216.34" family: IPv4 

node:dns 模块中的所有其他函数都连接到实际的域名系统服务器以执行名称解析。 它们将始终使用网络来执行域名系统查询。 这些函数不使用 dns.lookup() 使用的同一组配置文件(例如 /etc/hosts)。 使用这些函数始终执行域名系统查询,绕过其他名称解析工具。

const dns = require('node:dns');

dns.resolve4('archive.org', (err, addresses) => {
  if (err) throw err;

  console.log(`addresses: ${JSON.stringify(addresses)}`);

  addresses.forEach((a) => {
    dns.reverse(a, (err, hostnames) => {
      if (err) {
        throw err;
      }
      console.log(`reverse for ${a}: ${JSON.stringify(hostnames)}`);
    });
  });
}); 

有关详细信息,请参阅 实现的注意事项章节

类:dns.Resolver#

域名系统请求的独立解析器。

创建新的解析器使用默认的服务器设置。 使用 resolver.setServers() 设置用于解析器的服务器不会影响其他解析器:

const { Resolver } = require('node:dns');
const resolver = new Resolver();
resolver.setServers(['4.4.4.4']);

// This request will use the server at 4.4.4.4, independent of global settings.
resolver.resolve4('example.org', (err, addresses) => {
  // ...
}); 

可以使用 node:dns 模块中的以下方法:

Resolver([options])#

创建新的解析器。

  • options <Object>
    • timeout <integer> 查询超时(以毫秒为单位),或 -1 使用默认超时。
    • tries <integer> 解析器在放弃之前尝试联系每个名称服务器的尝试次数。 默认值: 4

resolver.cancel()#

取消此解析器进行的所有未完成的域名系统查询。 相应的回调将被调用,错误码为 ECANCELLED

resolver.setLocalAddress([ipv4][, ipv6])#

  • ipv4 <string> IPv4 地址的字符串表示形式。 默认值: '0.0.0.0'
  • ipv6 <string> IPv6 地址的字符串表示形式。 默认值: '::0'

解析器实例将从指定的 IP 地址发送其请求。 这允许程序在多宿主系统上使用时指定出站接口。

如果没有指定 v4 或 v6 地址,则设置为默认值,操作系统会自动选择本地地址。

解析器在向 IPv4域名系统服务器触发请求时将使用 v4 本地地址,在向 IPv6域名系统服务器触发请求时将使用 v6 本地地址。 解析请求的 rrtype 对使用的本地地址没有影响。

dns.getServers()#

返回 IP 地址字符串数组,格式根据 RFC 5952,当前配置为 DNS 解析。 如果使用自定义端口,则字符串将包含端口部分。

[
  '4.4.4.4',
  '2001:4860:4860::8888',
  '4.4.4.4:1053',
  '[2001:4860:4860::8888]:1053',
] 

dns.lookup(hostname[, options], callback)#

  • hostname <string>
  • options <integer> | <Object>
    • family <integer> | <string> 记录族。 必须是 460。 出于向后兼容的原因,'IPv4''IPv6' 分别被解释为 46。 值 0 表示同时返回 IPv4 和 IPv6 地址。 默认值: 0
    • hints <number> 一个或多个 支持的 getaddrinfo 标志。 多个标志可以通过按位 OR 其值来传入。
    • all <boolean> 当为 true 时,回调返回数组中所有已解析的地址。 否则,返回单个地址。 默认值: false
    • verbatim <boolean> 当为 true 时,回调按照 DNS 解析器返回的顺序接收 IPv4 和 IPv6 地址。 当为 false 时,IPv4 地址位于 IPv6 地址之前。 默认值: true(地址未重新排序)。 默认值可使用 dns.setDefaultResultOrder()--dns-result-order 进行配置。
  • callback <Function>
    • err <Error>
    • address <string> IPv4 或 IPv6 地址的字符串表示形式。
    • family <integer> 46,表示 address 族,如果地址不是 IPv4 或 IPv6 地址,则表示为 00 可能是操作系统使用的名称解析服务中存在错误的指示符。

将主机名(例如 'nodejs.org')解析为第一个找到的 A (IPv4) 或 AAAA (IPv6) 记录。 所有 option 属性都是可选的。 如果 options 是整数,则它必须是 46 – 如果 options0 或未提供,则如果找到则返回 IPv4 和 IPv6 地址。

all 选项设置为 truecallback 的参数更改为 (err, addresses)addresses 是具有属性 addressfamily 的对象数组。

出错时,errError 对象,其中 err.code 是错误码。 记住,err.code 将设置为 'ENOTFOUND',不仅当主机名不存在时,而且当查找以其他方式失败时,例如没有可用的文件描述符。

dns.lookup() 不一定与域名系统协议有任何关系。 该实现使用一种操作系统工具,可以将名称与地址关联起来,反之亦然。 这种实现会对任何 Node.js 程序的行为产生微妙但重要的影响。 在使用 dns.lookup() 之前,请花一些时间查阅 实现的注意事项章节

用法示例:

const dns = require('node:dns');
const options = {
  family: 6,
  hints: dns.ADDRCONFIG | dns.V4MAPPED,
};
dns.lookup('example.com', options, (err, address, family) =>
  console.log('address: %j family: IPv%s', address, family));
// address: "2606:2800:220:1:248:1893:25c8:1946" family: IPv6

// When options.all is true, the result will be an Array.
options.all = true;
dns.lookup('example.com', options, (err, addresses) =>
  console.log('addresses: %j', addresses));
// addresses: [{"address":"2606:2800:220:1:248:1893:25c8:1946","family":6}] 

如果此方法作为其 util.promisify() 版本被调用,并且 all 未设置为 true,则它为具有 addressfamily 属性的 Object 返回 Promise

支持的 getaddrinfo 标志#

以下标志可以作为提示传给 dns.lookup()

  • dns.ADDRCONFIG: 将返回的地址类型限制为系统上配置的非环回地址类型。 例如,仅当当前系统至少配置了一个 IPv4 地址时,才会返回 IPv4 地址。
  • dns.V4MAPPED: 如果指定了 IPv6 族,但未找到 IPv6 地址,则返回 IPv4 映射的 IPv6 地址。 某些操作系统(例如 FreeBSD 10.1)不支持它。
  • dns.ALL: 如果指定了 dns.V4MAPPED,则返回解析的 IPv6 地址以及 IPv4 映射的 IPv6 地址。

dns.lookupService(address, port, callback)#

使用操作系统的底层 getnameinfo 实现将给定的 addressport 解析为主机名和服务。

如果 address 不是有效的 IP 地址,则会抛出 TypeErrorport 将被强制为数字。 如果不是合法的端口,则会抛出 TypeError

出错时,errError 对象,其中 err.code 是错误码。

const dns = require('node:dns');
dns.lookupService('127.0.0.1', 22, (err, hostname, service) => {
  console.log(hostname, service);
  // Prints: localhost ssh
}); 

如果此方法作为其 util.promisify() 版本被调用,则其将为具有 hostnameservice 属性的 Object 返回 Promise

dns.resolve(hostname[, rrtype], callback)#

使用域名系统协议将主机名(例如 'nodejs.org')解析为资源记录数组。 callback 函数有参数 (err, records)。 当成功时,records 将是资源记录数组。 个别结果的类型和结构因 rrtype 而异:

rrtyperecords包含结果类型速记法
'A'IPv4 地址(默认)<string>dns.resolve4()
'AAAA'IPv6 地址<string>dns.resolve6()
'ANY'任何记录<Object>dns.resolveAny()
'CAA'CA授权记录<Object>dns.resolveCaa()
'CNAME'规范名称记录<string>dns.resolveCname()
'MX'邮件往来记录<Object>dns.resolveMx()
'NAPTR'名称权限指针记录<Object>dns.resolveNaptr()
'NS'名称服务器记录<string>dns.resolveNs()
'PTR'指针记录<string>dns.resolvePtr()
'SOA'权限记录的开始<Object>dns.resolveSoa()
'SRV'服务记录<Object>dns.resolveSrv()
'TXT'文本记录<string[]>dns.resolveTxt()

出错时,err 是一个 Error 对象,其中 err.codeDNS 错误代码 之一。

dns.resolve4(hostname[, options], callback)#

使用域名系统协议为 hostname 解析 IPv4 地址(A 记录)。 传给 callback 函数的 addresses 参数将包含 IPv4 地址的数组(例如 ['74.125.79.104', '74.125.79.105', '74.125.79.106'])。

dns.resolve6(hostname[, options], callback)#

  • hostname <string> 要解析的主机名。
  • options <Object>
    • ttl <boolean> 检索每条记录的生存时间值 (TTL)。 当为 true 时,回调接收 { address: '0:1:2:3:4:5:6:7', ttl: 60 } 对象数组而不是字符串数组,TTL 以秒表示。
  • callback <Function>

使用域名系统协议为 hostname 解析 IPv6 地址(AAAA 记录)。 传给 callback 函数的 addresses 参数将包含 IPv6 地址数组。

dns.resolveAny(hostname, callback)#

使用域名系统协议解析所有记录(也称为 ANY* 查询)。 传给 callback 函数的 ret 参数将是包含各种类型记录的数组。 每个对象都有表示当前记录的类型的属性 type。 并且根据 type,对象上将出现其他属性:

类型属性
'A'address/ttl
'AAAA'address/ttl
'CNAME'value
'MX'参考dns.resolveMx()
'NAPTR'参考dns.resolveNaptr()
'NS'value
'PTR'value
'SOA'参考dns.resolveSoa()
'SRV'参考dns.resolveSrv()
'TXT'这种类型的记录包含一个名为 entries 的数组属性,它引用 dns.resolveTxt(),例如 { entries: ['...'], type: 'TXT' }

这是传给回调的 ret 对象的示例:

[ { type: 'A', address: '127.0.0.1', ttl: 299 },
  { type: 'CNAME', value: 'example.com' },
  { type: 'MX', exchange: 'alt4.aspmx.l.example.com', priority: 50 },
  { type: 'NS', value: 'ns1.example.com' },
  { type: 'TXT', entries: [ 'v=spf1 include:_spf.example.com ~all' ] },
  { type: 'SOA',
    nsname: 'ns1.example.com',
    hostmaster: 'admin.example.com',
    serial: 156696742,
    refresh: 900,
    retry: 900,
    expire: 1800,
    minttl: 60 } ] 

域名系统服务器运营商可以选择不响应 ANY 查询。 调用单个方法(如 dns.resolve4()dns.resolveMx() 等)可能会更好。 更多详细信息,请参见 RFC 8482

dns.resolveCname(hostname, callback)#

使用域名系统协议为 hostname 解析 CNAME 记录。 传给 callback 函数的 addresses 参数将包含可用于 hostname(例如 ['bar.example.com'])的规范名称记录的数组。

dns.resolveCaa(hostname, callback)#

使用域名系统协议为 hostname 解析 CAA 记录。 传给 callback 函数的 addresses 参数将包含可用于 hostname(例如 [{critical: 0, iodef: 'mailto:pki@example.com'}, {critical: 128, issue: 'pki.example.com'}])的证书颁发机构授权记录的数组。

dns.resolveMx(hostname, callback)#

使用域名系统协议解析 hostname 的邮件交换记录(MX 记录)。 传给 callback 函数的 addresses 参数将包含其中包含 priorityexchange 属性(例如 [{priority: 10, exchange: 'mx.example.com'}, ...])的对象数组。

dns.resolveNaptr(hostname, callback)#

使用域名系统协议为 hostname 解析基于正则表达式的记录(NAPTR 记录)。 传给 callback 函数的 addresses 参数将包含具有以下属性的对象数组:

  • flags
  • service
  • regexp
  • replacement
  • order
  • preference
{
  flags: 's',
  service: 'SIP+D2U',
  regexp: '',
  replacement: '_sip._udp.example.com',
  order: 30,
  preference: 100
} 

dns.resolveNs(hostname, callback)#

使用域名系统协议为 hostname 解析名称服务器记录(NS 记录)。 传给 callback 函数的 addresses 参数将包含可用于 hostname(例如 ['ns1.example.com', 'ns2.example.com'])的名称服务器记录数组。

dns.resolvePtr(hostname, callback)#

使用域名系统协议解析 hostname 的指针记录(PTR 记录)。 传给 callback 函数的 addresses 参数将是包含响应记录的字符串数组。

dns.resolveSoa(hostname, callback)#

使用域名系统协议来解析 hostname 的起始规范记录(SOA 记录)。 传给 callback 函数的 address 参数将是具有以下属性的对象:

  • nsname
  • hostmaster
  • serial
  • refresh
  • retry
  • expire
  • minttl
{
  nsname: 'ns.example.com',
  hostmaster: 'root.example.com',
  serial: 2013101809,
  refresh: 10000,
  retry: 2400,
  expire: 604800,
  minttl: 3600
} 

dns.resolveSrv(hostname, callback)#

使用域名系统协议解析 hostname 的服务记录(SRV 记录)。 传给 callback 函数的 addresses 参数将是具有以下属性的对象数组:

  • priority
  • weight
  • port
  • name
{
  priority: 10,
  weight: 5,
  port: 21223,
  name: 'service.example.com'
} 

dns.resolveTxt(hostname, callback)#

使用域名系统协议为 hostname 解析文本查询(TXT 记录)。 传给 callback 函数的 records 参数是可用于 hostname(例如 [ ['v=spf1 ip4:0.0.0.0 ', '~all' ] ])的文本记录的二维数组。 每个子数组包含一条记录的 TXT 块。 根据用例,这些可以连接在一起或单独处理。

dns.reverse(ip, callback)#

执行反向域名系统查询,将 IPv4 或 IPv6 地址解析为主机名数组。

出错时,err 是一个 Error 对象,其中 err.codeDNS 错误代码 之一。

dns.setDefaultResultOrder(order)#

  • order <string> 必须是 'ipv4first''verbatim'

dns.lookup()dnsPromises.lookup() 中设置 verbatim 的默认值。 该值可能是:

  • ipv4first: 设置默认的 verbatimfalse
  • verbatim: 设置默认的 verbatimtrue

默认为 verbatim,并且 dns.setDefaultResultOrder() 的优先级高于 --dns-result-order。 当使用 工作线程 时,主线程中的 dns.setDefaultResultOrder() 不会影响 worker 中的默认 dns 命令。

dns.setServers(servers)#

设置执行 DNS 解析时要使用的服务器的 IP 地址和端口。 servers 参数是 RFC 5952 格式地址的数组。 如果端口是 IANA 默认 DNS 端口 (53),则可以省略。

dns.setServers([
  '4.4.4.4',
  '[2001:4860:4860::8888]',
  '4.4.4.4:1053',
  '[2001:4860:4860::8888]:1053',
]); 

如果提供的地址无效,则会抛出错误。

在进行域名系统查询时不得调用 dns.setServers() 方法。

dns.setServers() 方法仅影响 dns.resolve()dns.resolve*()dns.reverse()(特别是不影响 dns.lookup())。

此方法的工作原理与 resolve.conf 非常相似。 也就是说,如果尝试使用提供的第一个服务器进行解析导致 NOTFOUND 错误,则 resolve() 方法将不会尝试使用提供的后续服务器进行解析。 仅当较早的域名系统服务器超时或导致其他错误时,才会使用后备域名系统服务器。

DNS promise API#

dns.promises API 提供了一组替代的异步 DNS 方法,这些方法返回 Promise 对象而不是使用回调。 API 可通过 require('node:dns').promisesrequire('node:dns/promises') 访问。

类:dnsPromises.Resolver#

域名系统请求的独立解析器。

创建新的解析器使用默认的服务器设置。 使用 resolver.setServers() 设置用于解析器的服务器不会影响其他解析器:

const { Resolver } = require('node:dns').promises;
const resolver = new Resolver();
resolver.setServers(['4.4.4.4']);

// This request will use the server at 4.4.4.4, independent of global settings.
resolver.resolve4('example.org').then((addresses) => {
  // ...
});

// Alternatively, the same code can be written using async-await style.
(async function() {
  const addresses = await resolver.resolve4('example.org');
})(); 

来自 dnsPromises API 的以下方法可用:

resolver.cancel()#

取消此解析器进行的所有未完成的域名系统查询。 相应的 promise 将使用错误码 ECANCELLED 拒绝。

dnsPromises.getServers()#

返回 IP 地址字符串数组,格式根据 RFC 5952,当前配置为 DNS 解析。 如果使用自定义端口,则字符串将包含端口部分。

[
  '4.4.4.4',
  '2001:4860:4860::8888',
  '4.4.4.4:1053',
  '[2001:4860:4860::8888]:1053',
] 

dnsPromises.lookup(hostname[, options])#

  • hostname <string>
  • options <integer> | <Object>
    • family <integer> 记录族。 必须是 460。 值 0 表示同时返回 IPv4 和 IPv6 地址。 默认值: 0
    • hints <number> 一个或多个 支持的 getaddrinfo 标志。 多个标志可以通过按位 OR 其值来传入。
    • all <boolean> 当为 true 时,Promise 使用数组中的所有地址进行解决。 否则,返回单个地址。 默认值: false
    • verbatim <boolean> 当为 true 时,Promise 使用按照 DNS 解析器返回的顺序使用 IPv4 和 IPv6 地址进行解决。 当为 false 时,IPv4 地址位于 IPv6 地址之前。 Default: 当前为 false(地址已重新排序),但预计在不久的将来会发生变化。 默认值可使用 dns.setDefaultResultOrder()--dns-result-order 进行配置。 新代码应使用 { verbatim: true }

将主机名(例如 'nodejs.org')解析为第一个找到的 A (IPv4) 或 AAAA (IPv6) 记录。 所有 option 属性都是可选的。 如果 options 是整数,则它必须是 46 – 如果未提供 options,则在找到时返回 IPv4 和 IPv6 地址。

all 选项设置为 true,则 Promise 使用 addresses 是具有属性 addressfamily 的对象数组进行解决。

当出错时,Promise 使用 Error 对象拒绝,其中 err.code 是错误码。 记住,err.code 将设置为 'ENOTFOUND',不仅当主机名不存在时,而且当查找以其他方式失败时,例如没有可用的文件描述符。

dnsPromises.lookup() 不一定与域名系统协议有任何关系。 该实现使用一种操作系统工具,可以将名称与地址关联起来,反之亦然。 这种实现会对任何 Node.js 程序的行为产生微妙但重要的影响。 在使用 dnsPromises.lookup() 之前,请花一些时间查阅 实现的注意事项章节

用法示例:

const dns = require('node:dns');
const dnsPromises = dns.promises;
const options = {
  family: 6,
  hints: dns.ADDRCONFIG | dns.V4MAPPED,
};

dnsPromises.lookup('example.com', options).then((result) => {
  console.log('address: %j family: IPv%s', result.address, result.family);
  // address: "2606:2800:220:1:248:1893:25c8:1946" family: IPv6
});

// When options.all is true, the result will be an Array.
options.all = true;
dnsPromises.lookup('example.com', options).then((result) => {
  console.log('addresses: %j', result);
  // addresses: [{"address":"2606:2800:220:1:248:1893:25c8:1946","family":6}]
}); 

dnsPromises.lookupService(address, port)#

使用操作系统的底层 getnameinfo 实现将给定的 addressport 解析为主机名和服务。

如果 address 不是有效的 IP 地址,则会抛出 TypeErrorport 将被强制为数字。 如果不是合法的端口,则会抛出 TypeError

当出错时,Promise 使用 Error 对象拒绝,其中 err.code 是错误码。

const dnsPromises = require('node:dns').promises;
dnsPromises.lookupService('127.0.0.1', 22).then((result) => {
  console.log(result.hostname, result.service);
  // Prints: localhost ssh
}); 

dnsPromises.resolve(hostname[, rrtype])#

  • hostname <string> 要解析的主机名。
  • rrtype <string> 资源记录类型。 默认值: 'A'

使用域名系统协议将主机名(例如 'nodejs.org')解析为资源记录数组。 当成功时,Promise 使用资源记录数组解决。 个别结果的类型和结构因 rrtype 而异:

rrtyperecords包含结果类型速记法
'A'IPv4 地址(默认)<string>dnsPromises.resolve4()
'AAAA'IPv6 地址<string>dnsPromises.resolve6()
'ANY'任何记录<Object>dnsPromises.resolveAny()
'CAA'CA授权记录<Object>dnsPromises.resolveCaa()
'CNAME'规范名称记录<string>dnsPromises.resolveCname()
'MX'邮件往来记录<Object>dnsPromises.resolveMx()
'NAPTR'名称权限指针记录<Object>dnsPromises.resolveNaptr()
'NS'名称服务器记录<string>dnsPromises.resolveNs()
'PTR'指针记录<string>dnsPromises.resolvePtr()
'SOA'权限记录的开始<Object>dnsPromises.resolveSoa()
'SRV'服务记录<Object>dnsPromises.resolveSrv()
'TXT'文本记录<string[]>dnsPromises.resolveTxt()

出错时,PromiseError 对象拒绝,其中 err.codeDNS 错误代码 之一。

dnsPromises.resolve4(hostname[, options])#

  • hostname <string> 要解析的主机名。
  • options <Object>
    • ttl <boolean> 检索每条记录的生存时间值 (TTL)。 当为 true 时,Promise 使用 { address: '1.2.3.4', ttl: 60 } 对象数组而不是字符串数组进行解决,TTL 以秒表示。

使用域名系统协议为 hostname 解析 IPv4 地址(A 记录)。 当成功时,Promise 使用 IPv4 地址数值(例如 ['74.125.79.104', '74.125.79.105', '74.125.79.106'])解决。

dnsPromises.resolve6(hostname[, options])#

  • hostname <string> 要解析的主机名。
  • options <Object>
    • ttl <boolean> 检索每条记录的生存时间值 (TTL)。 当为 true 时,Promise 使用 { address: '0:1:2:3:4:5:6:7', ttl: 60 } 对象数组而不是字符串数组进行解决,TTL 以秒表示。

使用域名系统协议为 hostname 解析 IPv6 地址(AAAA 记录)。 当成功时,Promise 使用 IPv6 地址数组解决。

dnsPromises.resolveAny(hostname)#

使用域名系统协议解析所有记录(也称为 ANY* 查询)。 当成功时,Promise 使用包含各种类型记录的数组进行解决。 每个对象都有表示当前记录的类型的属性 type。 并且根据 type,对象上将出现其他属性:

类型属性
'A'address/ttl
'AAAA'address/ttl
'CNAME'value
'MX'参考dnsPromises.resolveMx()
'NAPTR'参考dnsPromises.resolveNaptr()
'NS'value
'PTR'value
'SOA'参考dnsPromises.resolveSoa()
'SRV'参考dnsPromises.resolveSrv()
'TXT'这种类型的记录包含一个名为 entries 的数组属性,它引用 dnsPromises.resolveTxt(),例如 { entries: ['...'], type: 'TXT' }

以下是结果对象的示例:

[ { type: 'A', address: '127.0.0.1', ttl: 299 },
  { type: 'CNAME', value: 'example.com' },
  { type: 'MX', exchange: 'alt4.aspmx.l.example.com', priority: 50 },
  { type: 'NS', value: 'ns1.example.com' },
  { type: 'TXT', entries: [ 'v=spf1 include:_spf.example.com ~all' ] },
  { type: 'SOA',
    nsname: 'ns1.example.com',
    hostmaster: 'admin.example.com',
    serial: 156696742,
    refresh: 900,
    retry: 900,
    expire: 1800,
    minttl: 60 } ] 

dnsPromises.resolveCaa(hostname)#

使用域名系统协议为 hostname 解析 CAA 记录。 当成功时,Promise 使用包含可用于 hostname(例如 [{critical: 0, iodef: 'mailto:pki@example.com'},{critical: 128, issue: 'pki.example.com'}])的可用证书颁发机构授权记录的对象数组进行解决。

dnsPromises.resolveCname(hostname)#

使用域名系统协议为 hostname 解析 CNAME 记录。 当成功时,Promise 使用 hostname 可用的规范名称记录数组(例如 ['bar.example.com'])进行解决。

dnsPromises.resolveMx(hostname)#

使用域名系统协议解析 hostname 的邮件交换记录(MX 记录)。 当成功时,Promise 使用包含 priorityexchange 属性(例如 [{priority: 10, exchange: 'mx.example.com'}, ...])的对象数组进行解决。

dnsPromises.resolveNaptr(hostname)#

使用域名系统协议为 hostname 解析基于正则表达式的记录(NAPTR 记录)。 当成功时,Promise 使用具有以下属性的对象数组进行解决:

  • flags
  • service
  • regexp
  • replacement
  • order
  • preference
{
  flags: 's',
  service: 'SIP+D2U',
  regexp: '',
  replacement: '_sip._udp.example.com',
  order: 30,
  preference: 100
} 

dnsPromises.resolveNs(hostname)#

使用域名系统协议为 hostname 解析名称服务器记录(NS 记录)。 当成功时,Promise 使用可用于 hostname 的名称服务器记录数组(例如 ['ns1.example.com', 'ns2.example.com'])进行解决。

dnsPromises.resolvePtr(hostname)#

使用域名系统协议解析 hostname 的指针记录(PTR 记录)。 当成功时,Promise 使用包含响应记录的字符串数组进行解决。

dnsPromises.resolveSoa(hostname)#

使用域名系统协议来解析 hostname 的起始规范记录(SOA 记录)。 当成功时,Promise 使用具有以下属性的对象进行解决:

  • nsname
  • hostmaster
  • serial
  • refresh
  • retry
  • expire
  • minttl
{
  nsname: 'ns.example.com',
  hostmaster: 'root.example.com',
  serial: 2013101809,
  refresh: 10000,
  retry: 2400,
  expire: 604800,
  minttl: 3600
} 

dnsPromises.resolveSrv(hostname)#

使用域名系统协议解析 hostname 的服务记录(SRV 记录)。 当成功时,Promise 使用具有以下属性的对象数组进行解决:

  • priority
  • weight
  • port
  • name
{
  priority: 10,
  weight: 5,
  port: 21223,
  name: 'service.example.com'
} 

dnsPromises.resolveTxt(hostname)#

使用域名系统协议为 hostname 解析文本查询(TXT 记录)。 当成功时,Promise 使用可用于 hostname(例如 [ ['v=spf1 ip4:0.0.0.0 ', '~all' ] ])的文本记录的二维数组进行解决。 每个子数组包含一条记录的 TXT 块。 根据用例,这些可以连接在一起或单独处理。

dnsPromises.reverse(ip)#

执行反向域名系统查询,将 IPv4 或 IPv6 地址解析为主机名数组。

出错时,PromiseError 对象拒绝,其中 err.codeDNS 错误代码 之一。

dnsPromises.setDefaultResultOrder(order)#

  • order <string> 必须是 'ipv4first''verbatim'

dns.lookup()dnsPromises.lookup() 中设置 verbatim 的默认值。 该值可能是:

  • ipv4first: 设置默认的 verbatimfalse
  • verbatim: 设置默认的 verbatimtrue

默认为 verbatim,并且 dnsPromises.setDefaultResultOrder() 的优先级高于 --dns-result-order。 当使用 工作线程 时,主线程中的 dnsPromises.setDefaultResultOrder() 不会影响 worker 中的默认 dns 命令。

dnsPromises.setServers(servers)#

设置执行 DNS 解析时要使用的服务器的 IP 地址和端口。 servers 参数是 RFC 5952 格式地址的数组。 如果端口是 IANA 默认 DNS 端口 (53),则可以省略。

dnsPromises.setServers([
  '4.4.4.4',
  '[2001:4860:4860::8888]',
  '4.4.4.4:1053',
  '[2001:4860:4860::8888]:1053',
]); 

如果提供的地址无效,则会抛出错误。

在进行域名系统查询时不得调用 dnsPromises.setServers() 方法。

此方法的工作原理与 resolve.conf 非常相似。 也就是说,如果尝试使用提供的第一个服务器进行解析导致 NOTFOUND 错误,则 resolve() 方法将不会尝试使用提供的后续服务器进行解析。 仅当较早的域名系统服务器超时或导致其他错误时,才会使用后备域名系统服务器。

错误代码#

每个域名系统查询都可以返回以下错误代码之一:

  • dns.NODATA: 域名系统服务器返回没有数据的答案。
  • dns.FORMERR: 域名系统服务器声称查询格式错误。
  • dns.SERVFAIL: 域名系统服务器返回一般故障。
  • dns.NOTFOUND: 未找到域名。
  • dns.NOTIMP: 域名系统服务器没有执行请求的操作。
  • dns.REFUSED: 域名系统服务器拒绝查询。
  • dns.BADQUERY: 域名系统查询格式错误。
  • dns.BADNAME: 主机名格式错误。
  • dns.BADFAMILY: 不支持的地址族。
  • dns.BADRESP: DNS 响应格式错误。
  • dns.CONNREFUSED: 无法联系域名系统服务器。
  • dns.TIMEOUT: 联系域名系统服务器时超时。
  • 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: 域名系统查询已取消。

dnsPromises API 也导出上述错误代码,例如,dnsPromises.NODATA

实现的注意事项#

尽管 dns.lookup() 和各种 dns.resolve*()/dns.reverse() 函数具有将网络名称与网络地址相关联的相同目标(反之亦然),但它们的行为却大不相同。 这些差异可能会对 Node.js 程序的行为产生微妙但重要的影响。

dns.lookup()#

在幕后,dns.lookup() 使用与大多数其他程序相同的操作系统设施。 例如,dns.lookup() 几乎总是以与 ping 命令相同的方式解析给定名称。 在大多数类似 POSIX 的操作系统上,可以通过更改 nsswitch.conf(5) 和/或 resolv.conf(5) 中的设置来修改 dns.lookup() 函数的行为,但更改这些文件将更改在同一操作系统上运行的所有其他程序的行为。

尽管对 dns.lookup() 的调用从 JavaScript 的角度来看是异步的,但它被实现为对运行在 libuv 线程池上的 getaddrinfo(3) 的同步调用。 这可能会对某些应用程序产生令人惊讶的负面性能影响,有关更多信息,请参阅 UV_THREADPOOL_SIZE 文档。

各种网络 API 将在内部调用 dns.lookup() 来解析主机名。 如果这是一个问题,则考虑使用 dns.resolve() 并使用地址而不是主机名将主机名解析为地址。 此外,某些网络 API(例如 socket.connect()dgram.createSocket())允许替换默认解析器 dns.lookup()

dns.resolve()dns.resolve*()dns.reverse()#

这些函数的实现与 dns.lookup() 完全不同。 他们不使用 getaddrinfo(3),他们总是在网络上执行 DNS 查询。 此网络通信始终异步完成,不使用 libuv 的线程池。

因此,这些函数不会对发生在 libuv 线程池上的其他处理产生与 dns.lookup() 相同的负面影响。

它们不使用 dns.lookup() 使用的同一组配置文件。 例如,他们不使用来自 /etc/hosts 的配置。