mirror of
https://github.com/XTLS/Xray-docs-next.git
synced 2026-09-29 02:18:06 +03:00
Refine domainStrategy
This commit is contained in:
+14
-5
@@ -4,20 +4,29 @@
|
||||
|
||||
The built-in DNS module in Xray has three main purposes:
|
||||
|
||||
- **Routing Phase:** Resolves domain names to IPs and matches rules based on the resolved IPs for traffic splitting.<br>
|
||||
Whether a domain is resolved for routing depends on `routing.domainStrategy`. The built-in DNS server is used for DNS queries only with the following values:
|
||||
- `"IPIfNonMatch"`: When the request target is a domain name without an accompanying IP, Xray first performs a round of matching using the other conditions. If no routing rule matches in that round, it resolves the domain through the built-in DNS server and performs another round of routing rule matching using the returned IP addresses.
|
||||
- `"IPOnDemand"`: When the request target is a domain name without an accompanying IP, the domain is immediately resolved to IPs for matching as soon as routing encounters an IP-based rule.
|
||||
- **Routing Phase:** Resolves domain names to IPs and matches rules based on the resolved IPs for traffic splitting.
|
||||
::: details Detailed explanation
|
||||
Whether a domain name is resolved for IP-based routing depends on `routing.domainStrategy`. The built-in DNS server may be used for DNS queries only with the following values:
|
||||
- `"IPIfNonMatch"`: If no rule matches during the first routing pass, resolution occurs whenever the target includes a domain name and at least one rule contains an `ip` condition.
|
||||
- `"IPOnDemand"`: Resolution occurs when the target includes a domain name and a rule containing an `ip` condition is encountered.
|
||||
|
||||
- **Outbound Phase:** Resolves target domain names for connections or for sending to a remote proxy server:
|
||||
:::
|
||||
|
||||
- **Outbound Phase:** Resolves target domain names for connections or for sending to a remote proxy server.
|
||||
::: details Detailed explanation
|
||||
- For example, setting `targetStrategy` to `UseIP` in a VLESS outbound resolves the target domain of the proxied request through the local built-in DNS module, then sends the resolved IP to the remote proxy server.
|
||||
- Setting `sockopt.domainStrategy` to `UseIP` in a VLESS outbound resolves the VLESS server's domain through the built-in DNS module, then connects to the resolved IP.
|
||||
- Setting `sockopt.domainStrategy` to `UseIP` in a Freedom outbound resolves the request's target domain through the built-in DNS module, then connects to the resolved IP.
|
||||
- WireGuard does not allow domain names as destinations, so its outbound can use the built-in DNS module to resolve them to IPs.
|
||||
|
||||
:::
|
||||
|
||||
- **TUN/Transparent Proxy DNS Traffic Hijacking:** Combines routing with the DNS outbound to hijack DNS traffic into this module; or uses [Tunnel](./inbounds/tunnel.md) to expose port 53 and act as a recursive DNS server.
|
||||
::: details Detailed explanation
|
||||
- Only basic IP queries (A and AAAA records) are supported. CNAME records will be queried repeatedly until an A/AAAA record is returned. Other queries will not enter the built-in DNS server; instead, they may be discarded or transparently forwarded to other servers depending on your outbound configuration.
|
||||
|
||||
:::
|
||||
|
||||
## DNS Processing Flow
|
||||
|
||||
The domain first undergoes a Hosts mapping check (see the `hosts` field). If the required IP is not found, the DNS server is used for the query.
|
||||
|
||||
@@ -24,15 +24,13 @@ For a more detailed analysis of the routing function: [Analysis of Routing (Part
|
||||
|
||||
Domain resolution strategy. Different strategies are used based on different settings.
|
||||
|
||||
- `"AsIs"`: No extra operation. Uses the domain in the destination address or the sniffed domain. Default value.
|
||||
- `"IPIfNonMatch"`: When no rule is matched after a full round of matching, resolve the domain to an IP and perform a second round of matching.
|
||||
- `"IPOnDemand"`: Before starting matching, resolve the domain to an IP immediately for matching.
|
||||
- `"AsIs"`: Does not perform DNS resolution. Default value.
|
||||
- `"IPIfNonMatch"`: Domain names are not resolved initially. If no rule matches after the full pass and the target includes a domain name, Xray starts a second pass. During that pass, when it encounters a rule containing an `ip` condition, it uses the built-in DNS server to resolve the domain name to IPs for matching.
|
||||
- `"IPOnDemand"`: If the target includes a domain name, Xray uses the built-in DNS server to resolve it to IPs for matching when it encounters a rule containing an `ip` condition. If resolution fails, the original destination IP is used for matching.
|
||||
|
||||
Actual resolution behavior will be delayed until the first IP rule is encountered to reduce latency. The result will contain both IPv4 and IPv6 (you can further restrict this via `queryStrategy` in the built-in DNS). When a domain resolves to multiple IPs, each rule will try all IPs in turn. If any IP meets the requirement, the rule is considered matched.
|
||||
Resolution results contain both IPv4 and IPv6 addresses (this can be further restricted through the built-in DNS module's `queryStrategy`). When a domain name resolves to multiple IPs, each rule tries all of them in turn. If any IP meets the condition, the rule is considered matched.
|
||||
|
||||
When `sniff` + `routeOnly` is enabled, allowing the routing system to see both IP and domain, if the aforementioned resolution occurs, the routing system can only see the IP resolved from the domain and cannot see the original destination IP, unless resolution fails.
|
||||
|
||||
When two domains exist (target domain + sniffed result), the priority of the sniffed result is always higher, whether for resolution or domain matching.
|
||||
The original destination may be either an IP address or a domain name. When [`sniffing`](./inbound.md#sniffingobject) and `routeOnly` are enabled, the routing system can see the domain name obtained through sniffing in addition to the original destination. Therefore, even if no DNS resolution occurs, it can still use an IP already present in the original destination for rule matching. If both the original destination domain and the sniffing result are available, the sniffing result always takes precedence for both DNS resolution and domain matching.
|
||||
|
||||
Regardless of whether resolution occurs, the routing system will not affect the actual destination address. The requested target remains the original target.
|
||||
|
||||
|
||||
@@ -93,7 +93,12 @@ When [tunnel](../inbounds/tunnel.md) has `followRedirect` set to `true`, and `tp
|
||||
|
||||
The default value is `"AsIs"`.
|
||||
|
||||
When the address an outbound needs to connect to is a domain name, this option controls how it is resolved:
|
||||
This option controls how the connection destination's domain name is resolved when an outbound establishes an underlying connection.
|
||||
|
||||
- Proxy outbounds such as VLESS, VMess, and Trojan: the underlying connection is to the proxy server, so this option controls resolution of the proxy server's domain name. Whether the target domain name in the proxied request is resolved locally is controlled by the outbound's [`targetStrategy`](../outbound.md#outboundobject).
|
||||
- Freedom outbound: the underlying connection is to the request's target itself, so this option controls resolution of the request's target domain name.
|
||||
|
||||
The strategies work as follows:
|
||||
|
||||
- With `"AsIs"`, Xray passes the domain name to Go, which resolves it using the operating system's DNS settings and connects. TCP usually tries IPv6 first and tries IPv4 if the connection does not proceed smoothly; UDP prefers IPv4.
|
||||
|
||||
@@ -102,7 +107,9 @@ When the address an outbound needs to connect to is a domain name, this option c
|
||||
|
||||
With a pure Go build of Xray, addresses are sorted using a simplified version of RFC 6724, which usually prefers IPv6 when other conditions are equal and does not read `/etc/gai.conf`. Most official Xray release builds use this approach; behavior may differ slightly on some operating systems or in downstream builds. See [Go's address sorting implementation](https://go.dev/src/net/addrselect.go).
|
||||
|
||||
UDP prefers an IPv4 address from the resolved results and uses IPv6 only if no IPv4 address is available. A send failure does not automatically switch to the other address family. This also applies when a `Use` strategy falls back to `AsIs`. See [Go's UDP address selection implementation](https://go.dev/src/net/ipsock.go).
|
||||
UDP prefers an IPv4 address from the resolved results and uses IPv6 only if no IPv4 address is available. A send failure does not automatically switch to the other address family. See [Go's UDP address selection implementation](https://go.dev/src/net/ipsock.go).
|
||||
|
||||
Note that a `Use` strategy may fall back to `AsIs` if resolution fails or the results do not meet the requirements. In that case, both TCP and UDP follow the behavior described above.
|
||||
:::
|
||||
|
||||
- With any other value, Xray uses its [built-in DNS module](../dns.md) for resolution. If no `DNSObject` is configured, system DNS is used. If multiple IP addresses match, one is selected randomly by default; when `sockopt.happyEyeballs` is enabled for TCP, the addresses are raced instead.
|
||||
@@ -132,6 +139,8 @@ This feature is **not recommended** for inexperienced users unless they understa
|
||||
8. The problem appears: the connection from step 3 is waiting for the query result from step 7, while step 7 cannot finish until the connection from step 3 is fully established.
|
||||
9. Good game.
|
||||
|
||||
Direct connections through Freedom can have the same problem: if connecting to a DNS server requires resolving its own domain name through that same server, a circular dependency is created.
|
||||
|
||||
Possible solutions:
|
||||
|
||||
- Fix the traffic split of the built-in DNS server.
|
||||
|
||||
Reference in New Issue
Block a user