github.com/v2fly/v2ray-core/v5@v5.16.2-0.20240507031116-8191faa6e095/infra/conf/synthetic/dns/dns_test.go (about) 1 package dns_test 2 3 import ( 4 "encoding/json" 5 "errors" 6 "io/fs" 7 "os" 8 "path/filepath" 9 "testing" 10 11 "google.golang.org/protobuf/runtime/protoiface" 12 13 "github.com/v2fly/v2ray-core/v5/app/dns" 14 "github.com/v2fly/v2ray-core/v5/app/dns/fakedns" 15 "github.com/v2fly/v2ray-core/v5/common" 16 "github.com/v2fly/v2ray-core/v5/common/net" 17 "github.com/v2fly/v2ray-core/v5/common/platform/filesystem" 18 "github.com/v2fly/v2ray-core/v5/infra/conf/cfgcommon/testassist" 19 _ "github.com/v2fly/v2ray-core/v5/infra/conf/geodata/standard" 20 dns2 "github.com/v2fly/v2ray-core/v5/infra/conf/synthetic/dns" 21 ) 22 23 func init() { 24 const ( 25 geoipURL = "https://raw.githubusercontent.com/v2fly/geoip/release/geoip.dat" 26 geositeURL = "https://raw.githubusercontent.com/v2fly/domain-list-community/release/dlc.dat" 27 ) 28 29 wd, err := os.Getwd() 30 common.Must(err) 31 32 tempPath := filepath.Join(wd, "..", "..", "..", "..", "testing", "temp") 33 geoipPath := filepath.Join(tempPath, "geoip.dat") 34 geositePath := filepath.Join(tempPath, "geosite.dat") 35 36 os.Setenv("v2ray.location.asset", tempPath) 37 38 if _, err := os.Stat(geoipPath); err != nil && errors.Is(err, fs.ErrNotExist) { 39 common.Must(os.MkdirAll(tempPath, 0o755)) 40 geoipBytes, err := common.FetchHTTPContent(geoipURL) 41 common.Must(err) 42 common.Must(filesystem.WriteFile(geoipPath, geoipBytes)) 43 } 44 if _, err := os.Stat(geositePath); err != nil && errors.Is(err, fs.ErrNotExist) { 45 common.Must(os.MkdirAll(tempPath, 0o755)) 46 geositeBytes, err := common.FetchHTTPContent(geositeURL) 47 common.Must(err) 48 common.Must(filesystem.WriteFile(geositePath, geositeBytes)) 49 } 50 } 51 52 func TestDNSConfigParsing(t *testing.T) { 53 parserCreator := func() func(string) (protoiface.MessageV1, error) { 54 return func(s string) (protoiface.MessageV1, error) { 55 config := new(dns2.DNSConfig) 56 if err := json.Unmarshal([]byte(s), config); err != nil { 57 return nil, err 58 } 59 return config.Build() 60 } 61 } 62 63 testassist.RunMultiTestCase(t, []testassist.TestCase{ 64 { 65 Input: `{ 66 "servers": [{ 67 "address": "8.8.8.8", 68 "clientIp": "10.0.0.1", 69 "port": 5353, 70 "skipFallback": true, 71 "domains": ["domain:v2fly.org"] 72 }], 73 "hosts": { 74 "v2fly.org": "127.0.0.1", 75 "www.v2fly.org": ["1.2.3.4", "5.6.7.8"], 76 "domain:example.com": "google.com", 77 "geosite:test": ["127.0.0.1", "127.0.0.2"], 78 "keyword:google": ["8.8.8.8", "8.8.4.4"], 79 "regexp:.*\\.com": "8.8.4.4" 80 }, 81 "clientIp": "10.0.0.1", 82 "queryStrategy": "UseIPv4", 83 "disableCache": true, 84 "disableFallback": true 85 }`, 86 Parser: parserCreator(), 87 Output: &dns.Config{ 88 NameServer: []*dns.NameServer{ 89 { 90 Address: &net.Endpoint{ 91 Address: &net.IPOrDomain{ 92 Address: &net.IPOrDomain_Ip{ 93 Ip: []byte{8, 8, 8, 8}, 94 }, 95 }, 96 Network: net.Network_UDP, 97 Port: 5353, 98 }, 99 ClientIp: []byte{10, 0, 0, 1}, 100 SkipFallback: true, 101 PrioritizedDomain: []*dns.NameServer_PriorityDomain{ 102 { 103 Type: dns.DomainMatchingType_Subdomain, 104 Domain: "v2fly.org", 105 }, 106 }, 107 OriginalRules: []*dns.NameServer_OriginalRule{ 108 { 109 Rule: "domain:v2fly.org", 110 Size: 1, 111 }, 112 }, 113 }, 114 }, 115 StaticHosts: []*dns.HostMapping{ 116 { 117 Type: dns.DomainMatchingType_Subdomain, 118 Domain: "example.com", 119 ProxiedDomain: "google.com", 120 }, 121 { 122 Type: dns.DomainMatchingType_Full, 123 Domain: "test.example.com", 124 Ip: [][]byte{{127, 0, 0, 1}, {127, 0, 0, 2}}, 125 }, 126 { 127 Type: dns.DomainMatchingType_Keyword, 128 Domain: "google", 129 Ip: [][]byte{{8, 8, 8, 8}, {8, 8, 4, 4}}, 130 }, 131 { 132 Type: dns.DomainMatchingType_Regex, 133 Domain: ".*\\.com", 134 Ip: [][]byte{{8, 8, 4, 4}}, 135 }, 136 { 137 Type: dns.DomainMatchingType_Full, 138 Domain: "v2fly.org", 139 Ip: [][]byte{{127, 0, 0, 1}}, 140 }, 141 { 142 Type: dns.DomainMatchingType_Full, 143 Domain: "www.v2fly.org", 144 Ip: [][]byte{{1, 2, 3, 4}, {5, 6, 7, 8}}, 145 }, 146 }, 147 ClientIp: []byte{10, 0, 0, 1}, 148 QueryStrategy: dns.QueryStrategy_USE_IP4, 149 DisableCache: true, 150 DisableFallback: true, 151 }, 152 }, 153 { 154 Input: `{ 155 "servers": [{ 156 "address": "fakedns", 157 "tag": "fake", 158 "queryStrategy": "UseIPv6", 159 "fallbackStrategy": "disabledIfAnyMatch", 160 "fakedns": true 161 }, { 162 "address": "8.8.8.8", 163 "port": 5353, 164 "tag": "local", 165 "clientIp": "10.0.0.1", 166 "queryStrategy": "UseIP", 167 "cacheStrategy": "enabled", 168 "fallbackStrategy": "disabled", 169 "domains": ["domain:v2fly.org"], 170 "fakedns": ["198.19.0.0/16", "fc01::/18"] 171 }], 172 "hosts": { 173 "v2fly.org": "127.0.0.1", 174 "www.v2fly.org": ["1.2.3.4", "5.6.7.8"], 175 "domain:example.com": "google.com", 176 "geosite:test": ["127.0.0.1", "127.0.0.2"], 177 "keyword:google": ["8.8.8.8", "8.8.4.4"], 178 "regexp:.*\\.com": "8.8.4.4" 179 }, 180 "fakedns": [ 181 { "ipPool": "198.18.0.0/16", "poolSize": 32768 }, 182 { "ipPool": "fc00::/18", "poolSize": 32768 } 183 ], 184 "tag": "global", 185 "clientIp": "10.0.0.1", 186 "queryStrategy": "UseIPv4", 187 "cacheStrategy": "disabled", 188 "fallbackStrategy": "enabled" 189 }`, 190 Parser: parserCreator(), 191 Output: &dns.Config{ 192 NameServer: []*dns.NameServer{ 193 { 194 Address: &net.Endpoint{ 195 Address: &net.IPOrDomain{ 196 Address: &net.IPOrDomain_Domain{ 197 Domain: "fakedns", 198 }, 199 }, 200 Network: net.Network_UDP, 201 }, 202 Tag: "fake", 203 QueryStrategy: dns.QueryStrategy_USE_IP6.Enum(), 204 FallbackStrategy: dns.FallbackStrategy_DisabledIfAnyMatch.Enum(), 205 FakeDns: &fakedns.FakeDnsPoolMulti{ 206 Pools: []*fakedns.FakeDnsPool{}, 207 }, 208 }, 209 { 210 Address: &net.Endpoint{ 211 Address: &net.IPOrDomain{ 212 Address: &net.IPOrDomain_Ip{ 213 Ip: []byte{8, 8, 8, 8}, 214 }, 215 }, 216 Network: net.Network_UDP, 217 Port: 5353, 218 }, 219 Tag: "local", 220 ClientIp: []byte{10, 0, 0, 1}, 221 QueryStrategy: dns.QueryStrategy_USE_IP.Enum(), 222 CacheStrategy: dns.CacheStrategy_CacheEnabled.Enum(), 223 FallbackStrategy: dns.FallbackStrategy_Disabled.Enum(), 224 PrioritizedDomain: []*dns.NameServer_PriorityDomain{ 225 { 226 Type: dns.DomainMatchingType_Subdomain, 227 Domain: "v2fly.org", 228 }, 229 }, 230 OriginalRules: []*dns.NameServer_OriginalRule{ 231 { 232 Rule: "domain:v2fly.org", 233 Size: 1, 234 }, 235 }, 236 FakeDns: &fakedns.FakeDnsPoolMulti{ 237 Pools: []*fakedns.FakeDnsPool{ 238 {IpPool: "198.19.0.0/16", LruSize: 65535}, 239 {IpPool: "fc01::/18", LruSize: 65535}, 240 }, 241 }, 242 }, 243 }, 244 StaticHosts: []*dns.HostMapping{ 245 { 246 Type: dns.DomainMatchingType_Subdomain, 247 Domain: "example.com", 248 ProxiedDomain: "google.com", 249 }, 250 { 251 Type: dns.DomainMatchingType_Full, 252 Domain: "test.example.com", 253 Ip: [][]byte{{127, 0, 0, 1}, {127, 0, 0, 2}}, 254 }, 255 { 256 Type: dns.DomainMatchingType_Keyword, 257 Domain: "google", 258 Ip: [][]byte{{8, 8, 8, 8}, {8, 8, 4, 4}}, 259 }, 260 { 261 Type: dns.DomainMatchingType_Regex, 262 Domain: ".*\\.com", 263 Ip: [][]byte{{8, 8, 4, 4}}, 264 }, 265 { 266 Type: dns.DomainMatchingType_Full, 267 Domain: "v2fly.org", 268 Ip: [][]byte{{127, 0, 0, 1}}, 269 }, 270 { 271 Type: dns.DomainMatchingType_Full, 272 Domain: "www.v2fly.org", 273 Ip: [][]byte{{1, 2, 3, 4}, {5, 6, 7, 8}}, 274 }, 275 }, 276 FakeDns: &fakedns.FakeDnsPoolMulti{ 277 Pools: []*fakedns.FakeDnsPool{ 278 {IpPool: "198.18.0.0/16", LruSize: 32768}, 279 {IpPool: "fc00::/18", LruSize: 32768}, 280 }, 281 }, 282 Tag: "global", 283 ClientIp: []byte{10, 0, 0, 1}, 284 QueryStrategy: dns.QueryStrategy_USE_IP4, 285 CacheStrategy: dns.CacheStrategy_CacheDisabled, 286 FallbackStrategy: dns.FallbackStrategy_Enabled, 287 }, 288 }, 289 }) 290 }