grpc/grpc-go · error

dns: error parsing A record IP address %v: %v

Error message

dns: error parsing A record IP address %v: %v

What it means

Returned by lookupSRV when, after fetching SRV records and resolving each SRV target's A records, formatIP(a) fails for one of the returned addresses. formatIP uses netip.ParseAddr, so this fires when an A-record value is not a parseable IP literal (e.g. a CNAME string leaked through, or a malformed record).

Source

Thrown at internal/resolver/dns/dns_resolver.go:269

	if err != nil {
		err = handleDNSError(err, "SRV") // may become nil
		return nil, err
	}
	for _, s := range srvs {
		lbAddrs, err := d.resolver.LookupHost(ctx, s.Target)
		if err != nil {
			err = handleDNSError(err, "A") // may become nil
			if err == nil {
				// If there are other SRV records, look them up and ignore this
				// one that does not exist.
				continue
			}
			return nil, err
		}
		for _, a := range lbAddrs {
			ip, err := formatIP(a)
			if err != nil {
				return nil, fmt.Errorf("dns: error parsing A record IP address %v: %v", a, err)
			}
			addr := ip + ":" + strconv.Itoa(int(s.Port))
			newAddrs = append(newAddrs, resolver.Address{Addr: addr, ServerName: s.Target})
		}
	}
	return newAddrs, nil
}

func handleDNSError(err error, lookupType string) error {
	dnsErr, ok := err.(*net.DNSError)
	if ok && !dnsErr.IsTimeout && !dnsErr.IsTemporary {
		// Timeouts and temporary errors should be communicated to gRPC to
		// attempt another DNS query (with backoff).  Other errors should be
		// suppressed (they may represent the absence of a TXT record).
		return nil
	}
	if err != nil {
		err = fmt.Errorf("dns: %v record lookup error: %v", lookupType, err)

View on GitHub (pinned to 03255a9237)

Solutions

  1. If you do not use grpclb, leave EnableSRVLookups = false (the default) so SRV resolution is skipped.
  2. Fix the upstream DNS so SRV targets resolve to valid IP A records.
  3. Validate SRV records with dig/nslookup to find the malformed target.

Example fix

// before
grpc.EnableSRVLookups = true // triggers SRV+A resolution
// after (if grpclb is not used)
grpc.EnableSRVLookups = false
Defensive patterns

Strategy: validation

Validate before calling

// Keep SRV lookups off unless grpclb is in use.
if !usingGrpcLB {
    grpc.EnableSRVLookups = false
}

Try / catch

// Surfaced as a resolver error; the dns resolver backs off and retries.
// To eliminate it entirely, disable SRV lookups or fix upstream DNS.

Prevention

When it happens

Trigger: An SRV record points at a target whose LookupHost returns a non-IP string; a misbehaving DNS server returning names instead of addresses in the A lookup; EnableSRVLookups is true and grpclb SRV records reference bad targets.

Common situations: Self-hosted DNS that returns inconsistent A records; legacy grpclb configuration pointing at hostnames inside the SRV chain; DNS poisoning or split-horizon DNS returning text.

Related errors


AI-assisted analysis of grpc/grpc-go@03255a9237 (2026-08-07). Data as JSON: /api/errors/289e261ba3ea33f8. Report an issue: GitHub.