mirror of
https://github.com/SagerNet/sing-box.git
synced 2026-04-13 20:28:32 +10:00
Compare commits
4 Commits
v1.12.0-be
...
dev-dns-ti
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
0d8c15932f | ||
|
|
70371c3cbe | ||
|
|
32bc8b48f1 | ||
|
|
b5df508bc9 |
@@ -3,6 +3,7 @@ package adapter
|
|||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"net/netip"
|
"net/netip"
|
||||||
|
"time"
|
||||||
|
|
||||||
C "github.com/sagernet/sing-box/constant"
|
C "github.com/sagernet/sing-box/constant"
|
||||||
"github.com/sagernet/sing-box/log"
|
"github.com/sagernet/sing-box/log"
|
||||||
@@ -36,6 +37,7 @@ type DNSQueryOptions struct {
|
|||||||
Transport DNSTransport
|
Transport DNSTransport
|
||||||
Strategy C.DomainStrategy
|
Strategy C.DomainStrategy
|
||||||
LookupStrategy C.DomainStrategy
|
LookupStrategy C.DomainStrategy
|
||||||
|
Timeout time.Duration
|
||||||
DisableCache bool
|
DisableCache bool
|
||||||
RewriteTTL *uint32
|
RewriteTTL *uint32
|
||||||
ClientSubnet netip.Prefix
|
ClientSubnet netip.Prefix
|
||||||
@@ -53,6 +55,7 @@ func DNSQueryOptionsFrom(ctx context.Context, options *option.DomainResolveOptio
|
|||||||
return &DNSQueryOptions{
|
return &DNSQueryOptions{
|
||||||
Transport: transport,
|
Transport: transport,
|
||||||
Strategy: C.DomainStrategy(options.Strategy),
|
Strategy: C.DomainStrategy(options.Strategy),
|
||||||
|
Timeout: time.Duration(options.Timeout),
|
||||||
DisableCache: options.DisableCache,
|
DisableCache: options.DisableCache,
|
||||||
RewriteTTL: options.RewriteTTL,
|
RewriteTTL: options.RewriteTTL,
|
||||||
ClientSubnet: options.ClientSubnet.Build(netip.Prefix{}),
|
ClientSubnet: options.ClientSubnet.Build(netip.Prefix{}),
|
||||||
@@ -70,6 +73,7 @@ type DNSTransport interface {
|
|||||||
Type() string
|
Type() string
|
||||||
Tag() string
|
Tag() string
|
||||||
Dependencies() []string
|
Dependencies() []string
|
||||||
|
HasDetour() bool
|
||||||
Exchange(ctx context.Context, message *dns.Msg) (*dns.Msg, error)
|
Exchange(ctx context.Context, message *dns.Msg) (*dns.Msg, error)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -89,6 +89,7 @@ func NewWithOptions(options Options) (N.Dialer, error) {
|
|||||||
dnsQueryOptions = adapter.DNSQueryOptions{
|
dnsQueryOptions = adapter.DNSQueryOptions{
|
||||||
Transport: transport,
|
Transport: transport,
|
||||||
Strategy: strategy,
|
Strategy: strategy,
|
||||||
|
Timeout: time.Duration(dialOptions.DomainResolver.Timeout),
|
||||||
DisableCache: dialOptions.DomainResolver.DisableCache,
|
DisableCache: dialOptions.DomainResolver.DisableCache,
|
||||||
RewriteTTL: dialOptions.DomainResolver.RewriteTTL,
|
RewriteTTL: dialOptions.DomainResolver.RewriteTTL,
|
||||||
ClientSubnet: dialOptions.DomainResolver.ClientSubnet.Build(netip.Prefix{}),
|
ClientSubnet: dialOptions.DomainResolver.ClientSubnet.Build(netip.Prefix{}),
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ const (
|
|||||||
TCPTimeout = 15 * time.Second
|
TCPTimeout = 15 * time.Second
|
||||||
ReadPayloadTimeout = 300 * time.Millisecond
|
ReadPayloadTimeout = 300 * time.Millisecond
|
||||||
DNSTimeout = 10 * time.Second
|
DNSTimeout = 10 * time.Second
|
||||||
|
DirectDNSTimeout = 5 * time.Second
|
||||||
UDPTimeout = 5 * time.Minute
|
UDPTimeout = 5 * time.Minute
|
||||||
DefaultURLTestInterval = 3 * time.Minute
|
DefaultURLTestInterval = 3 * time.Minute
|
||||||
DefaultURLTestIdleTimeout = 30 * time.Minute
|
DefaultURLTestIdleTimeout = 30 * time.Minute
|
||||||
|
|||||||
@@ -30,7 +30,6 @@ var (
|
|||||||
var _ adapter.DNSClient = (*Client)(nil)
|
var _ adapter.DNSClient = (*Client)(nil)
|
||||||
|
|
||||||
type Client struct {
|
type Client struct {
|
||||||
timeout time.Duration
|
|
||||||
disableCache bool
|
disableCache bool
|
||||||
disableExpire bool
|
disableExpire bool
|
||||||
independentCache bool
|
independentCache bool
|
||||||
@@ -43,7 +42,6 @@ type Client struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type ClientOptions struct {
|
type ClientOptions struct {
|
||||||
Timeout time.Duration
|
|
||||||
DisableCache bool
|
DisableCache bool
|
||||||
DisableExpire bool
|
DisableExpire bool
|
||||||
IndependentCache bool
|
IndependentCache bool
|
||||||
@@ -55,7 +53,6 @@ type ClientOptions struct {
|
|||||||
|
|
||||||
func NewClient(options ClientOptions) *Client {
|
func NewClient(options ClientOptions) *Client {
|
||||||
client := &Client{
|
client := &Client{
|
||||||
timeout: options.Timeout,
|
|
||||||
disableCache: options.DisableCache,
|
disableCache: options.DisableCache,
|
||||||
disableExpire: options.DisableExpire,
|
disableExpire: options.DisableExpire,
|
||||||
independentCache: options.IndependentCache,
|
independentCache: options.IndependentCache,
|
||||||
@@ -63,9 +60,6 @@ func NewClient(options ClientOptions) *Client {
|
|||||||
initRDRCFunc: options.RDRC,
|
initRDRCFunc: options.RDRC,
|
||||||
logger: options.Logger,
|
logger: options.Logger,
|
||||||
}
|
}
|
||||||
if client.timeout == 0 {
|
|
||||||
client.timeout = C.DNSTimeout
|
|
||||||
}
|
|
||||||
cacheCapacity := options.CacheCapacity
|
cacheCapacity := options.CacheCapacity
|
||||||
if cacheCapacity < 1024 {
|
if cacheCapacity < 1024 {
|
||||||
cacheCapacity = 1024
|
cacheCapacity = 1024
|
||||||
@@ -153,7 +147,15 @@ func (c *Client) Exchange(ctx context.Context, transport adapter.DNSTransport, m
|
|||||||
return nil, ErrResponseRejectedCached
|
return nil, ErrResponseRejectedCached
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ctx, cancel := context.WithTimeout(ctx, c.timeout)
|
timeout := options.Timeout
|
||||||
|
if timeout == 0 {
|
||||||
|
if transport.HasDetour() {
|
||||||
|
timeout = C.DNSTimeout
|
||||||
|
} else {
|
||||||
|
timeout = C.DirectDNSTimeout
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ctx, cancel := context.WithTimeout(ctx, timeout)
|
||||||
response, err := transport.Exchange(ctx, message)
|
response, err := transport.Exchange(ctx, message)
|
||||||
cancel()
|
cancel()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|||||||
@@ -158,6 +158,9 @@ func (r *Router) matchDNS(ctx context.Context, allowFakeIP bool, ruleIndex int,
|
|||||||
if action.Strategy != C.DomainStrategyAsIS {
|
if action.Strategy != C.DomainStrategyAsIS {
|
||||||
options.Strategy = action.Strategy
|
options.Strategy = action.Strategy
|
||||||
}
|
}
|
||||||
|
if action.Timeout > 0 {
|
||||||
|
options.Timeout = action.Timeout
|
||||||
|
}
|
||||||
if isFakeIP || action.DisableCache {
|
if isFakeIP || action.DisableCache {
|
||||||
options.DisableCache = true
|
options.DisableCache = true
|
||||||
}
|
}
|
||||||
@@ -180,6 +183,9 @@ func (r *Router) matchDNS(ctx context.Context, allowFakeIP bool, ruleIndex int,
|
|||||||
if action.Strategy != C.DomainStrategyAsIS {
|
if action.Strategy != C.DomainStrategyAsIS {
|
||||||
options.Strategy = action.Strategy
|
options.Strategy = action.Strategy
|
||||||
}
|
}
|
||||||
|
if action.Timeout > 0 {
|
||||||
|
options.Timeout = action.Timeout
|
||||||
|
}
|
||||||
if action.DisableCache {
|
if action.DisableCache {
|
||||||
options.DisableCache = true
|
options.DisableCache = true
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -41,6 +41,7 @@ type Transport struct {
|
|||||||
dns.TransportAdapter
|
dns.TransportAdapter
|
||||||
ctx context.Context
|
ctx context.Context
|
||||||
dialer N.Dialer
|
dialer N.Dialer
|
||||||
|
hasDetour bool
|
||||||
logger logger.ContextLogger
|
logger logger.ContextLogger
|
||||||
networkManager adapter.NetworkManager
|
networkManager adapter.NetworkManager
|
||||||
interfaceName string
|
interfaceName string
|
||||||
@@ -59,6 +60,7 @@ func NewTransport(ctx context.Context, logger log.ContextLogger, tag string, opt
|
|||||||
TransportAdapter: dns.NewTransportAdapterWithLocalOptions(C.DNSTypeDHCP, tag, options.LocalDNSServerOptions),
|
TransportAdapter: dns.NewTransportAdapterWithLocalOptions(C.DNSTypeDHCP, tag, options.LocalDNSServerOptions),
|
||||||
ctx: ctx,
|
ctx: ctx,
|
||||||
dialer: transportDialer,
|
dialer: transportDialer,
|
||||||
|
hasDetour: options.Detour != "",
|
||||||
logger: logger,
|
logger: logger,
|
||||||
networkManager: service.FromContext[adapter.NetworkManager](ctx),
|
networkManager: service.FromContext[adapter.NetworkManager](ctx),
|
||||||
interfaceName: options.Interface,
|
interfaceName: options.Interface,
|
||||||
@@ -89,6 +91,10 @@ func (t *Transport) Close() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (t *Transport) HasDetour() bool {
|
||||||
|
return t.hasDetour
|
||||||
|
}
|
||||||
|
|
||||||
func (t *Transport) Exchange(ctx context.Context, message *mDNS.Msg) (*mDNS.Msg, error) {
|
func (t *Transport) Exchange(ctx context.Context, message *mDNS.Msg) (*mDNS.Msg, error) {
|
||||||
err := t.fetchServers()
|
err := t.fetchServers()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|||||||
@@ -3,11 +3,15 @@ package transport
|
|||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"context"
|
"context"
|
||||||
|
"errors"
|
||||||
"io"
|
"io"
|
||||||
"net"
|
"net"
|
||||||
"net/http"
|
"net/http"
|
||||||
"net/url"
|
"net/url"
|
||||||
|
"os"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
"sync"
|
||||||
|
"time"
|
||||||
|
|
||||||
"github.com/sagernet/sing-box/adapter"
|
"github.com/sagernet/sing-box/adapter"
|
||||||
"github.com/sagernet/sing-box/common/dialer"
|
"github.com/sagernet/sing-box/common/dialer"
|
||||||
@@ -39,11 +43,13 @@ func RegisterHTTPS(registry *dns.TransportRegistry) {
|
|||||||
|
|
||||||
type HTTPSTransport struct {
|
type HTTPSTransport struct {
|
||||||
dns.TransportAdapter
|
dns.TransportAdapter
|
||||||
logger logger.ContextLogger
|
logger logger.ContextLogger
|
||||||
dialer N.Dialer
|
dialer N.Dialer
|
||||||
destination *url.URL
|
destination *url.URL
|
||||||
headers http.Header
|
headers http.Header
|
||||||
transport *http.Transport
|
transportAccess sync.Mutex
|
||||||
|
transport *http.Transport
|
||||||
|
transportResetAt time.Time
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewHTTPS(ctx context.Context, logger log.ContextLogger, tag string, options option.RemoteHTTPSDNSServerOptions) (adapter.DNSTransport, error) {
|
func NewHTTPS(ctx context.Context, logger log.ContextLogger, tag string, options option.RemoteHTTPSDNSServerOptions) (adapter.DNSTransport, error) {
|
||||||
@@ -122,7 +128,6 @@ func NewHTTPSRaw(
|
|||||||
var transport *http.Transport
|
var transport *http.Transport
|
||||||
if tlsConfig != nil {
|
if tlsConfig != nil {
|
||||||
transport = &http.Transport{
|
transport = &http.Transport{
|
||||||
IdleConnTimeout: C.TCPKeepAliveInitial,
|
|
||||||
ForceAttemptHTTP2: true,
|
ForceAttemptHTTP2: true,
|
||||||
DialTLSContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
|
DialTLSContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
|
||||||
tcpConn, hErr := dialer.DialContext(ctx, network, serverAddr)
|
tcpConn, hErr := dialer.DialContext(ctx, network, serverAddr)
|
||||||
@@ -139,7 +144,6 @@ func NewHTTPSRaw(
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
transport = &http.Transport{
|
transport = &http.Transport{
|
||||||
IdleConnTimeout: C.TCPKeepAliveInitial,
|
|
||||||
DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
|
DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
|
||||||
return dialer.DialContext(ctx, network, serverAddr)
|
return dialer.DialContext(ctx, network, serverAddr)
|
||||||
},
|
},
|
||||||
@@ -163,12 +167,33 @@ func (t *HTTPSTransport) Start(stage adapter.StartStage) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (t *HTTPSTransport) Close() error {
|
func (t *HTTPSTransport) Close() error {
|
||||||
|
t.transportAccess.Lock()
|
||||||
|
defer t.transportAccess.Unlock()
|
||||||
t.transport.CloseIdleConnections()
|
t.transport.CloseIdleConnections()
|
||||||
t.transport = t.transport.Clone()
|
t.transport = t.transport.Clone()
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *HTTPSTransport) Exchange(ctx context.Context, message *mDNS.Msg) (*mDNS.Msg, error) {
|
func (t *HTTPSTransport) Exchange(ctx context.Context, message *mDNS.Msg) (*mDNS.Msg, error) {
|
||||||
|
startAt := time.Now()
|
||||||
|
response, err := t.exchange(ctx, message)
|
||||||
|
if err != nil {
|
||||||
|
if errors.Is(err, os.ErrDeadlineExceeded) {
|
||||||
|
t.transportAccess.Lock()
|
||||||
|
defer t.transportAccess.Unlock()
|
||||||
|
if t.transportResetAt.After(startAt) {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
t.transport.CloseIdleConnections()
|
||||||
|
t.transport = t.transport.Clone()
|
||||||
|
t.transportResetAt = time.Now()
|
||||||
|
}
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return response, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (t *HTTPSTransport) exchange(ctx context.Context, message *mDNS.Msg) (*mDNS.Msg, error) {
|
||||||
exMessage := *message
|
exMessage := *message
|
||||||
exMessage.Id = 0
|
exMessage.Id = 0
|
||||||
exMessage.Compress = true
|
exMessage.Compress = true
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ type TransportAdapter struct {
|
|||||||
transportType string
|
transportType string
|
||||||
transportTag string
|
transportTag string
|
||||||
dependencies []string
|
dependencies []string
|
||||||
|
hasDetour bool
|
||||||
strategy C.DomainStrategy
|
strategy C.DomainStrategy
|
||||||
clientSubnet netip.Prefix
|
clientSubnet netip.Prefix
|
||||||
}
|
}
|
||||||
@@ -35,6 +36,7 @@ func NewTransportAdapterWithLocalOptions(transportType string, transportTag stri
|
|||||||
transportType: transportType,
|
transportType: transportType,
|
||||||
transportTag: transportTag,
|
transportTag: transportTag,
|
||||||
dependencies: dependencies,
|
dependencies: dependencies,
|
||||||
|
hasDetour: localOptions.Detour != "",
|
||||||
strategy: C.DomainStrategy(localOptions.LegacyStrategy),
|
strategy: C.DomainStrategy(localOptions.LegacyStrategy),
|
||||||
clientSubnet: localOptions.LegacyClientSubnet,
|
clientSubnet: localOptions.LegacyClientSubnet,
|
||||||
}
|
}
|
||||||
@@ -69,6 +71,10 @@ func (a *TransportAdapter) Dependencies() []string {
|
|||||||
return a.dependencies
|
return a.dependencies
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (a *TransportAdapter) HasDetour() bool {
|
||||||
|
return a.hasDetour
|
||||||
|
}
|
||||||
|
|
||||||
func (a *TransportAdapter) LegacyStrategy() C.DomainStrategy {
|
func (a *TransportAdapter) LegacyStrategy() C.DomainStrategy {
|
||||||
return a.strategy
|
return a.strategy
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
icon: material/alert-decagram
|
icon: material/alert-decagram
|
||||||
---
|
---
|
||||||
|
|
||||||
#### 1.12.0-beta.29
|
#### 1.12.0-beta.30
|
||||||
|
|
||||||
* Fixes and improvements
|
* Fixes and improvements
|
||||||
|
|
||||||
|
|||||||
2
go.mod
2
go.mod
@@ -34,7 +34,7 @@ require (
|
|||||||
github.com/sagernet/sing-shadowsocks v0.2.8
|
github.com/sagernet/sing-shadowsocks v0.2.8
|
||||||
github.com/sagernet/sing-shadowsocks2 v0.2.1
|
github.com/sagernet/sing-shadowsocks2 v0.2.1
|
||||||
github.com/sagernet/sing-shadowtls v0.2.1-0.20250503051639-fcd445d33c11
|
github.com/sagernet/sing-shadowtls v0.2.1-0.20250503051639-fcd445d33c11
|
||||||
github.com/sagernet/sing-tun v0.6.10-0.20250620051458-5e343c4b66b2
|
github.com/sagernet/sing-tun v0.6.10-0.20250630100036-8763c24e4935
|
||||||
github.com/sagernet/sing-vmess v0.2.4-0.20250605032146-38cc72672c88
|
github.com/sagernet/sing-vmess v0.2.4-0.20250605032146-38cc72672c88
|
||||||
github.com/sagernet/smux v1.5.34-mod.2
|
github.com/sagernet/smux v1.5.34-mod.2
|
||||||
github.com/sagernet/tailscale v1.80.3-mod.5
|
github.com/sagernet/tailscale v1.80.3-mod.5
|
||||||
|
|||||||
4
go.sum
4
go.sum
@@ -180,8 +180,8 @@ github.com/sagernet/sing-shadowsocks2 v0.2.1 h1:dWV9OXCeFPuYGHb6IRqlSptVnSzOelnq
|
|||||||
github.com/sagernet/sing-shadowsocks2 v0.2.1/go.mod h1:RnXS0lExcDAovvDeniJ4IKa2IuChrdipolPYWBv9hWQ=
|
github.com/sagernet/sing-shadowsocks2 v0.2.1/go.mod h1:RnXS0lExcDAovvDeniJ4IKa2IuChrdipolPYWBv9hWQ=
|
||||||
github.com/sagernet/sing-shadowtls v0.2.1-0.20250503051639-fcd445d33c11 h1:tK+75l64tm9WvEFrYRE1t0YxoFdWQqw/h7Uhzj0vJ+w=
|
github.com/sagernet/sing-shadowtls v0.2.1-0.20250503051639-fcd445d33c11 h1:tK+75l64tm9WvEFrYRE1t0YxoFdWQqw/h7Uhzj0vJ+w=
|
||||||
github.com/sagernet/sing-shadowtls v0.2.1-0.20250503051639-fcd445d33c11/go.mod h1:sWqKnGlMipCHaGsw1sTTlimyUpgzP4WP3pjhCsYt9oA=
|
github.com/sagernet/sing-shadowtls v0.2.1-0.20250503051639-fcd445d33c11/go.mod h1:sWqKnGlMipCHaGsw1sTTlimyUpgzP4WP3pjhCsYt9oA=
|
||||||
github.com/sagernet/sing-tun v0.6.10-0.20250620051458-5e343c4b66b2 h1:ykbqGFHDNVvp0jhgLime/XBAtQpcOcFpT8Rs5Hcc5n4=
|
github.com/sagernet/sing-tun v0.6.10-0.20250630100036-8763c24e4935 h1:wha4BG4mrEKaIoouVyiU5BcPfKD1n0LkiL4vqdjaVps=
|
||||||
github.com/sagernet/sing-tun v0.6.10-0.20250620051458-5e343c4b66b2/go.mod h1:fisFCbC4Vfb6HqQNcwPJi2CDK2bf0Xapyz3j3t4cnHE=
|
github.com/sagernet/sing-tun v0.6.10-0.20250630100036-8763c24e4935/go.mod h1:fisFCbC4Vfb6HqQNcwPJi2CDK2bf0Xapyz3j3t4cnHE=
|
||||||
github.com/sagernet/sing-vmess v0.2.4-0.20250605032146-38cc72672c88 h1:0pVm8sPOel+BoiCddW3pV3cKDKEaSioVTYDdTSKjyFI=
|
github.com/sagernet/sing-vmess v0.2.4-0.20250605032146-38cc72672c88 h1:0pVm8sPOel+BoiCddW3pV3cKDKEaSioVTYDdTSKjyFI=
|
||||||
github.com/sagernet/sing-vmess v0.2.4-0.20250605032146-38cc72672c88/go.mod h1:IL8Rr+EGwuqijszZkNrEFTQDKhilEpkqFqOlvdpS6/w=
|
github.com/sagernet/sing-vmess v0.2.4-0.20250605032146-38cc72672c88/go.mod h1:IL8Rr+EGwuqijszZkNrEFTQDKhilEpkqFqOlvdpS6/w=
|
||||||
github.com/sagernet/smux v1.5.34-mod.2 h1:gkmBjIjlJ2zQKpLigOkFur5kBKdV6bNRoFu2WkltRQ4=
|
github.com/sagernet/smux v1.5.34-mod.2 h1:gkmBjIjlJ2zQKpLigOkFur5kBKdV6bNRoFu2WkltRQ4=
|
||||||
|
|||||||
@@ -91,6 +91,7 @@ type DialerOptions struct {
|
|||||||
type _DomainResolveOptions struct {
|
type _DomainResolveOptions struct {
|
||||||
Server string `json:"server"`
|
Server string `json:"server"`
|
||||||
Strategy DomainStrategy `json:"strategy,omitempty"`
|
Strategy DomainStrategy `json:"strategy,omitempty"`
|
||||||
|
Timeout badoption.Duration `json:"timeout,omitempty"`
|
||||||
DisableCache bool `json:"disable_cache,omitempty"`
|
DisableCache bool `json:"disable_cache,omitempty"`
|
||||||
RewriteTTL *uint32 `json:"rewrite_ttl,omitempty"`
|
RewriteTTL *uint32 `json:"rewrite_ttl,omitempty"`
|
||||||
ClientSubnet *badoption.Prefixable `json:"client_subnet,omitempty"`
|
ClientSubnet *badoption.Prefixable `json:"client_subnet,omitempty"`
|
||||||
@@ -102,6 +103,7 @@ func (o DomainResolveOptions) MarshalJSON() ([]byte, error) {
|
|||||||
if o.Server == "" {
|
if o.Server == "" {
|
||||||
return []byte("{}"), nil
|
return []byte("{}"), nil
|
||||||
} else if o.Strategy == DomainStrategy(C.DomainStrategyAsIS) &&
|
} else if o.Strategy == DomainStrategy(C.DomainStrategyAsIS) &&
|
||||||
|
o.Timeout == 0 &&
|
||||||
!o.DisableCache &&
|
!o.DisableCache &&
|
||||||
o.RewriteTTL == nil &&
|
o.RewriteTTL == nil &&
|
||||||
o.ClientSubnet == nil {
|
o.ClientSubnet == nil {
|
||||||
|
|||||||
@@ -180,6 +180,7 @@ func (r *RouteOptionsActionOptions) UnmarshalJSON(data []byte) error {
|
|||||||
type DNSRouteActionOptions struct {
|
type DNSRouteActionOptions struct {
|
||||||
Server string `json:"server,omitempty"`
|
Server string `json:"server,omitempty"`
|
||||||
Strategy DomainStrategy `json:"strategy,omitempty"`
|
Strategy DomainStrategy `json:"strategy,omitempty"`
|
||||||
|
Timeout badoption.Duration `json:"timeout,omitempty"`
|
||||||
DisableCache bool `json:"disable_cache,omitempty"`
|
DisableCache bool `json:"disable_cache,omitempty"`
|
||||||
RewriteTTL *uint32 `json:"rewrite_ttl,omitempty"`
|
RewriteTTL *uint32 `json:"rewrite_ttl,omitempty"`
|
||||||
ClientSubnet *badoption.Prefixable `json:"client_subnet,omitempty"`
|
ClientSubnet *badoption.Prefixable `json:"client_subnet,omitempty"`
|
||||||
@@ -187,6 +188,7 @@ type DNSRouteActionOptions struct {
|
|||||||
|
|
||||||
type _DNSRouteOptionsActionOptions struct {
|
type _DNSRouteOptionsActionOptions struct {
|
||||||
Strategy DomainStrategy `json:"strategy,omitempty"`
|
Strategy DomainStrategy `json:"strategy,omitempty"`
|
||||||
|
Timeout badoption.Duration `json:"timeout,omitempty"`
|
||||||
DisableCache bool `json:"disable_cache,omitempty"`
|
DisableCache bool `json:"disable_cache,omitempty"`
|
||||||
RewriteTTL *uint32 `json:"rewrite_ttl,omitempty"`
|
RewriteTTL *uint32 `json:"rewrite_ttl,omitempty"`
|
||||||
ClientSubnet *badoption.Prefixable `json:"client_subnet,omitempty"`
|
ClientSubnet *badoption.Prefixable `json:"client_subnet,omitempty"`
|
||||||
|
|||||||
@@ -76,6 +76,7 @@ func NewNetworkManager(ctx context.Context, logger logger.ContextLogger, routeOp
|
|||||||
DomainResolver: defaultDomainResolver.Server,
|
DomainResolver: defaultDomainResolver.Server,
|
||||||
DomainResolveOptions: adapter.DNSQueryOptions{
|
DomainResolveOptions: adapter.DNSQueryOptions{
|
||||||
Strategy: C.DomainStrategy(defaultDomainResolver.Strategy),
|
Strategy: C.DomainStrategy(defaultDomainResolver.Strategy),
|
||||||
|
Timeout: time.Duration(defaultDomainResolver.Timeout),
|
||||||
DisableCache: defaultDomainResolver.DisableCache,
|
DisableCache: defaultDomainResolver.DisableCache,
|
||||||
RewriteTTL: defaultDomainResolver.RewriteTTL,
|
RewriteTTL: defaultDomainResolver.RewriteTTL,
|
||||||
ClientSubnet: defaultDomainResolver.ClientSubnet.Build(netip.Prefix{}),
|
ClientSubnet: defaultDomainResolver.ClientSubnet.Build(netip.Prefix{}),
|
||||||
|
|||||||
@@ -666,6 +666,7 @@ func (r *Router) actionResolve(ctx context.Context, metadata *adapter.InboundCon
|
|||||||
addresses, err := r.dns.Lookup(adapter.WithContext(ctx, metadata), metadata.Destination.Fqdn, adapter.DNSQueryOptions{
|
addresses, err := r.dns.Lookup(adapter.WithContext(ctx, metadata), metadata.Destination.Fqdn, adapter.DNSQueryOptions{
|
||||||
Transport: transport,
|
Transport: transport,
|
||||||
Strategy: action.Strategy,
|
Strategy: action.Strategy,
|
||||||
|
Timeout: action.Timeout,
|
||||||
DisableCache: action.DisableCache,
|
DisableCache: action.DisableCache,
|
||||||
RewriteTTL: action.RewriteTTL,
|
RewriteTTL: action.RewriteTTL,
|
||||||
ClientSubnet: action.ClientSubnet,
|
ClientSubnet: action.ClientSubnet,
|
||||||
|
|||||||
@@ -113,6 +113,7 @@ func NewDNSRuleAction(logger logger.ContextLogger, action option.DNSRuleAction)
|
|||||||
Server: action.RouteOptions.Server,
|
Server: action.RouteOptions.Server,
|
||||||
RuleActionDNSRouteOptions: RuleActionDNSRouteOptions{
|
RuleActionDNSRouteOptions: RuleActionDNSRouteOptions{
|
||||||
Strategy: C.DomainStrategy(action.RouteOptions.Strategy),
|
Strategy: C.DomainStrategy(action.RouteOptions.Strategy),
|
||||||
|
Timeout: time.Duration(action.RouteOptions.Timeout),
|
||||||
DisableCache: action.RouteOptions.DisableCache,
|
DisableCache: action.RouteOptions.DisableCache,
|
||||||
RewriteTTL: action.RouteOptions.RewriteTTL,
|
RewriteTTL: action.RouteOptions.RewriteTTL,
|
||||||
ClientSubnet: netip.Prefix(common.PtrValueOrDefault(action.RouteOptions.ClientSubnet)),
|
ClientSubnet: netip.Prefix(common.PtrValueOrDefault(action.RouteOptions.ClientSubnet)),
|
||||||
@@ -121,6 +122,7 @@ func NewDNSRuleAction(logger logger.ContextLogger, action option.DNSRuleAction)
|
|||||||
case C.RuleActionTypeRouteOptions:
|
case C.RuleActionTypeRouteOptions:
|
||||||
return &RuleActionDNSRouteOptions{
|
return &RuleActionDNSRouteOptions{
|
||||||
Strategy: C.DomainStrategy(action.RouteOptionsOptions.Strategy),
|
Strategy: C.DomainStrategy(action.RouteOptionsOptions.Strategy),
|
||||||
|
Timeout: time.Duration(action.RouteOptionsOptions.Timeout),
|
||||||
DisableCache: action.RouteOptionsOptions.DisableCache,
|
DisableCache: action.RouteOptionsOptions.DisableCache,
|
||||||
RewriteTTL: action.RouteOptionsOptions.RewriteTTL,
|
RewriteTTL: action.RouteOptionsOptions.RewriteTTL,
|
||||||
ClientSubnet: netip.Prefix(common.PtrValueOrDefault(action.RouteOptionsOptions.ClientSubnet)),
|
ClientSubnet: netip.Prefix(common.PtrValueOrDefault(action.RouteOptionsOptions.ClientSubnet)),
|
||||||
@@ -235,20 +237,13 @@ func (r *RuleActionDNSRoute) Type() string {
|
|||||||
func (r *RuleActionDNSRoute) String() string {
|
func (r *RuleActionDNSRoute) String() string {
|
||||||
var descriptions []string
|
var descriptions []string
|
||||||
descriptions = append(descriptions, r.Server)
|
descriptions = append(descriptions, r.Server)
|
||||||
if r.DisableCache {
|
descriptions = append(descriptions, r.Descriptions()...)
|
||||||
descriptions = append(descriptions, "disable-cache")
|
|
||||||
}
|
|
||||||
if r.RewriteTTL != nil {
|
|
||||||
descriptions = append(descriptions, F.ToString("rewrite-ttl=", *r.RewriteTTL))
|
|
||||||
}
|
|
||||||
if r.ClientSubnet.IsValid() {
|
|
||||||
descriptions = append(descriptions, F.ToString("client-subnet=", r.ClientSubnet))
|
|
||||||
}
|
|
||||||
return F.ToString("route(", strings.Join(descriptions, ","), ")")
|
return F.ToString("route(", strings.Join(descriptions, ","), ")")
|
||||||
}
|
}
|
||||||
|
|
||||||
type RuleActionDNSRouteOptions struct {
|
type RuleActionDNSRouteOptions struct {
|
||||||
Strategy C.DomainStrategy
|
Strategy C.DomainStrategy
|
||||||
|
Timeout time.Duration
|
||||||
DisableCache bool
|
DisableCache bool
|
||||||
RewriteTTL *uint32
|
RewriteTTL *uint32
|
||||||
ClientSubnet netip.Prefix
|
ClientSubnet netip.Prefix
|
||||||
@@ -259,7 +254,17 @@ func (r *RuleActionDNSRouteOptions) Type() string {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (r *RuleActionDNSRouteOptions) String() string {
|
func (r *RuleActionDNSRouteOptions) String() string {
|
||||||
|
return F.ToString("route-options(", strings.Join(r.Descriptions(), ","), ")")
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *RuleActionDNSRouteOptions) Descriptions() []string {
|
||||||
var descriptions []string
|
var descriptions []string
|
||||||
|
if r.Strategy != C.DomainStrategyAsIS {
|
||||||
|
descriptions = append(descriptions, F.ToString("strategy=", option.DomainStrategy(r.Strategy)))
|
||||||
|
}
|
||||||
|
if r.Timeout > 0 {
|
||||||
|
descriptions = append(descriptions, F.ToString("timeout=", r.Timeout.String()))
|
||||||
|
}
|
||||||
if r.DisableCache {
|
if r.DisableCache {
|
||||||
descriptions = append(descriptions, "disable-cache")
|
descriptions = append(descriptions, "disable-cache")
|
||||||
}
|
}
|
||||||
@@ -269,7 +274,7 @@ func (r *RuleActionDNSRouteOptions) String() string {
|
|||||||
if r.ClientSubnet.IsValid() {
|
if r.ClientSubnet.IsValid() {
|
||||||
descriptions = append(descriptions, F.ToString("client-subnet=", r.ClientSubnet))
|
descriptions = append(descriptions, F.ToString("client-subnet=", r.ClientSubnet))
|
||||||
}
|
}
|
||||||
return F.ToString("route-options(", strings.Join(descriptions, ","), ")")
|
return descriptions
|
||||||
}
|
}
|
||||||
|
|
||||||
type RuleActionDirect struct {
|
type RuleActionDirect struct {
|
||||||
@@ -421,6 +426,7 @@ func (r *RuleActionSniff) String() string {
|
|||||||
type RuleActionResolve struct {
|
type RuleActionResolve struct {
|
||||||
Server string
|
Server string
|
||||||
Strategy C.DomainStrategy
|
Strategy C.DomainStrategy
|
||||||
|
Timeout time.Duration
|
||||||
DisableCache bool
|
DisableCache bool
|
||||||
RewriteTTL *uint32
|
RewriteTTL *uint32
|
||||||
ClientSubnet netip.Prefix
|
ClientSubnet netip.Prefix
|
||||||
@@ -438,6 +444,9 @@ func (r *RuleActionResolve) String() string {
|
|||||||
if r.Strategy != C.DomainStrategyAsIS {
|
if r.Strategy != C.DomainStrategyAsIS {
|
||||||
options = append(options, F.ToString(option.DomainStrategy(r.Strategy)))
|
options = append(options, F.ToString(option.DomainStrategy(r.Strategy)))
|
||||||
}
|
}
|
||||||
|
if r.Timeout > 0 {
|
||||||
|
options = append(options, F.ToString("timeout=", r.Timeout.String()))
|
||||||
|
}
|
||||||
if r.DisableCache {
|
if r.DisableCache {
|
||||||
options = append(options, "disable_cache")
|
options = append(options, "disable_cache")
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user