DoH#

Added in version 1.12.0.

实现了一个由 RFC 8484 定义的 DNS over HTTPS (DoH) 服务器。接受通过 HTTP/HTTPS 承载的 DNS 查询,并通过 UDP 或 TCP 将其代理到一组 DNS 服务器。

DoH 客户端提交 DNS 查询有两种方式:一种是作为 GET 请求,将 DNS 消息以 Base64URL 编码后放在 dns 查询字符串参数中;另一种是作为 POST 请求,将原始 DNS 消息放在请求体中。这两种情况下,DNS 消息的媒体类型都是 application/dns-message

模块接受的带有非零 RCODE 的 DNS 响应会以 200 (OK) 状态返回给客户端。其中 RCODE 保留在 DNS 消息中,并且不会在 doh_next_upstreaminvalid_response 条件下触发重试。

doh_transport 指令控制查询使用 UDP 还是 TCP。为了防止路径外(off-path)响应欺骗,模块会随机化发送给 DNS 服务器的查询 ID,并在响应中恢复客户端的原始 ID。

备注

这种查询 ID 随机化使用非加密的生成器,只能提供有限的保护;请通过妥善保护的可信网络访问 DNS 服务器,正如 resolver 指令所建议的那样。

响应的 Cache-Control 头字段由响应的最小 TTL 派生而来:它被设置为 max-age=<ttl>,或者在无法确定可缓存的 TTL 时设置为 no-store

从源代码构建时,可以使用 --without-http_doh_module 构建选项禁用该模块。在来自 我们的仓库的软件包和镜像中,该模块已包含在构建中。

配置示例#

将 DNS over HTTPS 查询代理到一组 DNS 服务器:

http {
    upstream dns_upstream {
        server 127.0.0.1:53;
    }

    server {
        listen 443 ssl;
        server_name dns.example.com;

        ssl_certificate     dns.example.com.crt;
        ssl_certificate_key dns.example.com.key;

        location /dns-query {
            doh_pass dns_upstream;
        }
    }
}

指令#

doh_bind#

语法

doh_bind address [transparent] | off;

默认值

上下文

http, server, location

使到 DNS 服务器的出站连接从指定的本地 IP 地址(可选端口)发起。参数值可以包含变量。特殊值 off 取消从上一级配置继承的 doh_bind 指令的效果,允许系统自动分配本地 IP 地址和端口。

transparent 参数允许到 DNS 服务器的出站连接从非本地 IP 地址发起,例如,从客户端的真实 IP 地址:

doh_bind $remote_addr transparent;

为了使此参数生效,通常需要以 超级用户 权限运行 Angie 工作进程。在 Linux 上不需要这样做,因为当指定了 transparent 参数时,工作进程会从主进程继承 CAP_NET_RAW 能力。

doh_buffer_size#

语法

doh_buffer_size size;

默认值

doh_buffer_size 16k;

上下文

http, server, location

设置用于读取从 DNS 服务器接收的响应的缓冲区的 size。该 size 不能小于 512 字节。

doh_connect_timeout#

语法

doh_connect_timeout time;

默认值

doh_connect_timeout 60s;

上下文

http, server, location

定义与 DNS 服务器建立连接的超时时间。

doh_max_size#

语法

doh_max_size size;

默认值

一个操作系统内存页的大小

上下文

http, server, location

限制从客户端接受的 DNS 查询消息的大小。配置的 size 必须至少为 12 字节。短于 12 字节(DNS 消息头的大小)或大于 size 的查询将被拒绝。

doh_next_upstream#

语法

doh_next_upstream error | timeout | invalid_response | off ...;

默认值

doh_next_upstream error timeout;

上下文

http, server, location

指定在哪些情况下应将查询传递给 upstream 组中的下一个服务器:

error

在与服务器建立连接、向其传递查询或读取响应时发生了错误;

timeout

在与服务器建立连接、向其传递查询或读取响应时发生了超时;

invalid_response

服务器返回了无效的 DNS 响应;

off

禁用将查询传递给下一个服务器。

将查询传递给下一个服务器可以受到尝试次数时间的限制。

doh_next_upstream_timeout#

语法

doh_next_upstream_timeout time;

默认值

doh_next_upstream_timeout 0;

上下文

http, server, location

限制可以将查询传递给下一个服务器的时间。设置为 0 将禁用此限制。

doh_next_upstream_tries#

语法

doh_next_upstream_tries number;

默认值

doh_next_upstream_tries 0;

上下文

http, server, location

限制将查询传递给下一个服务器的可能尝试次数。设置为 0 将禁用此限制。

doh_pass#

语法

doh_pass address;

默认值

上下文

location, if in location

设置将 DNS 查询代理到的 DNS 服务器的地址。该地址可以指定为域名或带端口的 IP 地址:

doh_pass 127.0.0.1:53;

或指定为服务器组:

doh_pass dns_upstream;

查询通过 UDP 或 TCP 转发给服务器,具体由 doh_transport 指令配置。在一个 location 中只能指定一个 doh_pass 指令。

doh_read_timeout#

语法

doh_read_timeout time;

默认值

doh_read_timeout 60s;

上下文

http, server, location

定义从 DNS 服务器读取响应的超时时间。该超时只在两次连续的读操作之间设置,而不是针对整个响应的传输。如果 DNS 服务器在此时间内没有传输任何内容,则连接将被关闭。

doh_send_timeout#

语法

doh_send_timeout time;

默认值

doh_send_timeout 60s;

上下文

http, server, location

设置向 DNS 服务器传输请求的超时时间。该超时只在两次连续的写操作之间设置,而不是针对整个请求的传输。如果 DNS 服务器在此时间内没有收到任何内容,则连接将被关闭。

doh_socket_keepalive#

语法

doh_socket_keepalive on | off;

默认值

doh_socket_keepalive off;

上下文

http, server, location

为到 DNS 服务器的出站连接启用 SO_KEEPALIVE 套接字选项。当设置为 off 时,操作系统的套接字设置保持有效。

doh_transport#

语法

doh_transport tcp | udp | auto;

默认值

doh_transport auto;

上下文

http, server, location

选择用于将 DNS 查询转发给 DNS 服务器的传输协议:

auto

如果上游的 keepalive 缓存中有空闲的 TCP 连接,则通过它(TCP)发送查询;否则先通过 UDP 发送,如果服务器返回被截断的消息(设置了 TC 标志),则通过 TCP 重试;

udp

查询只通过 UDP 发送;被截断的响应会被视为错误,查询不会通过 TCP 重试;

tcp

查询只通过 TCP 发送。