agent: convert all intention tests to testify/assert

pull/4275/head
Mitchell Hashimoto 2018-03-06 10:35:20 -08:00
parent 454ef7d106
commit 0719ff6905
No known key found for this signature in database
GPG Key ID: 744E147AA52F5B0A
6 changed files with 218 additions and 491 deletions

View File

@ -15,6 +15,7 @@ import (
"github.com/hashicorp/go-uuid" "github.com/hashicorp/go-uuid"
"github.com/hashicorp/serf/coordinate" "github.com/hashicorp/serf/coordinate"
"github.com/pascaldekloe/goe/verify" "github.com/pascaldekloe/goe/verify"
"github.com/stretchr/testify/assert"
) )
func generateUUID() (ret string) { func generateUUID() (ret string) {
@ -1152,10 +1153,9 @@ func TestFSM_Autopilot(t *testing.T) {
func TestFSM_Intention_CRUD(t *testing.T) { func TestFSM_Intention_CRUD(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
fsm, err := New(nil, os.Stderr) fsm, err := New(nil, os.Stderr)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err)
}
// Create a new intention. // Create a new intention.
ixn := structs.IntentionRequest{ ixn := structs.IntentionRequest{
@ -1167,28 +1167,19 @@ func TestFSM_Intention_CRUD(t *testing.T) {
{ {
buf, err := structs.Encode(structs.IntentionRequestType, ixn) buf, err := structs.Encode(structs.IntentionRequestType, ixn)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err) assert.Nil(fsm.Apply(makeLog(buf)))
}
resp := fsm.Apply(makeLog(buf))
if resp != nil {
t.Fatalf("resp: %v", resp)
}
} }
// Verify it's in the state store. // Verify it's in the state store.
{ {
_, actual, err := fsm.state.IntentionGet(nil, ixn.Intention.ID) _, actual, err := fsm.state.IntentionGet(nil, ixn.Intention.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err)
}
actual.CreateIndex, actual.ModifyIndex = 0, 0 actual.CreateIndex, actual.ModifyIndex = 0, 0
actual.CreatedAt = ixn.Intention.CreatedAt actual.CreatedAt = ixn.Intention.CreatedAt
actual.UpdatedAt = ixn.Intention.UpdatedAt actual.UpdatedAt = ixn.Intention.UpdatedAt
if !reflect.DeepEqual(actual, ixn.Intention) { assert.Equal(ixn.Intention, actual)
t.Fatalf("bad: %v", actual)
}
} }
// Make an update // Make an update
@ -1196,52 +1187,33 @@ func TestFSM_Intention_CRUD(t *testing.T) {
ixn.Intention.SourceName = "api" ixn.Intention.SourceName = "api"
{ {
buf, err := structs.Encode(structs.IntentionRequestType, ixn) buf, err := structs.Encode(structs.IntentionRequestType, ixn)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err) assert.Nil(fsm.Apply(makeLog(buf)))
}
resp := fsm.Apply(makeLog(buf))
if resp != nil {
t.Fatalf("resp: %v", resp)
}
} }
// Verify the update. // Verify the update.
{ {
_, actual, err := fsm.state.IntentionGet(nil, ixn.Intention.ID) _, actual, err := fsm.state.IntentionGet(nil, ixn.Intention.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err)
}
actual.CreateIndex, actual.ModifyIndex = 0, 0 actual.CreateIndex, actual.ModifyIndex = 0, 0
actual.CreatedAt = ixn.Intention.CreatedAt actual.CreatedAt = ixn.Intention.CreatedAt
actual.UpdatedAt = ixn.Intention.UpdatedAt actual.UpdatedAt = ixn.Intention.UpdatedAt
if !reflect.DeepEqual(actual, ixn.Intention) { assert.Equal(ixn.Intention, actual)
t.Fatalf("bad: %v", actual)
}
} }
// Delete // Delete
ixn.Op = structs.IntentionOpDelete ixn.Op = structs.IntentionOpDelete
{ {
buf, err := structs.Encode(structs.IntentionRequestType, ixn) buf, err := structs.Encode(structs.IntentionRequestType, ixn)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err) assert.Nil(fsm.Apply(makeLog(buf)))
}
resp := fsm.Apply(makeLog(buf))
if resp != nil {
t.Fatalf("resp: %v", resp)
}
} }
// Make sure it's gone. // Make sure it's gone.
{ {
_, actual, err := fsm.state.IntentionGet(nil, ixn.Intention.ID) _, actual, err := fsm.state.IntentionGet(nil, ixn.Intention.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Nil(actual)
}
if actual != nil {
t.Fatalf("bad: %v", actual)
}
} }
} }

View File

@ -13,10 +13,13 @@ import (
"github.com/hashicorp/consul/api" "github.com/hashicorp/consul/api"
"github.com/hashicorp/consul/lib" "github.com/hashicorp/consul/lib"
"github.com/pascaldekloe/goe/verify" "github.com/pascaldekloe/goe/verify"
"github.com/stretchr/testify/assert"
) )
func TestFSM_SnapshotRestore_OSS(t *testing.T) { func TestFSM_SnapshotRestore_OSS(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
fsm, err := New(nil, os.Stderr) fsm, err := New(nil, os.Stderr)
if err != nil { if err != nil {
t.Fatalf("err: %v", err) t.Fatalf("err: %v", err)
@ -105,9 +108,7 @@ func TestFSM_SnapshotRestore_OSS(t *testing.T) {
CreateIndex: 14, CreateIndex: 14,
ModifyIndex: 14, ModifyIndex: 14,
} }
if err := fsm.state.IntentionSet(14, ixn); err != nil { assert.Nil(fsm.state.IntentionSet(14, ixn))
t.Fatalf("err: %s", err)
}
// Snapshot // Snapshot
snap, err := fsm.Snapshot() snap, err := fsm.Snapshot()
@ -273,15 +274,9 @@ func TestFSM_SnapshotRestore_OSS(t *testing.T) {
// Verify intentions are restored. // Verify intentions are restored.
_, ixns, err := fsm2.state.Intentions(nil) _, ixns, err := fsm2.state.Intentions(nil)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Len(ixns, 1)
} assert.Equal(ixn, ixns[0])
if len(ixns) != 1 {
t.Fatalf("bad: %#v", ixns)
}
if !reflect.DeepEqual(ixns[0], ixn) {
t.Fatalf("bad: %#v", ixns[0])
}
// Snapshot // Snapshot
snap, err = fsm2.Snapshot() snap, err = fsm2.Snapshot()

View File

@ -2,19 +2,20 @@ package consul
import ( import (
"os" "os"
"reflect"
"strings"
"testing" "testing"
"time" "time"
"github.com/hashicorp/consul/agent/structs" "github.com/hashicorp/consul/agent/structs"
"github.com/hashicorp/consul/testrpc" "github.com/hashicorp/consul/testrpc"
"github.com/hashicorp/net-rpc-msgpackrpc" "github.com/hashicorp/net-rpc-msgpackrpc"
"github.com/stretchr/testify/assert"
) )
// Test basic creation // Test basic creation
func TestIntentionApply_new(t *testing.T) { func TestIntentionApply_new(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -43,12 +44,8 @@ func TestIntentionApply_new(t *testing.T) {
now := time.Now() now := time.Now()
// Create // Create
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err) assert.NotEmpty(reply)
}
if reply == "" {
t.Fatal("reply should be non-empty")
}
// Read // Read
ixn.Intention.ID = reply ixn.Intention.ID = reply
@ -58,45 +55,25 @@ func TestIntentionApply_new(t *testing.T) {
IntentionID: ixn.Intention.ID, IntentionID: ixn.Intention.ID,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
if resp.Index != actual.ModifyIndex { assert.Equal(resp.Index, actual.ModifyIndex)
t.Fatalf("bad index: %d", resp.Index) assert.WithinDuration(now, actual.CreatedAt, 5*time.Second)
} assert.WithinDuration(now, actual.UpdatedAt, 5*time.Second)
// Test CreatedAt
{
timeDiff := actual.CreatedAt.Sub(now)
if timeDiff < 0 || timeDiff > 5*time.Second {
t.Fatalf("should set created at: %s", actual.CreatedAt)
}
}
// Test UpdatedAt
{
timeDiff := actual.UpdatedAt.Sub(now)
if timeDiff < 0 || timeDiff > 5*time.Second {
t.Fatalf("should set updated at: %s", actual.CreatedAt)
}
}
actual.CreateIndex, actual.ModifyIndex = 0, 0 actual.CreateIndex, actual.ModifyIndex = 0, 0
actual.CreatedAt = ixn.Intention.CreatedAt actual.CreatedAt = ixn.Intention.CreatedAt
actual.UpdatedAt = ixn.Intention.UpdatedAt actual.UpdatedAt = ixn.Intention.UpdatedAt
if !reflect.DeepEqual(actual, ixn.Intention) { assert.Equal(ixn.Intention, actual)
t.Fatalf("bad:\n\n%#v\n\n%#v", actual, ixn.Intention)
}
} }
} }
// Test the source type defaults // Test the source type defaults
func TestIntentionApply_defaultSourceType(t *testing.T) { func TestIntentionApply_defaultSourceType(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -120,12 +97,8 @@ func TestIntentionApply_defaultSourceType(t *testing.T) {
var reply string var reply string
// Create // Create
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err) assert.NotEmpty(reply)
}
if reply == "" {
t.Fatal("reply should be non-empty")
}
// Read // Read
ixn.Intention.ID = reply ixn.Intention.ID = reply
@ -135,23 +108,18 @@ func TestIntentionApply_defaultSourceType(t *testing.T) {
IntentionID: ixn.Intention.ID, IntentionID: ixn.Intention.ID,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
if actual.SourceType != structs.IntentionSourceConsul { assert.Equal(structs.IntentionSourceConsul, actual.SourceType)
t.Fatalf("bad:\n\n%#v\n\n%#v", actual, ixn.Intention)
}
} }
} }
// Shouldn't be able to create with an ID set // Shouldn't be able to create with an ID set
func TestIntentionApply_createWithID(t *testing.T) { func TestIntentionApply_createWithID(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -173,14 +141,15 @@ func TestIntentionApply_createWithID(t *testing.T) {
// Create // Create
err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply) err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply)
if err == nil || !strings.Contains(err.Error(), "ID must be empty") { assert.NotNil(err)
t.Fatalf("bad: %v", err) assert.Contains(err, "ID must be empty")
}
} }
// Test basic updating // Test basic updating
func TestIntentionApply_updateGood(t *testing.T) { func TestIntentionApply_updateGood(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -206,12 +175,8 @@ func TestIntentionApply_updateGood(t *testing.T) {
var reply string var reply string
// Create // Create
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err) assert.NotEmpty(reply)
}
if reply == "" {
t.Fatal("reply should be non-empty")
}
// Read CreatedAt // Read CreatedAt
var createdAt time.Time var createdAt time.Time
@ -222,12 +187,8 @@ func TestIntentionApply_updateGood(t *testing.T) {
IntentionID: ixn.Intention.ID, IntentionID: ixn.Intention.ID,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
createdAt = actual.CreatedAt createdAt = actual.CreatedAt
} }
@ -239,9 +200,7 @@ func TestIntentionApply_updateGood(t *testing.T) {
ixn.Op = structs.IntentionOpUpdate ixn.Op = structs.IntentionOpUpdate
ixn.Intention.ID = reply ixn.Intention.ID = reply
ixn.Intention.SourceName = "bar" ixn.Intention.SourceName = "bar"
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err)
}
// Read // Read
ixn.Intention.ID = reply ixn.Intention.ID = reply
@ -251,39 +210,24 @@ func TestIntentionApply_updateGood(t *testing.T) {
IntentionID: ixn.Intention.ID, IntentionID: ixn.Intention.ID,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
assert.Equal(createdAt, actual.CreatedAt)
// Test CreatedAt assert.WithinDuration(time.Now(), actual.UpdatedAt, 5*time.Second)
if !actual.CreatedAt.Equal(createdAt) {
t.Fatalf("should not modify created at: %s", actual.CreatedAt)
}
// Test UpdatedAt
{
timeDiff := actual.UpdatedAt.Sub(createdAt)
if timeDiff <= 0 || timeDiff > 5*time.Second {
t.Fatalf("should set updated at: %s", actual.CreatedAt)
}
}
actual.CreateIndex, actual.ModifyIndex = 0, 0 actual.CreateIndex, actual.ModifyIndex = 0, 0
actual.CreatedAt = ixn.Intention.CreatedAt actual.CreatedAt = ixn.Intention.CreatedAt
actual.UpdatedAt = ixn.Intention.UpdatedAt actual.UpdatedAt = ixn.Intention.UpdatedAt
if !reflect.DeepEqual(actual, ixn.Intention) { assert.Equal(ixn.Intention, actual)
t.Fatalf("bad: %v", actual)
}
} }
} }
// Shouldn't be able to update a non-existent intention // Shouldn't be able to update a non-existent intention
func TestIntentionApply_updateNonExist(t *testing.T) { func TestIntentionApply_updateNonExist(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -305,14 +249,15 @@ func TestIntentionApply_updateNonExist(t *testing.T) {
// Create // Create
err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply) err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply)
if err == nil || !strings.Contains(err.Error(), "Cannot modify non-existent intention") { assert.NotNil(err)
t.Fatalf("bad: %v", err) assert.Contains(err, "Cannot modify non-existent intention")
}
} }
// Test basic deleting // Test basic deleting
func TestIntentionApply_deleteGood(t *testing.T) { func TestIntentionApply_deleteGood(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -336,19 +281,13 @@ func TestIntentionApply_deleteGood(t *testing.T) {
var reply string var reply string
// Create // Create
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err) assert.NotEmpty(reply)
}
if reply == "" {
t.Fatal("reply should be non-empty")
}
// Delete // Delete
ixn.Op = structs.IntentionOpDelete ixn.Op = structs.IntentionOpDelete
ixn.Intention.ID = reply ixn.Intention.ID = reply
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err)
}
// Read // Read
ixn.Intention.ID = reply ixn.Intention.ID = reply
@ -359,14 +298,15 @@ func TestIntentionApply_deleteGood(t *testing.T) {
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
err := msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp) err := msgpackrpc.CallWithCodec(codec, "Intention.Get", req, &resp)
if err == nil || !strings.Contains(err.Error(), ErrIntentionNotFound.Error()) { assert.NotNil(err)
t.Fatalf("err: %v", err) assert.Contains(err, ErrIntentionNotFound.Error())
}
} }
} }
func TestIntentionList(t *testing.T) { func TestIntentionList(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -381,16 +321,9 @@ func TestIntentionList(t *testing.T) {
Datacenter: "dc1", Datacenter: "dc1",
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := msgpackrpc.CallWithCodec(codec, "Intention.List", req, &resp); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.List", req, &resp))
t.Fatalf("err: %v", err) assert.NotNil(resp.Intentions)
} assert.Len(resp.Intentions, 0)
if resp.Intentions == nil {
t.Fatal("should not be nil")
}
if len(resp.Intentions) != 0 {
t.Fatalf("bad: %v", resp)
}
} }
} }
@ -398,6 +331,8 @@ func TestIntentionList(t *testing.T) {
// is tested in the agent/consul/state package. // is tested in the agent/consul/state package.
func TestIntentionMatch_good(t *testing.T) { func TestIntentionMatch_good(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
dir1, s1 := testServer(t) dir1, s1 := testServer(t)
defer os.RemoveAll(dir1) defer os.RemoveAll(dir1)
defer s1.Shutdown() defer s1.Shutdown()
@ -432,9 +367,7 @@ func TestIntentionMatch_good(t *testing.T) {
// Create // Create
var reply string var reply string
if err := msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err)
}
} }
} }
@ -452,21 +385,13 @@ func TestIntentionMatch_good(t *testing.T) {
}, },
} }
var resp structs.IndexedIntentionMatches var resp structs.IndexedIntentionMatches
if err := msgpackrpc.CallWithCodec(codec, "Intention.Match", req, &resp); err != nil { assert.Nil(msgpackrpc.CallWithCodec(codec, "Intention.Match", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Matches, 1)
}
if len(resp.Matches) != 1 {
t.Fatalf("bad: %#v", resp.Matches)
}
expected := [][]string{{"foo", "bar"}, {"foo", "*"}, {"*", "*"}} expected := [][]string{{"foo", "bar"}, {"foo", "*"}, {"*", "*"}}
var actual [][]string var actual [][]string
for _, ixn := range resp.Matches[0] { for _, ixn := range resp.Matches[0] {
actual = append(actual, []string{ixn.DestinationNS, ixn.DestinationName}) actual = append(actual, []string{ixn.DestinationNS, ixn.DestinationName})
} }
assert.Equal(expected, actual)
if !reflect.DeepEqual(actual, expected) {
t.Fatalf("bad (got, wanted):\n\n%#v\n\n%#v", actual, expected)
}
} }

View File

@ -1,34 +1,34 @@
package state package state
import ( import (
"reflect"
"testing" "testing"
"time" "time"
"github.com/hashicorp/consul/agent/structs" "github.com/hashicorp/consul/agent/structs"
"github.com/hashicorp/go-memdb" "github.com/hashicorp/go-memdb"
"github.com/stretchr/testify/assert"
) )
func TestStore_IntentionGet_none(t *testing.T) { func TestStore_IntentionGet_none(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Querying with no results returns nil. // Querying with no results returns nil.
ws := memdb.NewWatchSet() ws := memdb.NewWatchSet()
idx, res, err := s.IntentionGet(ws, testUUID()) idx, res, err := s.IntentionGet(ws, testUUID())
if idx != 0 || res != nil || err != nil { assert.Equal(idx, uint64(0))
t.Fatalf("expected (0, nil, nil), got: (%d, %#v, %#v)", idx, res, err) assert.Nil(res)
} assert.Nil(err)
} }
func TestStore_IntentionSetGet_basic(t *testing.T) { func TestStore_IntentionSetGet_basic(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Call Get to populate the watch set // Call Get to populate the watch set
ws := memdb.NewWatchSet() ws := memdb.NewWatchSet()
_, _, err := s.IntentionGet(ws, testUUID()) _, _, err := s.IntentionGet(ws, testUUID())
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err)
}
// Build a valid intention // Build a valid intention
ixn := &structs.Intention{ ixn := &structs.Intention{
@ -37,17 +37,11 @@ func TestStore_IntentionSetGet_basic(t *testing.T) {
} }
// Inserting a with empty ID is disallowed. // Inserting a with empty ID is disallowed.
if err := s.IntentionSet(1, ixn); err != nil { assert.Nil(s.IntentionSet(1, ixn))
t.Fatalf("err: %s", err)
}
// Make sure the index got updated. // Make sure the index got updated.
if idx := s.maxIndex(intentionsTableName); idx != 1 { assert.Equal(s.maxIndex(intentionsTableName), uint64(1))
t.Fatalf("bad index: %d", idx) assert.True(watchFired(ws), "watch fired")
}
if !watchFired(ws) {
t.Fatalf("bad")
}
// Read it back out and verify it. // Read it back out and verify it.
expected := &structs.Intention{ expected := &structs.Intention{
@ -61,70 +55,48 @@ func TestStore_IntentionSetGet_basic(t *testing.T) {
ws = memdb.NewWatchSet() ws = memdb.NewWatchSet()
idx, actual, err := s.IntentionGet(ws, ixn.ID) idx, actual, err := s.IntentionGet(ws, ixn.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(expected.CreateIndex, idx)
} assert.Equal(expected, actual)
if idx != expected.CreateIndex {
t.Fatalf("bad index: %d", idx)
}
if !reflect.DeepEqual(actual, expected) {
t.Fatalf("bad: %v", actual)
}
// Change a value and test updating // Change a value and test updating
ixn.SourceNS = "foo" ixn.SourceNS = "foo"
if err := s.IntentionSet(2, ixn); err != nil { assert.Nil(s.IntentionSet(2, ixn))
t.Fatalf("err: %s", err)
}
// Make sure the index got updated. // Make sure the index got updated.
if idx := s.maxIndex(intentionsTableName); idx != 2 { assert.Equal(s.maxIndex(intentionsTableName), uint64(2))
t.Fatalf("bad index: %d", idx) assert.True(watchFired(ws), "watch fired")
}
if !watchFired(ws) {
t.Fatalf("bad")
}
// Read it back and verify the data was updated // Read it back and verify the data was updated
expected.SourceNS = ixn.SourceNS expected.SourceNS = ixn.SourceNS
expected.ModifyIndex = 2 expected.ModifyIndex = 2
ws = memdb.NewWatchSet() ws = memdb.NewWatchSet()
idx, actual, err = s.IntentionGet(ws, ixn.ID) idx, actual, err = s.IntentionGet(ws, ixn.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(expected.ModifyIndex, idx)
} assert.Equal(expected, actual)
if idx != expected.ModifyIndex {
t.Fatalf("bad index: %d", idx)
}
if !reflect.DeepEqual(actual, expected) {
t.Fatalf("bad: %#v", actual)
}
} }
func TestStore_IntentionSet_emptyId(t *testing.T) { func TestStore_IntentionSet_emptyId(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
ws := memdb.NewWatchSet() ws := memdb.NewWatchSet()
_, _, err := s.IntentionGet(ws, testUUID()) _, _, err := s.IntentionGet(ws, testUUID())
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err)
}
// Inserting a with empty ID is disallowed. // Inserting a with empty ID is disallowed.
if err := s.IntentionSet(1, &structs.Intention{}); err == nil { err = s.IntentionSet(1, &structs.Intention{})
t.Fatalf("expected %#v, got: %#v", ErrMissingIntentionID, err) assert.NotNil(err)
} assert.Contains(err.Error(), ErrMissingIntentionID.Error())
// Index is not updated if nothing is saved. // Index is not updated if nothing is saved.
if idx := s.maxIndex(intentionsTableName); idx != 0 { assert.Equal(s.maxIndex(intentionsTableName), uint64(0))
t.Fatalf("bad index: %d", idx) assert.False(watchFired(ws), "watch fired")
}
if watchFired(ws) {
t.Fatalf("bad")
}
} }
func TestStore_IntentionSet_updateCreatedAt(t *testing.T) { func TestStore_IntentionSet_updateCreatedAt(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Build a valid intention // Build a valid intention
@ -135,28 +107,21 @@ func TestStore_IntentionSet_updateCreatedAt(t *testing.T) {
} }
// Insert // Insert
if err := s.IntentionSet(1, &ixn); err != nil { assert.Nil(s.IntentionSet(1, &ixn))
t.Fatalf("err: %s", err)
}
// Change a value and test updating // Change a value and test updating
ixnUpdate := ixn ixnUpdate := ixn
ixnUpdate.CreatedAt = now.Add(10 * time.Second) ixnUpdate.CreatedAt = now.Add(10 * time.Second)
if err := s.IntentionSet(2, &ixnUpdate); err != nil { assert.Nil(s.IntentionSet(2, &ixnUpdate))
t.Fatalf("err: %s", err)
}
// Read it back and verify // Read it back and verify
_, actual, err := s.IntentionGet(nil, ixn.ID) _, actual, err := s.IntentionGet(nil, ixn.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(now, actual.CreatedAt)
}
if !actual.CreatedAt.Equal(now) {
t.Fatalf("bad: %#v", actual)
}
} }
func TestStore_IntentionSet_metaNil(t *testing.T) { func TestStore_IntentionSet_metaNil(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Build a valid intention // Build a valid intention
@ -165,21 +130,16 @@ func TestStore_IntentionSet_metaNil(t *testing.T) {
} }
// Insert // Insert
if err := s.IntentionSet(1, &ixn); err != nil { assert.Nil(s.IntentionSet(1, &ixn))
t.Fatalf("err: %s", err)
}
// Read it back and verify // Read it back and verify
_, actual, err := s.IntentionGet(nil, ixn.ID) _, actual, err := s.IntentionGet(nil, ixn.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.NotNil(actual.Meta)
}
if actual.Meta == nil {
t.Fatal("meta should be non-nil")
}
} }
func TestStore_IntentionSet_metaSet(t *testing.T) { func TestStore_IntentionSet_metaSet(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Build a valid intention // Build a valid intention
@ -189,79 +149,55 @@ func TestStore_IntentionSet_metaSet(t *testing.T) {
} }
// Insert // Insert
if err := s.IntentionSet(1, &ixn); err != nil { assert.Nil(s.IntentionSet(1, &ixn))
t.Fatalf("err: %s", err)
}
// Read it back and verify // Read it back and verify
_, actual, err := s.IntentionGet(nil, ixn.ID) _, actual, err := s.IntentionGet(nil, ixn.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(ixn.Meta, actual.Meta)
}
if !reflect.DeepEqual(actual.Meta, ixn.Meta) {
t.Fatalf("bad: %#v", actual)
}
} }
func TestStore_IntentionDelete(t *testing.T) { func TestStore_IntentionDelete(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Call Get to populate the watch set // Call Get to populate the watch set
ws := memdb.NewWatchSet() ws := memdb.NewWatchSet()
_, _, err := s.IntentionGet(ws, testUUID()) _, _, err := s.IntentionGet(ws, testUUID())
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err)
}
// Create // Create
ixn := &structs.Intention{ID: testUUID()} ixn := &structs.Intention{ID: testUUID()}
if err := s.IntentionSet(1, ixn); err != nil { assert.Nil(s.IntentionSet(1, ixn))
t.Fatalf("err: %s", err)
}
// Make sure the index got updated. // Make sure the index got updated.
if idx := s.maxIndex(intentionsTableName); idx != 1 { assert.Equal(s.maxIndex(intentionsTableName), uint64(1))
t.Fatalf("bad index: %d", idx) assert.True(watchFired(ws), "watch fired")
}
if !watchFired(ws) {
t.Fatalf("bad")
}
// Delete // Delete
if err := s.IntentionDelete(2, ixn.ID); err != nil { assert.Nil(s.IntentionDelete(2, ixn.ID))
t.Fatalf("err: %s", err)
}
// Make sure the index got updated. // Make sure the index got updated.
if idx := s.maxIndex(intentionsTableName); idx != 2 { assert.Equal(s.maxIndex(intentionsTableName), uint64(2))
t.Fatalf("bad index: %d", idx) assert.True(watchFired(ws), "watch fired")
}
if !watchFired(ws) {
t.Fatalf("bad")
}
// Sanity check to make sure it's not there. // Sanity check to make sure it's not there.
idx, actual, err := s.IntentionGet(nil, ixn.ID) idx, actual, err := s.IntentionGet(nil, ixn.ID)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(idx, uint64(2))
} assert.Nil(actual)
if idx != 2 {
t.Fatalf("bad index: %d", idx)
}
if actual != nil {
t.Fatalf("bad: %v", actual)
}
} }
func TestStore_IntentionsList(t *testing.T) { func TestStore_IntentionsList(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Querying with no results returns nil. // Querying with no results returns nil.
ws := memdb.NewWatchSet() ws := memdb.NewWatchSet()
idx, res, err := s.Intentions(ws) idx, res, err := s.Intentions(ws)
if idx != 0 || res != nil || err != nil { assert.Nil(err)
t.Fatalf("expected (0, nil, nil), got: (%d, %#v, %#v)", idx, res, err) assert.Nil(res)
} assert.Equal(idx, uint64(0))
// Create some intentions // Create some intentions
ixns := structs.Intentions{ ixns := structs.Intentions{
@ -281,13 +217,9 @@ func TestStore_IntentionsList(t *testing.T) {
// Create // Create
for i, ixn := range ixns { for i, ixn := range ixns {
if err := s.IntentionSet(uint64(1+i), ixn); err != nil { assert.Nil(s.IntentionSet(uint64(1+i), ixn))
t.Fatalf("err: %s", err)
}
}
if !watchFired(ws) {
t.Fatalf("bad")
} }
assert.True(watchFired(ws), "watch fired")
// Read it back and verify. // Read it back and verify.
expected := structs.Intentions{ expected := structs.Intentions{
@ -309,15 +241,9 @@ func TestStore_IntentionsList(t *testing.T) {
}, },
} }
idx, actual, err := s.Intentions(nil) idx, actual, err := s.Intentions(nil)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(idx, uint64(2))
} assert.Equal(expected, actual)
if idx != 2 {
t.Fatalf("bad index: %d", idx)
}
if !reflect.DeepEqual(actual, expected) {
t.Fatalf("bad: %v", actual)
}
} }
// Test the matrix of match logic. // Test the matrix of match logic.
@ -386,6 +312,7 @@ func TestStore_IntentionMatch_table(t *testing.T) {
// test both cases. // test both cases.
testRunner := func(t *testing.T, tc testCase, typ structs.IntentionMatchType) { testRunner := func(t *testing.T, tc testCase, typ structs.IntentionMatchType) {
// Insert the set // Insert the set
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
var idx uint64 = 1 var idx uint64 = 1
for _, v := range tc.Insert { for _, v := range tc.Insert {
@ -399,10 +326,7 @@ func TestStore_IntentionMatch_table(t *testing.T) {
ixn.SourceName = v[1] ixn.SourceName = v[1]
} }
err := s.IntentionSet(idx, ixn) assert.Nil(s.IntentionSet(idx, ixn))
if err != nil {
t.Fatalf("error inserting: %s", err)
}
idx++ idx++
} }
@ -418,14 +342,10 @@ func TestStore_IntentionMatch_table(t *testing.T) {
// Match // Match
_, matches, err := s.IntentionMatch(nil, args) _, matches, err := s.IntentionMatch(nil, args)
if err != nil { assert.Nil(err)
t.Fatalf("error matching: %s", err)
}
// Should have equal lengths // Should have equal lengths
if len(matches) != len(tc.Expected) { assert.Len(matches, len(tc.Expected))
t.Fatalf("bad (got, wanted):\n\n%#v\n\n%#v", tc.Expected, matches)
}
// Verify matches // Verify matches
for i, expected := range tc.Expected { for i, expected := range tc.Expected {
@ -439,9 +359,7 @@ func TestStore_IntentionMatch_table(t *testing.T) {
} }
} }
if !reflect.DeepEqual(actual, expected) { assert.Equal(expected, actual)
t.Fatalf("bad (got, wanted):\n\n%#v\n\n%#v", actual, expected)
}
} }
} }
@ -457,6 +375,7 @@ func TestStore_IntentionMatch_table(t *testing.T) {
} }
func TestStore_Intention_Snapshot_Restore(t *testing.T) { func TestStore_Intention_Snapshot_Restore(t *testing.T) {
assert := assert.New(t)
s := testStateStore(t) s := testStateStore(t)
// Create some intentions. // Create some intentions.
@ -481,9 +400,7 @@ func TestStore_Intention_Snapshot_Restore(t *testing.T) {
// Now create // Now create
for i, ixn := range ixns { for i, ixn := range ixns {
if err := s.IntentionSet(uint64(4+i), ixn); err != nil { assert.Nil(s.IntentionSet(uint64(4+i), ixn))
t.Fatalf("err: %s", err)
}
} }
// Snapshot the queries. // Snapshot the queries.
@ -491,14 +408,10 @@ func TestStore_Intention_Snapshot_Restore(t *testing.T) {
defer snap.Close() defer snap.Close()
// Alter the real state store. // Alter the real state store.
if err := s.IntentionDelete(7, ixns[0].ID); err != nil { assert.Nil(s.IntentionDelete(7, ixns[0].ID))
t.Fatalf("err: %s", err)
}
// Verify the snapshot. // Verify the snapshot.
if idx := snap.LastIndex(); idx != 6 { assert.Equal(snap.LastIndex(), uint64(6))
t.Fatalf("bad index: %d", idx)
}
expected := structs.Intentions{ expected := structs.Intentions{
&structs.Intention{ &structs.Intention{
ID: ixns[0].ID, ID: ixns[0].ID,
@ -529,34 +442,22 @@ func TestStore_Intention_Snapshot_Restore(t *testing.T) {
}, },
} }
dump, err := snap.Intentions() dump, err := snap.Intentions()
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(expected, dump)
}
if !reflect.DeepEqual(dump, expected) {
t.Fatalf("bad: %#v", dump[0])
}
// Restore the values into a new state store. // Restore the values into a new state store.
func() { func() {
s := testStateStore(t) s := testStateStore(t)
restore := s.Restore() restore := s.Restore()
for _, ixn := range dump { for _, ixn := range dump {
if err := restore.Intention(ixn); err != nil { assert.Nil(restore.Intention(ixn))
t.Fatalf("err: %s", err)
}
} }
restore.Commit() restore.Commit()
// Read the restored values back out and verify that they match. // Read the restored values back out and verify that they match.
idx, actual, err := s.Intentions(nil) idx, actual, err := s.Intentions(nil)
if err != nil { assert.Nil(err)
t.Fatalf("err: %s", err) assert.Equal(idx, uint64(6))
} assert.Equal(expected, actual)
if idx != 6 {
t.Fatalf("bad index: %d", idx)
}
if !reflect.DeepEqual(actual, expected) {
t.Fatalf("bad: %v", actual)
}
}() }()
} }

View File

@ -4,17 +4,17 @@ import (
"fmt" "fmt"
"net/http" "net/http"
"net/http/httptest" "net/http/httptest"
"reflect"
"sort" "sort"
"strings"
"testing" "testing"
"github.com/hashicorp/consul/agent/structs" "github.com/hashicorp/consul/agent/structs"
"github.com/stretchr/testify/assert"
) )
func TestIntentionsList_empty(t *testing.T) { func TestIntentionsList_empty(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -22,19 +22,17 @@ func TestIntentionsList_empty(t *testing.T) {
req, _ := http.NewRequest("GET", "/v1/connect/intentions", nil) req, _ := http.NewRequest("GET", "/v1/connect/intentions", nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionList(resp, req) obj, err := a.srv.IntentionList(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err)
}
value := obj.(structs.Intentions) value := obj.(structs.Intentions)
if value == nil || len(value) != 0 { assert.NotNil(value)
t.Fatalf("bad: %v", value) assert.Len(value, 0)
}
} }
func TestIntentionsList_values(t *testing.T) { func TestIntentionsList_values(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -48,35 +46,28 @@ func TestIntentionsList_values(t *testing.T) {
req.Intention.SourceName = v req.Intention.SourceName = v
var reply string var reply string
if err := a.RPC("Intention.Apply", &req, &reply); err != nil { assert.Nil(a.RPC("Intention.Apply", &req, &reply))
t.Fatalf("err: %s", err)
}
} }
// Request // Request
req, _ := http.NewRequest("GET", "/v1/connect/intentions", nil) req, _ := http.NewRequest("GET", "/v1/connect/intentions", nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionList(resp, req) obj, err := a.srv.IntentionList(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err)
}
value := obj.(structs.Intentions) value := obj.(structs.Intentions)
if len(value) != 2 { assert.Len(value, 2)
t.Fatalf("bad: %v", value)
}
expected := []string{"bar", "foo"} expected := []string{"bar", "foo"}
actual := []string{value[0].SourceName, value[1].SourceName} actual := []string{value[0].SourceName, value[1].SourceName}
sort.Strings(actual) sort.Strings(actual)
if !reflect.DeepEqual(actual, expected) { assert.Equal(expected, actual)
t.Fatalf("bad: %#v", actual)
}
} }
func TestIntentionsMatch_basic(t *testing.T) { func TestIntentionsMatch_basic(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -102,9 +93,7 @@ func TestIntentionsMatch_basic(t *testing.T) {
// Create // Create
var reply string var reply string
if err := a.RPC("Intention.Apply", &ixn, &reply); err != nil { assert.Nil(a.RPC("Intention.Apply", &ixn, &reply))
t.Fatalf("err: %v", err)
}
} }
} }
@ -113,14 +102,10 @@ func TestIntentionsMatch_basic(t *testing.T) {
"/v1/connect/intentions/match?by=destination&name=foo/bar", nil) "/v1/connect/intentions/match?by=destination&name=foo/bar", nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionMatch(resp, req) obj, err := a.srv.IntentionMatch(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err)
}
value := obj.(map[string]structs.Intentions) value := obj.(map[string]structs.Intentions)
if len(value) != 1 { assert.Len(value, 1)
t.Fatalf("bad: %v", value)
}
var actual [][]string var actual [][]string
expected := [][]string{{"foo", "bar"}, {"foo", "*"}, {"*", "*"}} expected := [][]string{{"foo", "bar"}, {"foo", "*"}, {"*", "*"}}
@ -128,14 +113,13 @@ func TestIntentionsMatch_basic(t *testing.T) {
actual = append(actual, []string{ixn.DestinationNS, ixn.DestinationName}) actual = append(actual, []string{ixn.DestinationNS, ixn.DestinationName})
} }
if !reflect.DeepEqual(actual, expected) { assert.Equal(expected, actual)
t.Fatalf("bad (got, wanted):\n\n%#v\n\n%#v", actual, expected)
}
} }
func TestIntentionsMatch_noBy(t *testing.T) { func TestIntentionsMatch_noBy(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -144,17 +128,15 @@ func TestIntentionsMatch_noBy(t *testing.T) {
"/v1/connect/intentions/match?name=foo/bar", nil) "/v1/connect/intentions/match?name=foo/bar", nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionMatch(resp, req) obj, err := a.srv.IntentionMatch(resp, req)
if err == nil || !strings.Contains(err.Error(), "by") { assert.NotNil(err)
t.Fatalf("err: %v", err) assert.Contains(err.Error(), "by")
} assert.Nil(obj)
if obj != nil {
t.Fatal("should have no response")
}
} }
func TestIntentionsMatch_byInvalid(t *testing.T) { func TestIntentionsMatch_byInvalid(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -163,17 +145,15 @@ func TestIntentionsMatch_byInvalid(t *testing.T) {
"/v1/connect/intentions/match?by=datacenter", nil) "/v1/connect/intentions/match?by=datacenter", nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionMatch(resp, req) obj, err := a.srv.IntentionMatch(resp, req)
if err == nil || !strings.Contains(err.Error(), "'by' parameter") { assert.NotNil(err)
t.Fatalf("err: %v", err) assert.Contains(err.Error(), "'by' parameter")
} assert.Nil(obj)
if obj != nil {
t.Fatal("should have no response")
}
} }
func TestIntentionsMatch_noName(t *testing.T) { func TestIntentionsMatch_noName(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -182,17 +162,15 @@ func TestIntentionsMatch_noName(t *testing.T) {
"/v1/connect/intentions/match?by=source", nil) "/v1/connect/intentions/match?by=source", nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionMatch(resp, req) obj, err := a.srv.IntentionMatch(resp, req)
if err == nil || !strings.Contains(err.Error(), "'name' not set") { assert.NotNil(err)
t.Fatalf("err: %v", err) assert.Contains(err.Error(), "'name' not set")
} assert.Nil(obj)
if obj != nil {
t.Fatal("should have no response")
}
} }
func TestIntentionsCreate_good(t *testing.T) { func TestIntentionsCreate_good(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -202,14 +180,10 @@ func TestIntentionsCreate_good(t *testing.T) {
req, _ := http.NewRequest("POST", "/v1/connect/intentions", jsonReader(args)) req, _ := http.NewRequest("POST", "/v1/connect/intentions", jsonReader(args))
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionCreate(resp, req) obj, err := a.srv.IntentionCreate(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err)
}
value := obj.(intentionCreateResponse) value := obj.(intentionCreateResponse)
if value.ID == "" { assert.NotEqual("", value.ID)
t.Fatalf("bad: %v", value)
}
// Read the value // Read the value
{ {
@ -218,22 +192,17 @@ func TestIntentionsCreate_good(t *testing.T) {
IntentionID: value.ID, IntentionID: value.ID,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := a.RPC("Intention.Get", req, &resp); err != nil { assert.Nil(a.RPC("Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
if actual.SourceName != "foo" { assert.Equal("foo", actual.SourceName)
t.Fatalf("bad: %#v", actual)
}
} }
} }
func TestIntentionsSpecificGet_good(t *testing.T) { func TestIntentionsSpecificGet_good(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -248,35 +217,28 @@ func TestIntentionsSpecificGet_good(t *testing.T) {
Op: structs.IntentionOpCreate, Op: structs.IntentionOpCreate,
Intention: ixn, Intention: ixn,
} }
if err := a.RPC("Intention.Apply", &req, &reply); err != nil { assert.Nil(a.RPC("Intention.Apply", &req, &reply))
t.Fatalf("err: %s", err)
}
} }
// Get the value // Get the value
req, _ := http.NewRequest("GET", fmt.Sprintf("/v1/connect/intentions/%s", reply), nil) req, _ := http.NewRequest("GET", fmt.Sprintf("/v1/connect/intentions/%s", reply), nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionSpecific(resp, req) obj, err := a.srv.IntentionSpecific(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err)
}
value := obj.(*structs.Intention) value := obj.(*structs.Intention)
if value.ID != reply { assert.Equal(reply, value.ID)
t.Fatalf("bad: %v", value)
}
ixn.ID = value.ID ixn.ID = value.ID
ixn.RaftIndex = value.RaftIndex ixn.RaftIndex = value.RaftIndex
ixn.CreatedAt, ixn.UpdatedAt = value.CreatedAt, value.UpdatedAt ixn.CreatedAt, ixn.UpdatedAt = value.CreatedAt, value.UpdatedAt
if !reflect.DeepEqual(value, ixn) { assert.Equal(ixn, value)
t.Fatalf("bad (got, want):\n\n%#v\n\n%#v", value, ixn)
}
} }
func TestIntentionsSpecificUpdate_good(t *testing.T) { func TestIntentionsSpecificUpdate_good(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -291,9 +253,7 @@ func TestIntentionsSpecificUpdate_good(t *testing.T) {
Op: structs.IntentionOpCreate, Op: structs.IntentionOpCreate,
Intention: ixn, Intention: ixn,
} }
if err := a.RPC("Intention.Apply", &req, &reply); err != nil { assert.Nil(a.RPC("Intention.Apply", &req, &reply))
t.Fatalf("err: %s", err)
}
} }
// Update the intention // Update the intention
@ -302,12 +262,8 @@ func TestIntentionsSpecificUpdate_good(t *testing.T) {
req, _ := http.NewRequest("PUT", fmt.Sprintf("/v1/connect/intentions/%s", reply), jsonReader(ixn)) req, _ := http.NewRequest("PUT", fmt.Sprintf("/v1/connect/intentions/%s", reply), jsonReader(ixn))
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionSpecific(resp, req) obj, err := a.srv.IntentionSpecific(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err) assert.Nil(obj)
}
if obj != nil {
t.Fatalf("obj should be nil: %v", err)
}
// Read the value // Read the value
{ {
@ -316,22 +272,17 @@ func TestIntentionsSpecificUpdate_good(t *testing.T) {
IntentionID: reply, IntentionID: reply,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := a.RPC("Intention.Get", req, &resp); err != nil { assert.Nil(a.RPC("Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
if actual.SourceName != "bar" { assert.Equal("bar", actual.SourceName)
t.Fatalf("bad: %#v", actual)
}
} }
} }
func TestIntentionsSpecificDelete_good(t *testing.T) { func TestIntentionsSpecificDelete_good(t *testing.T) {
t.Parallel() t.Parallel()
assert := assert.New(t)
a := NewTestAgent(t.Name(), "") a := NewTestAgent(t.Name(), "")
defer a.Shutdown() defer a.Shutdown()
@ -347,9 +298,7 @@ func TestIntentionsSpecificDelete_good(t *testing.T) {
Op: structs.IntentionOpCreate, Op: structs.IntentionOpCreate,
Intention: ixn, Intention: ixn,
} }
if err := a.RPC("Intention.Apply", &req, &reply); err != nil { assert.Nil(a.RPC("Intention.Apply", &req, &reply))
t.Fatalf("err: %s", err)
}
} }
// Sanity check that the intention exists // Sanity check that the intention exists
@ -359,28 +308,18 @@ func TestIntentionsSpecificDelete_good(t *testing.T) {
IntentionID: reply, IntentionID: reply,
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
if err := a.RPC("Intention.Get", req, &resp); err != nil { assert.Nil(a.RPC("Intention.Get", req, &resp))
t.Fatalf("err: %v", err) assert.Len(resp.Intentions, 1)
}
if len(resp.Intentions) != 1 {
t.Fatalf("bad: %v", resp)
}
actual := resp.Intentions[0] actual := resp.Intentions[0]
if actual.SourceName != "foo" { assert.Equal("foo", actual.SourceName)
t.Fatalf("bad: %#v", actual)
}
} }
// Delete the intention // Delete the intention
req, _ := http.NewRequest("DELETE", fmt.Sprintf("/v1/connect/intentions/%s", reply), nil) req, _ := http.NewRequest("DELETE", fmt.Sprintf("/v1/connect/intentions/%s", reply), nil)
resp := httptest.NewRecorder() resp := httptest.NewRecorder()
obj, err := a.srv.IntentionSpecific(resp, req) obj, err := a.srv.IntentionSpecific(resp, req)
if err != nil { assert.Nil(err)
t.Fatalf("err: %v", err) assert.Nil(obj)
}
if obj != nil {
t.Fatalf("obj should be nil: %v", err)
}
// Verify the intention is gone // Verify the intention is gone
{ {
@ -390,9 +329,8 @@ func TestIntentionsSpecificDelete_good(t *testing.T) {
} }
var resp structs.IndexedIntentions var resp structs.IndexedIntentions
err := a.RPC("Intention.Get", req, &resp) err := a.RPC("Intention.Get", req, &resp)
if err == nil || !strings.Contains(err.Error(), "not found") { assert.NotNil(err)
t.Fatalf("err: %v", err) assert.Contains(err.Error(), "not found")
}
} }
} }
@ -429,17 +367,14 @@ func TestParseIntentionMatchEntry(t *testing.T) {
for _, tc := range cases { for _, tc := range cases {
t.Run(tc.Input, func(t *testing.T) { t.Run(tc.Input, func(t *testing.T) {
assert := assert.New(t)
actual, err := parseIntentionMatchEntry(tc.Input) actual, err := parseIntentionMatchEntry(tc.Input)
if (err != nil) != tc.Err { assert.Equal(err != nil, tc.Err, err)
t.Fatalf("err: %s", err)
}
if err != nil { if err != nil {
return return
} }
if !reflect.DeepEqual(actual, tc.Expected) { assert.Equal(tc.Expected, actual)
t.Fatalf("bad: %#v", actual)
}
}) })
} }
} }

View File

@ -1,10 +1,11 @@
package structs package structs
import ( import (
"reflect"
"sort" "sort"
"strings" "strings"
"testing" "testing"
"github.com/stretchr/testify/assert"
) )
func TestIntentionValidate(t *testing.T) { func TestIntentionValidate(t *testing.T) {
@ -108,19 +109,17 @@ func TestIntentionValidate(t *testing.T) {
for _, tc := range cases { for _, tc := range cases {
t.Run(tc.Name, func(t *testing.T) { t.Run(tc.Name, func(t *testing.T) {
assert := assert.New(t)
ixn := TestIntention(t) ixn := TestIntention(t)
tc.Modify(ixn) tc.Modify(ixn)
err := ixn.Validate() err := ixn.Validate()
if (err != nil) != (tc.Err != "") { assert.Equal(err != nil, tc.Err != "", err)
t.Fatalf("err: %s", err)
}
if err == nil { if err == nil {
return return
} }
if !strings.Contains(strings.ToLower(err.Error()), strings.ToLower(tc.Err)) {
t.Fatalf("err: %s", err) assert.Contains(strings.ToLower(err.Error()), strings.ToLower(tc.Err))
}
}) })
} }
} }
@ -160,6 +159,8 @@ func TestIntentionPrecedenceSorter(t *testing.T) {
for _, tc := range cases { for _, tc := range cases {
t.Run(tc.Name, func(t *testing.T) { t.Run(tc.Name, func(t *testing.T) {
assert := assert.New(t)
var input Intentions var input Intentions
for _, v := range tc.Input { for _, v := range tc.Input {
input = append(input, &Intention{ input = append(input, &Intention{
@ -183,9 +184,7 @@ func TestIntentionPrecedenceSorter(t *testing.T) {
v.DestinationName, v.DestinationName,
}) })
} }
if !reflect.DeepEqual(actual, tc.Expected) { assert.Equal(tc.Expected, actual)
t.Fatalf("bad (got, wanted):\n\n%#v\n\n%#v", actual, tc.Expected)
}
}) })
} }
} }