dns: add endpoint for querying service virtual IPs
This commit is contained in:
parent
dbb58b726a
commit
a0ea359147
|
@ -0,0 +1,3 @@
|
||||||
|
```release-note:improvement
|
||||||
|
dns: Added a `virtual` endpoint for querying the assigned virtual IP for a service.
|
||||||
|
```
|
37
agent/dns.go
37
agent/dns.go
|
@ -695,7 +695,7 @@ func (d *DNSServer) dispatch(remoteAddr net.Addr, req, resp *dns.Msg, maxRecursi
|
||||||
done := false
|
done := false
|
||||||
for i := len(labels) - 1; i >= 0 && !done; i-- {
|
for i := len(labels) - 1; i >= 0 && !done; i-- {
|
||||||
switch labels[i] {
|
switch labels[i] {
|
||||||
case "service", "connect", "ingress", "node", "query", "addr":
|
case "service", "connect", "virtual", "ingress", "node", "query", "addr":
|
||||||
queryParts = labels[:i]
|
queryParts = labels[:i]
|
||||||
querySuffixes = labels[i+1:]
|
querySuffixes = labels[i+1:]
|
||||||
queryKind = labels[i]
|
queryKind = labels[i]
|
||||||
|
@ -785,6 +785,41 @@ func (d *DNSServer) dispatch(remoteAddr net.Addr, req, resp *dns.Msg, maxRecursi
|
||||||
// name.connect.consul
|
// name.connect.consul
|
||||||
return d.serviceLookup(cfg, lookup, req, resp)
|
return d.serviceLookup(cfg, lookup, req, resp)
|
||||||
|
|
||||||
|
case "virtual":
|
||||||
|
if len(queryParts) < 1 {
|
||||||
|
return invalid()
|
||||||
|
}
|
||||||
|
|
||||||
|
if !d.parseDatacenterAndEnterpriseMeta(querySuffixes, cfg, &datacenter, &entMeta) {
|
||||||
|
return invalid()
|
||||||
|
}
|
||||||
|
|
||||||
|
args := structs.ServiceSpecificRequest{
|
||||||
|
Datacenter: datacenter,
|
||||||
|
ServiceName: queryParts[len(queryParts)-1],
|
||||||
|
EnterpriseMeta: entMeta,
|
||||||
|
QueryOptions: structs.QueryOptions{
|
||||||
|
Token: d.agent.tokens.UserToken(),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
var out string
|
||||||
|
if err := d.agent.RPC("Catalog.VirtualIPForService", &args, &out); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if out != "" {
|
||||||
|
resp.Answer = append(resp.Answer, &dns.A{
|
||||||
|
Hdr: dns.RR_Header{
|
||||||
|
Name: qName + respDomain,
|
||||||
|
Rrtype: dns.TypeA,
|
||||||
|
Class: dns.ClassINET,
|
||||||
|
Ttl: uint32(cfg.NodeTTL / time.Second),
|
||||||
|
},
|
||||||
|
A: net.ParseIP(out),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
|
||||||
case "ingress":
|
case "ingress":
|
||||||
if len(queryParts) < 1 {
|
if len(queryParts) < 1 {
|
||||||
return invalid()
|
return invalid()
|
||||||
|
|
|
@ -1756,6 +1756,24 @@ func TestDNS_ConnectServiceLookup(t *testing.T) {
|
||||||
require.Equal(t, uint32(0), srvRec.Hdr.Ttl)
|
require.Equal(t, uint32(0), srvRec.Hdr.Ttl)
|
||||||
require.Equal(t, "127.0.0.55", cnameRec.A.String())
|
require.Equal(t, "127.0.0.55", cnameRec.A.String())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Look up the virtual IP of the proxy.
|
||||||
|
questions = []string{
|
||||||
|
"db.virtual.consul.",
|
||||||
|
}
|
||||||
|
for _, question := range questions {
|
||||||
|
m := new(dns.Msg)
|
||||||
|
m.SetQuestion(question, dns.TypeA)
|
||||||
|
|
||||||
|
c := new(dns.Client)
|
||||||
|
in, _, err := c.Exchange(m, a.DNSAddr())
|
||||||
|
require.Nil(t, err)
|
||||||
|
require.Len(t, in.Answer, 1)
|
||||||
|
|
||||||
|
aRec, ok := in.Answer[0].(*dns.A)
|
||||||
|
require.True(t, ok)
|
||||||
|
require.Equal(t, "240.0.0.1", aRec.A.String())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestDNS_IngressServiceLookup(t *testing.T) {
|
func TestDNS_IngressServiceLookup(t *testing.T) {
|
||||||
|
|
Loading…
Reference in New Issue