mirror of
https://github.com/coredns/coredns.git
synced 2025-10-26 15:54:16 -04:00
205 lines
6.2 KiB
Go
205 lines
6.2 KiB
Go
package nomad
|
|
|
|
import (
|
|
"context"
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"testing"
|
|
|
|
"github.com/coredns/coredns/plugin/pkg/dnstest"
|
|
"github.com/coredns/coredns/plugin/test"
|
|
|
|
nomad "github.com/hashicorp/nomad/api"
|
|
"github.com/miekg/dns"
|
|
)
|
|
|
|
func TestNomad(t *testing.T) {
|
|
var demoNomad = Nomad{
|
|
Next: test.ErrorHandler(),
|
|
ttl: uint32(defaultTTL),
|
|
Zone: "service.nomad",
|
|
clients: make([]*nomad.Client, 0),
|
|
}
|
|
|
|
var cases = []test.Case{
|
|
{
|
|
Qname: "example.default.service.nomad.",
|
|
Qtype: dns.TypeA,
|
|
Rcode: dns.RcodeSuccess,
|
|
Answer: []dns.RR{
|
|
test.A("example.default.service.nomad. 30 IN A 1.2.3.4"),
|
|
},
|
|
},
|
|
{
|
|
Qname: "example.default.service.nomad.",
|
|
Qtype: dns.TypeAAAA,
|
|
Rcode: dns.RcodeSuccess,
|
|
Answer: []dns.RR{},
|
|
},
|
|
{
|
|
Qname: "fakeipv6.default.service.nomad.",
|
|
Qtype: dns.TypeAAAA,
|
|
Rcode: dns.RcodeSuccess,
|
|
Answer: []dns.RR{
|
|
test.AAAA("fakeipv6.default.service.nomad. 30 IN AAAA 1:2:3::4"),
|
|
},
|
|
},
|
|
{
|
|
Qname: "fakeipv6.default.service.nomad.",
|
|
Qtype: dns.TypeA,
|
|
Rcode: dns.RcodeSuccess,
|
|
Answer: []dns.RR{},
|
|
},
|
|
{
|
|
Qname: "multi.default.service.nomad.",
|
|
Qtype: dns.TypeA,
|
|
Rcode: dns.RcodeSuccess,
|
|
Answer: []dns.RR{
|
|
test.A("multi.default.service.nomad. 30 IN A 1.2.3.4"),
|
|
test.A("multi.default.service.nomad. 30 IN A 1.2.3.5"),
|
|
test.A("multi.default.service.nomad. 30 IN A 1.2.3.6"),
|
|
},
|
|
},
|
|
{
|
|
Qname: "nonexistent.default.service.nomad.",
|
|
Qtype: dns.TypeA,
|
|
Rcode: dns.RcodeNameError,
|
|
Answer: []dns.RR{
|
|
test.SOA("nonexistent.default.service.nomad. 30 IN SOA ns1.nonexistent.default.service.nomad. hostmaster.service.nomad. 0 3600 600 86400 30"),
|
|
},
|
|
},
|
|
{
|
|
Qname: "example.default.service.nomad.",
|
|
Qtype: dns.TypeSRV,
|
|
Rcode: dns.RcodeSuccess,
|
|
Answer: []dns.RR{test.SRV("example.default.service.nomad. 30 IN SRV 10 10 23202 example.default.service.nomad.")},
|
|
Extra: []dns.RR{test.A("example.default.service.nomad. 30 IN A 1.2.3.4")},
|
|
},
|
|
}
|
|
|
|
ctx := context.Background()
|
|
|
|
// Setup a fake Nomad servers.
|
|
nomadServer1 := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
switch r.URL.Path {
|
|
case "/v1/service/example":
|
|
w.Write([]byte(`[{"Address":"1.2.3.4","Namespace":"default","Port":23202,"ServiceName":"example"}]`))
|
|
case "/v1/service/fakeipv6":
|
|
w.Write([]byte(`[{"Address":"1:2:3::4","Namespace":"default","Port":8000,"ServiceName":"fakeipv6"}]`))
|
|
case "/v1/service/multi":
|
|
w.Write([]byte(`[{"Address":"1.2.3.4","Namespace":"default","Port":25395,"ServiceName":"multi"},{"Address":"1.2.3.5","Namespace":"default","Port":20888,"ServiceName":"multi"},{"Address":"1.2.3.6","Namespace":"default","Port":26292,"ServiceName":"multi"}]`))
|
|
case "/v1/service/nonexistent":
|
|
w.Write([]byte(`[]`))
|
|
case "/v1/agent/self":
|
|
w.Write([]byte(`{"Member":{"Name":"foobar1"}}`))
|
|
}
|
|
}))
|
|
defer nomadServer1.Close()
|
|
nomadServer2 := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
switch r.URL.Path {
|
|
case "/v1/service/example":
|
|
w.Write([]byte(`[{"Address":"1.2.3.4","Namespace":"default","Port":23202,"ServiceName":"example"}]`))
|
|
case "/v1/service/fakeipv6":
|
|
w.Write([]byte(`[{"Address":"1:2:3::4","Namespace":"default","Port":8000,"ServiceName":"fakeipv6"}]`))
|
|
case "/v1/service/multi":
|
|
w.Write([]byte(`[{"Address":"1.2.3.4","Namespace":"default","Port":25395,"ServiceName":"multi"},{"Address":"1.2.3.5","Namespace":"default","Port":20888,"ServiceName":"multi"},{"Address":"1.2.3.6","Namespace":"default","Port":26292,"ServiceName":"multi"}]`))
|
|
case "/v1/service/nonexistent":
|
|
w.Write([]byte(`[]`))
|
|
case "/v1/agent/self":
|
|
w.Write([]byte(`{"Member":{"Name":"foobar2"}}`))
|
|
}
|
|
}))
|
|
defer nomadServer2.Close()
|
|
nomadServer3 := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
switch r.URL.Path {
|
|
case "/v1/service/example":
|
|
w.Write([]byte(`[{"Address":"1.2.3.4","Namespace":"default","Port":23202,"ServiceName":"example"}]`))
|
|
case "/v1/service/fakeipv6":
|
|
w.Write([]byte(`[{"Address":"1:2:3::4","Namespace":"default","Port":8000,"ServiceName":"fakeipv6"}]`))
|
|
case "/v1/service/multi":
|
|
w.Write([]byte(`[{"Address":"1.2.3.4","Namespace":"default","Port":25395,"ServiceName":"multi"},{"Address":"1.2.3.5","Namespace":"default","Port":20888,"ServiceName":"multi"},{"Address":"1.2.3.6","Namespace":"default","Port":26292,"ServiceName":"multi"}]`))
|
|
case "/v1/service/nonexistent":
|
|
w.Write([]byte(`[]`))
|
|
case "/v1/agent/self":
|
|
w.Write([]byte(`{"Member":{"Name":"foobar3"}}`))
|
|
}
|
|
}))
|
|
defer nomadServer3.Close()
|
|
|
|
// Configure the plugin to use the fake Nomad server.
|
|
cfg := nomad.DefaultConfig()
|
|
cfg.Address = nomadServer1.URL
|
|
client1, err := nomad.NewClient(cfg)
|
|
if err != nil {
|
|
t.Errorf("Failed to create Nomad client: %v", err)
|
|
return
|
|
}
|
|
|
|
demoNomad.clients = append(demoNomad.clients, client1)
|
|
|
|
cfg = nomad.DefaultConfig()
|
|
cfg.Address = nomadServer2.URL
|
|
client2, err := nomad.NewClient(cfg)
|
|
if err != nil {
|
|
t.Errorf("Failed to create Nomad client: %v", err)
|
|
return
|
|
}
|
|
|
|
demoNomad.clients = append(demoNomad.clients, client2)
|
|
|
|
cfg = nomad.DefaultConfig()
|
|
cfg.Address = nomadServer3.URL
|
|
client3, err := nomad.NewClient(cfg)
|
|
if err != nil {
|
|
t.Errorf("Failed to create Nomad client: %v", err)
|
|
return
|
|
}
|
|
demoNomad.clients = append(demoNomad.clients, client3)
|
|
|
|
client, _ := demoNomad.getClient()
|
|
if client != client1 {
|
|
t.Errorf("Expected client1")
|
|
}
|
|
|
|
nomadServer1.Close()
|
|
|
|
client, _ = demoNomad.getClient()
|
|
if client == client1 {
|
|
t.Errorf("Expected client2")
|
|
}
|
|
|
|
client, err = demoNomad.getClient()
|
|
if err != nil {
|
|
t.Errorf("Expected no error, but got %v", err)
|
|
}
|
|
if client == nil {
|
|
t.Errorf("Expected client2 but got nil")
|
|
}
|
|
if client != client2 {
|
|
t.Errorf("Expected client2")
|
|
}
|
|
|
|
runTests(ctx, t, &demoNomad, cases)
|
|
}
|
|
|
|
func runTests(ctx context.Context, t *testing.T, n *Nomad, cases []test.Case) {
|
|
t.Helper()
|
|
for i, tc := range cases {
|
|
r := tc.Msg()
|
|
w := dnstest.NewRecorder(&test.ResponseWriter{})
|
|
|
|
_, err := n.ServeDNS(ctx, w, r)
|
|
if err != tc.Error {
|
|
t.Errorf("Test %d: %v (%v) (%v)", i, err, w, r)
|
|
return
|
|
}
|
|
|
|
if w.Msg == nil {
|
|
t.Errorf("Test %d: nil message", i)
|
|
}
|
|
if err := test.SortAndCheck(w.Msg, tc); err != nil {
|
|
t.Errorf("Test %d: %v", i, err)
|
|
}
|
|
}
|
|
}
|