aboutsummaryrefslogtreecommitdiff
path: root/middleware/erratic
diff options
context:
space:
mode:
Diffstat (limited to 'middleware/erratic')
-rw-r--r--middleware/erratic/README.md76
-rw-r--r--middleware/erratic/autopath.go8
-rw-r--r--middleware/erratic/erratic.go95
-rw-r--r--middleware/erratic/erratic_test.go79
-rw-r--r--middleware/erratic/setup.go117
-rw-r--r--middleware/erratic/setup_test.go103
6 files changed, 0 insertions, 478 deletions
diff --git a/middleware/erratic/README.md b/middleware/erratic/README.md
deleted file mode 100644
index a84146fbb..000000000
--- a/middleware/erratic/README.md
+++ /dev/null
@@ -1,76 +0,0 @@
-# erratic
-
-*erratic* is a middleware useful for testing client behavior. It returns a static response to all
-queries, but the responses can be delayed, dropped or truncated.
-
-The *erratic* middleware will respond to every A or AAAA query. For any other type it will return
-a SERVFAIL response. The reply for A will return 192.0.2.53 (see RFC 5737), for AAAA it returns
-2001:DB8::53 (see RFC 3849).
-
-*erratic* can also be used in conjunction with the *autopath* middleware. This is mostly to aid in
- testing.
-
-## Syntax
-
-~~~ txt
-erratic {
- drop [AMOUNT]
- truncate [AMOUNT]
- delay [AMOUNT [DURATION]]
-}
-~~~
-
-* `drop`: drop 1 per **AMOUNT** of queries, the default is 2.
-* `truncate`: truncate 1 per **AMOUNT** of queries, the default is 2.
-* `delay`: delay 1 per **AMOUNT** of queries for **DURATION**, the default for **AMOUNT** is 2 and
- the default for **DURATION** is 100ms.
-
-## Examples
-
-~~~ txt
-.:53 {
- erratic {
- drop 3
- }
-}
-~~~
-
-Or even shorter if the defaults suits you. Note this only drops queries, it does not delay them.
-
-~~~ txt
-. {
- erratic
-}
-~~~
-
-Delay 1 in 3 queries for 50ms
-
-~~~ txt
-. {
- erratic {
- delay 3 50ms
- }
-}
-~~~
-
-Delay 1 in 3 and truncate 1 in 5.
-
-~~~ txt
-. {
- erratic {
- delay 3 5ms
- truncate 5
- }
-}
-~~~
-
-Drop every second query.
-
-~~~ txt
-. {
- erratic {
- drop 2
- truncate 2
- }
-}
-~~~
diff --git a/middleware/erratic/autopath.go b/middleware/erratic/autopath.go
deleted file mode 100644
index 79b0ec847..000000000
--- a/middleware/erratic/autopath.go
+++ /dev/null
@@ -1,8 +0,0 @@
-package erratic
-
-import "github.com/coredns/coredns/request"
-
-// AutoPath implements the AutoPathFunc call from the autopath middleware.
-func (e *Erratic) AutoPath(state request.Request) []string {
- return []string{"a.example.org.", "b.example.org.", ""}
-}
diff --git a/middleware/erratic/erratic.go b/middleware/erratic/erratic.go
deleted file mode 100644
index b05e45f03..000000000
--- a/middleware/erratic/erratic.go
+++ /dev/null
@@ -1,95 +0,0 @@
-// Package erratic implements a middleware that returns erratic answers (delayed, dropped).
-package erratic
-
-import (
- "sync/atomic"
- "time"
-
- "github.com/coredns/coredns/request"
-
- "github.com/miekg/dns"
- "golang.org/x/net/context"
-)
-
-// Erratic is a middleware that returns erratic repsonses to each client.
-type Erratic struct {
- drop uint64
-
- delay uint64
- duration time.Duration
-
- truncate uint64
-
- q uint64 // counter of queries
-}
-
-// ServeDNS implements the middleware.Handler interface.
-func (e *Erratic) ServeDNS(ctx context.Context, w dns.ResponseWriter, r *dns.Msg) (int, error) {
- state := request.Request{W: w, Req: r}
- drop := false
- delay := false
- trunc := false
-
- queryNr := atomic.LoadUint64(&e.q)
- atomic.AddUint64(&e.q, 1)
-
- if e.drop > 0 && queryNr%e.drop == 0 {
- drop = true
- }
- if e.delay > 0 && queryNr%e.delay == 0 {
- delay = true
- }
- if e.truncate > 0 && queryNr&e.truncate == 0 {
- trunc = true
- }
-
- m := new(dns.Msg)
- m.SetReply(r)
- m.Compress = true
- m.Authoritative = true
- if trunc {
- m.Truncated = true
- }
-
- // small dance to copy rrA or rrAAAA into a non-pointer var that allows us to overwrite the ownername
- // in a non-racy way.
- switch state.QType() {
- case dns.TypeA:
- rr := *(rrA.(*dns.A))
- rr.Header().Name = state.QName()
- m.Answer = append(m.Answer, &rr)
- case dns.TypeAAAA:
- rr := *(rrAAAA.(*dns.AAAA))
- rr.Header().Name = state.QName()
- m.Answer = append(m.Answer, &rr)
- default:
- if !drop {
- if delay {
- time.Sleep(e.duration)
- }
- // coredns will return error.
- return dns.RcodeServerFailure, nil
- }
- }
-
- if drop {
- return 0, nil
- }
-
- if delay {
- time.Sleep(e.duration)
- }
-
- state.SizeAndDo(m)
- w.WriteMsg(m)
-
- return 0, nil
-}
-
-// Name implements the Handler interface.
-func (e *Erratic) Name() string { return "erratic" }
-
-var (
- rrA, _ = dns.NewRR(". IN 0 A 192.0.2.53")
- rrAAAA, _ = dns.NewRR(". IN 0 AAAA 2001:DB8::53")
-)
diff --git a/middleware/erratic/erratic_test.go b/middleware/erratic/erratic_test.go
deleted file mode 100644
index 4b54e0c12..000000000
--- a/middleware/erratic/erratic_test.go
+++ /dev/null
@@ -1,79 +0,0 @@
-package erratic
-
-import (
- "testing"
-
- "github.com/coredns/coredns/middleware/pkg/dnsrecorder"
- "github.com/coredns/coredns/middleware/test"
-
- "github.com/miekg/dns"
- "golang.org/x/net/context"
-)
-
-func TestErraticDrop(t *testing.T) {
- e := &Erratic{drop: 2} // 50% drops
-
- tests := []struct {
- expectedCode int
- expectedErr error
- drop bool
- }{
- {expectedCode: dns.RcodeSuccess, expectedErr: nil, drop: true},
- {expectedCode: dns.RcodeSuccess, expectedErr: nil, drop: false},
- }
-
- ctx := context.TODO()
-
- for i, tc := range tests {
- req := new(dns.Msg)
- req.SetQuestion("example.org.", dns.TypeA)
-
- rec := dnsrecorder.New(&test.ResponseWriter{})
- code, err := e.ServeDNS(ctx, rec, req)
-
- if err != tc.expectedErr {
- t.Errorf("Test %d: Expected error %q, but got %q", i, tc.expectedErr, err)
- }
- if code != int(tc.expectedCode) {
- t.Errorf("Test %d: Expected status code %d, but got %d", i, tc.expectedCode, code)
- }
-
- if tc.drop && rec.Msg != nil {
- t.Errorf("Test %d: Expected dropped message, but got %q", i, rec.Msg.Question[0].Name)
- }
- }
-}
-
-func TestErraticTruncate(t *testing.T) {
- e := &Erratic{truncate: 2} // 50% drops
-
- tests := []struct {
- expectedCode int
- expectedErr error
- truncate bool
- }{
- {expectedCode: dns.RcodeSuccess, expectedErr: nil, truncate: true},
- {expectedCode: dns.RcodeSuccess, expectedErr: nil, truncate: false},
- }
-
- ctx := context.TODO()
-
- for i, tc := range tests {
- req := new(dns.Msg)
- req.SetQuestion("example.org.", dns.TypeA)
-
- rec := dnsrecorder.New(&test.ResponseWriter{})
- code, err := e.ServeDNS(ctx, rec, req)
-
- if err != tc.expectedErr {
- t.Errorf("Test %d: Expected error %q, but got %q", i, tc.expectedErr, err)
- }
- if code != int(tc.expectedCode) {
- t.Errorf("Test %d: Expected status code %d, but got %d", i, tc.expectedCode, code)
- }
-
- if tc.truncate && !rec.Msg.Truncated {
- t.Errorf("Test %d: Expected truncated message, but got %q", i, rec.Msg.Question[0].Name)
- }
- }
-}
diff --git a/middleware/erratic/setup.go b/middleware/erratic/setup.go
deleted file mode 100644
index 98db02247..000000000
--- a/middleware/erratic/setup.go
+++ /dev/null
@@ -1,117 +0,0 @@
-package erratic
-
-import (
- "fmt"
- "strconv"
- "time"
-
- "github.com/coredns/coredns/core/dnsserver"
- "github.com/coredns/coredns/middleware"
-
- "github.com/mholt/caddy"
-)
-
-func init() {
- caddy.RegisterPlugin("erratic", caddy.Plugin{
- ServerType: "dns",
- Action: setupErratic,
- })
-}
-
-func setupErratic(c *caddy.Controller) error {
- e, err := parseErratic(c)
- if err != nil {
- return middleware.Error("erratic", err)
- }
-
- dnsserver.GetConfig(c).AddMiddleware(func(next middleware.Handler) middleware.Handler {
- return e
- })
-
- return nil
-}
-
-func parseErratic(c *caddy.Controller) (*Erratic, error) {
- e := &Erratic{drop: 2}
- drop := false // true if we've seen the drop keyword
-
- for c.Next() { // 'erratic'
- for c.NextBlock() {
- switch c.Val() {
- case "drop":
- args := c.RemainingArgs()
- if len(args) > 1 {
- return nil, c.ArgErr()
- }
-
- if len(args) == 0 {
- continue
- }
-
- amount, err := strconv.ParseInt(args[0], 10, 32)
- if err != nil {
- return nil, err
- }
- if amount < 0 {
- return nil, fmt.Errorf("illegal amount value given %q", args[0])
- }
- e.drop = uint64(amount)
- drop = true
- case "delay":
- args := c.RemainingArgs()
- if len(args) > 2 {
- return nil, c.ArgErr()
- }
-
- // Defaults.
- e.delay = 2
- e.duration = 100 * time.Millisecond
- if len(args) == 0 {
- continue
- }
-
- amount, err := strconv.ParseInt(args[0], 10, 32)
- if err != nil {
- return nil, err
- }
- if amount < 0 {
- return nil, fmt.Errorf("illegal amount value given %q", args[0])
- }
- e.delay = uint64(amount)
-
- if len(args) > 1 {
- duration, err := time.ParseDuration(args[1])
- if err != nil {
- return nil, err
- }
- e.duration = duration
- }
- case "truncate":
- args := c.RemainingArgs()
- if len(args) > 1 {
- return nil, c.ArgErr()
- }
-
- if len(args) == 0 {
- continue
- }
-
- amount, err := strconv.ParseInt(args[0], 10, 32)
- if err != nil {
- return nil, err
- }
- if amount < 0 {
- return nil, fmt.Errorf("illegal amount value given %q", args[0])
- }
- e.truncate = uint64(amount)
- default:
- return nil, c.Errf("unknown property '%s'", c.Val())
- }
- }
- }
- if (e.delay > 0 || e.truncate > 0) && !drop { // delay is set, but we've haven't seen a drop keyword, remove default drop stuff
- e.drop = 0
- }
-
- return e, nil
-}
diff --git a/middleware/erratic/setup_test.go b/middleware/erratic/setup_test.go
deleted file mode 100644
index 759845f7a..000000000
--- a/middleware/erratic/setup_test.go
+++ /dev/null
@@ -1,103 +0,0 @@
-package erratic
-
-import (
- "testing"
-
- "github.com/mholt/caddy"
-)
-
-func TestSetupErratic(t *testing.T) {
- c := caddy.NewTestController("dns", `erratic {
- drop
- }`)
- if err := setupErratic(c); err != nil {
- t.Fatalf("Test 1, expected no errors, but got: %q", err)
- }
-
- c = caddy.NewTestController("dns", `erratic`)
- if err := setupErratic(c); err != nil {
- t.Fatalf("Test 2, expected no errors, but got: %q", err)
- }
-
- c = caddy.NewTestController("dns", `erratic {
- drop -1
- }`)
- if err := setupErratic(c); err == nil {
- t.Fatalf("Test 4, expected errors, but got: %q", err)
- }
-}
-
-func TestParseErratic(t *testing.T) {
- tests := []struct {
- input string
- shouldErr bool
- drop uint64
- delay uint64
- truncate uint64
- }{
- // oks
- {`erratic`, false, 2, 0, 0},
- {`erratic {
- drop 2
- delay 3 1ms
-
- }`, false, 2, 3, 0},
- {`erratic {
- truncate 2
- delay 3 1ms
-
- }`, false, 0, 3, 2},
- {`erraric {
- drop 3
- delay
- }`, false, 3, 2, 0},
- // fails
- {`erratic {
- drop -1
- }`, true, 0, 0, 0},
- {`erratic {
- delay -1
- }`, true, 0, 0, 0},
- {`erratic {
- delay 1 2 4
- }`, true, 0, 0, 0},
- {`erratic {
- delay 15.a
- }`, true, 0, 0, 0},
- {`erraric {
- drop 3
- delay 3 bla
- }`, true, 0, 0, 0},
- {`erraric {
- truncate 15.a
- }`, true, 0, 0, 0},
- {`erraric {
- something-else
- }`, true, 0, 0, 0},
- }
- for i, test := range tests {
- c := caddy.NewTestController("dns", test.input)
- e, err := parseErratic(c)
- if test.shouldErr && err == nil {
- t.Errorf("Test %v: Expected error but found nil", i)
- continue
- } else if !test.shouldErr && err != nil {
- t.Errorf("Test %v: Expected no error but found error: %v", i, err)
- continue
- }
-
- if test.shouldErr {
- continue
- }
-
- if test.delay != e.delay {
- t.Errorf("Test %v: Expected delay %d but found: %d", i, test.delay, e.delay)
- }
- if test.drop != e.drop {
- t.Errorf("Test %v: Expected drop %d but found: %d", i, test.drop, e.drop)
- }
- if test.truncate != e.truncate {
- t.Errorf("Test %v: Expected truncate %d but found: %d", i, test.truncate, e.truncate)
- }
- }
-}