{"record":{"id":"5d99397e96f542e6","repo":"thanos-io/thanos","slug":"unsupported-network-q","errorCode":null,"errorMessage":"unsupported network %q","messagePattern":"unsupported network %q","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/discovery/dns/miekgdns/resolver.go","lineNumber":79,"sourceCode":"\t\t}\n\t}\n\n\treturn \"\", addrs, nil\n}\n\nfunc (r *Resolver) LookupIPAddr(_ context.Context, host string) ([]net.IPAddr, error) {\n\treturn r.lookupIPAddr(host, 1, 8)\n}\n\nfunc (r *Resolver) LookupIPAddrByNetwork(ctx context.Context, network, host string) ([]net.IPAddr, error) {\n\tvar qtype dns.Type\n\tswitch network {\n\tcase \"ip6\":\n\t\tqtype = dns.Type(dns.TypeAAAA)\n\tcase \"ip4\":\n\t\tqtype = dns.Type(dns.TypeA)\n\tdefault:\n\t\treturn nil, errors.Errorf(\"unsupported network %q\", network)\n\t}\n\treturn r.lookupIPAddrByNetwork(ctx, host, qtype, 1, 8)\n}\n\nfunc (r *Resolver) lookupIPAddrByNetwork(ctx context.Context, host string, qtype dns.Type, currIteration, maxIterations int) ([]net.IPAddr, error) {\n\tif currIteration > maxIterations {\n\t\treturn nil, errors.Errorf(\"maximum number of recursive iterations reached (%d)\", maxIterations)\n\t}\n\n\tselect {\n\tcase <-ctx.Done():\n\t\treturn nil, ctx.Err()\n\tdefault:\n\t}\n\n\tresponse, err := r.lookupWithSearchPath(host, qtype)\n\tif err != nil {\n\t\treturn nil, err","sourceCodeStart":61,"sourceCodeEnd":97,"githubUrl":"https://github.com/thanos-io/thanos/blob/35b8b991177def87ed52dcf10f9b6d87f07282c8/pkg/discovery/dns/miekgdns/resolver.go#L61-L97","documentation":"LookupIPAddrByNetwork only accepts the network selectors \"ip4\" (A records) and \"ip6\" (AAAA records). Any other value fails the switch before any DNS query is made and is rejected with this error, so no lookup is attempted.","triggerScenarios":"Calling Resolver.LookupIPAddrByNetwork(ctx, network, host) with a network string other than exactly \"ip4\" or \"ip6\" — e.g. \"ip\", \"tcp\", \"ipv4\", \"IP4\", or an empty string. Within this repo, dns.Resolve with qtype dnsdualstack always passes valid values, so the error comes from direct callers.","commonSituations":"Hand-written dual-stack discovery code passing net.Dial-style network strings like \"tcp4\"/\"udp\"; case-mismatched literals like \"IP4\"; variables derived from config flags holding empty or mistyped network names.","solutions":["Pass exactly \"ip4\" or \"ip6\" as the network argument","Normalize/validate the network string before the call (trim, lowercase, map aliases like ipv4->ip4)","If you need plain A/AAAA lookup without network selection, use LookupIPAddr instead","For dual-stack resolution via config, use the dns.Resolve API with qtype dnsdualstack, which handles both networks"],"exampleFix":"// before\naddrs, err := r.LookupIPAddrByNetwork(ctx, \"tcp4\", \"example.com\")\n// after\naddrs, err := r.LookupIPAddrByNetwork(ctx, \"ip4\", \"example.com\")","handlingStrategy":"validation","validationCode":"func validNetwork(n string) bool { return n == \"ip4\" || n == \"ip6\" }\nif !validNetwork(network) { return nil, fmt.Errorf(\"network must be ip4 or ip6, got %q\", network) }","typeGuard":"func isDNSNetwork(s string) bool { return s == \"ip4\" || s == \"ip6\" }","tryCatchPattern":"addrs, err := r.LookupIPAddrByNetwork(ctx, network, host)\nif err != nil {\n    if strings.Contains(err.Error(), \"unsupported network\") {\n        // fix the network value or fall back\n    }\n    return err\n}","preventionTips":["Only ever pass the literals \"ip4\" or \"ip6\"","Do not reuse net.Dial network strings (\"tcp4\", \"udp\") for this API","Centralize dual-stack lookup in one helper that validates the network value","Prefer dns.Resolve with dnsdualstack qtype instead of calling this directly"],"tags":["dns","go","invalid-argument","network"],"backgroundTag":"invalid-enum-value","analyzedSha":"35b8b991177def87ed52dcf10f9b6d87f07282c8","analyzedAt":"2026-09-07T01:49:59.689Z","contentChangedAt":"2026-09-07T01:49:59.689Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}