Add basic kv tests

This commit is contained in:
Ethan Frey 2017-07-26 14:39:04 -04:00
parent 28ebfd64dd
commit 37b5d16b73
5 changed files with 146 additions and 71 deletions

View File

@ -49,12 +49,16 @@ type SimpleDB interface {
//----------------------------------------
// MemKVStore is a simple implementation of SimpleDB.
// It is only intended for quick testing, not to be used
// in production or with large data stores.
type MemKVStore struct {
m map[string][]byte
}
var _ SimpleDB = NewMemKVStore()
// NewMemKVStore initializes a MemKVStore
func NewMemKVStore() *MemKVStore {
return &MemKVStore{
m: make(map[string][]byte, 0),
@ -83,7 +87,12 @@ func (mkv *MemKVStore) Remove(key []byte) (value []byte) {
func (mkv *MemKVStore) List(start, end []byte, limit int) []Model {
keys := mkv.keysInRange(start, end)
sort.Strings(keys)
keys = keys[:limit]
if limit > 0 && len(keys) > 0 {
if limit > len(keys) {
limit = len(keys)
}
keys = keys[:limit]
}
res := make([]Model, len(keys))
for i, k := range keys {

View File

@ -1,70 +0,0 @@
package state
import (
"bytes"
"testing"
"github.com/stretchr/testify/assert"
)
func TestKVStore(t *testing.T) {
assert := assert.New(t)
//stores to be tested
ms := NewMemKVStore()
store := NewMemKVStore()
kvc := NewKVCache(store)
//key value pairs to be tested within the system
var keyvalue = []struct {
key string
value string
}{
{"foo", "snake"},
{"bar", "mouse"},
}
//set the kvc to have all the key value pairs
setRecords := func(kv KVStore) {
for _, n := range keyvalue {
kv.Set([]byte(n.key), []byte(n.value))
}
}
//store has all the key value pairs
storeHasAll := func(kv KVStore) bool {
for _, n := range keyvalue {
if !bytes.Equal(kv.Get([]byte(n.key)), []byte(n.value)) {
return false
}
}
return true
}
//test read/write for MemKVStore
setRecords(ms)
assert.True(storeHasAll(ms), "MemKVStore doesn't retrieve after Set")
//test read/write for KVCache
setRecords(kvc)
assert.True(storeHasAll(kvc), "KVCache doesn't retrieve after Set")
//test reset
kvc.Reset()
assert.False(storeHasAll(kvc), "KVCache retrieving after reset")
//test sync
setRecords(kvc)
assert.False(storeHasAll(store), "store retrieving before synced")
kvc.Sync()
assert.True(storeHasAll(store), "store isn't retrieving after synced")
//test logging
assert.Zero(len(kvc.GetLogLines()), "logging events existed before using SetLogging")
kvc.SetLogging()
setRecords(kvc)
assert.Equal(len(kvc.GetLogLines()), 2, "incorrect number of logging events recorded")
kvc.ClearLogLines()
assert.Zero(len(kvc.GetLogLines()), "logging events still exists after ClearLogLines")
}

136
state/store_test.go Normal file
View File

@ -0,0 +1,136 @@
package state
import (
"testing"
"github.com/stretchr/testify/assert"
)
func GetDBs() []SimpleDB {
return []SimpleDB{
NewMemKVStore(),
}
}
// TestKVStore makes sure that get/set/remove operations work,
// as well as list
func TestKVStore(t *testing.T) {
assert := assert.New(t)
type listQuery struct {
// this is the list query
start, end []byte
limit int
// expected result from List, first element also expected for First
expected []Model
// expected result from Last
last Model
}
cases := []struct {
toSet []Model
toRemove []Model
toGet []Model
toList []listQuery
}{
// simple add
{
[]Model{
{[]byte{1}, []byte{2}},
{[]byte{3}, []byte{4}},
},
nil,
[]Model{{[]byte{1}, []byte{2}}},
[]listQuery{
{
[]byte{1}, []byte{4}, 0,
// all
[]Model{
{[]byte{1}, []byte{2}},
{[]byte{3}, []byte{4}},
},
// last one
Model{[]byte{3}, []byte{4}},
},
{
[]byte{1}, []byte{3}, 10,
// all
[]Model{
{[]byte{1}, []byte{2}},
},
// last one
Model{[]byte{1}, []byte{2}},
},
},
},
// over-write data, remove
{
[]Model{
{[]byte{1}, []byte{2}},
{[]byte{2}, []byte{2}},
{[]byte{3}, []byte{2}},
{[]byte{2}, []byte{4}},
},
[]Model{{[]byte{3}, []byte{2}}},
[]Model{
{[]byte{1}, []byte{2}},
{[]byte{2}, []byte{4}},
{[]byte{3}, nil},
},
[]listQuery{
{
[]byte{0, 5}, []byte{10}, 1,
// all
[]Model{
{[]byte{1}, []byte{2}},
},
// last
Model{[]byte{2}, []byte{4}},
},
{
[]byte{1, 4}, []byte{1, 7}, 10,
[]Model{},
Model{},
},
{
[]byte{1, 5}, []byte{10}, 0,
[]Model{
{[]byte{2}, []byte{4}},
},
Model{[]byte{2}, []byte{4}},
},
},
},
}
for i, tc := range cases {
for j, db := range GetDBs() {
for _, s := range tc.toSet {
db.Set(s.Key, s.Value)
}
for k, r := range tc.toRemove {
val := db.Remove(r.Key)
assert.EqualValues(r.Value, val, "%d/%d/%d", i, j, k)
}
for k, g := range tc.toGet {
val := db.Get(g.Key)
assert.EqualValues(g.Value, val, "%d/%d/%d", i, j, k)
has := db.Has(g.Key)
assert.Equal(len(g.Value) != 0, has, "%d/%d/%d", i, j, k)
}
for k, lq := range tc.toList {
list := db.List(lq.start, lq.end, lq.limit)
if assert.EqualValues(lq.expected, list, "%d/%d/%d", i, j, k) {
var first Model
if len(lq.expected) > 0 {
first = lq.expected[0]
}
f := db.First(lq.start, lq.end)
assert.EqualValues(first, f, "%d/%d/%d", i, j, k)
l := db.Last(lq.start, lq.end)
assert.EqualValues(lq.last, l, "%d/%d/%d", i, j, k)
}
}
}
}
}