github.com/annwntech/go-micro/v2@v2.9.5/store/cache/cache_test.go (about) 1 package cache 2 3 import ( 4 "sort" 5 "testing" 6 7 "github.com/annwntech/go-micro/v2/store" 8 "github.com/annwntech/go-micro/v2/store/memory" 9 "github.com/stretchr/testify/assert" 10 ) 11 12 func TestCache(t *testing.T) { 13 l0, l1, l2 := memory.NewStore(store.Database("l0")), memory.NewStore(store.Table("l1")), memory.NewStore() 14 _, _, _ = l0.Init(), l1.Init(), l2.Init() 15 16 assert := assert.New(t) 17 18 nonCache := NewCache(nil) 19 assert.Equal(len(nonCache.(*cache).stores), 1, "Expected a cache initialised with just 1 store to fail") 20 21 // Basic functionality 22 cachedStore := NewCache(l0, l1, l2) 23 assert.Equal(cachedStore.Options(), l0.Options(), "Options on store/cache are nonsensical") 24 expectedString := "cache [memory memory memory]" 25 assert.Equal(cachedStore.String(), expectedString, "Cache couldn't describe itself as expected") 26 27 // Read/Write tests 28 _, err := cachedStore.Read("test") 29 assert.Equal(store.ErrNotFound, err, "Read non existant key") 30 r1 := &store.Record{ 31 Key: "aaa", 32 Value: []byte("bbb"), 33 Metadata: map[string]interface{}{}, 34 } 35 r2 := &store.Record{ 36 Key: "aaaa", 37 Value: []byte("bbbb"), 38 Metadata: map[string]interface{}{}, 39 } 40 r3 := &store.Record{ 41 Key: "aaaaa", 42 Value: []byte("bbbbb"), 43 Metadata: map[string]interface{}{}, 44 } 45 // Write 3 records directly to l2 46 l2.Write(r1) 47 l2.Write(r2) 48 l2.Write(r3) 49 // Ensure it's not in l0 50 assert.Equal(store.ErrNotFound, func() error { _, err := l0.Read(r1.Key); return err }()) 51 // Read from cache, ensure it's in all 3 stores 52 results, err := cachedStore.Read(r1.Key) 53 assert.Nil(err, "cachedStore.Read() returned error") 54 assert.Len(results, 1, "cachedStore.Read() should only return 1 result") 55 assert.Equal(r1, results[0], "Cached read didn't return the record that was put in") 56 results, err = l0.Read(r1.Key) 57 assert.Nil(err) 58 assert.Equal(r1, results[0], "l0 not coherent") 59 results, err = l1.Read(r1.Key) 60 assert.Nil(err) 61 assert.Equal(r1, results[0], "l1 not coherent") 62 results, err = l2.Read(r1.Key) 63 assert.Nil(err) 64 assert.Equal(r1, results[0], "l2 not coherent") 65 // Multiple read 66 results, err = cachedStore.Read("aa", store.ReadPrefix()) 67 assert.Nil(err, "Cachedstore multiple read errored") 68 assert.Len(results, 3, "ReadPrefix should have read all records") 69 // l1 should now have all 3 records 70 l1results, err := l1.Read("aa", store.ReadPrefix()) 71 assert.Nil(err, "l1.Read failed") 72 assert.Len(l1results, 3, "l1 didn't contain a full cache") 73 sort.Slice(results, func(i, j int) bool { return results[i].Key < results[j].Key }) 74 sort.Slice(l1results, func(i, j int) bool { return l1results[i].Key < l1results[j].Key }) 75 assert.Equal(results[0], l1results[0], "l1 cache not coherent") 76 assert.Equal(results[1], l1results[1], "l1 cache not coherent") 77 assert.Equal(results[2], l1results[2], "l1 cache not coherent") 78 79 // Test List and Delete 80 keys, err := cachedStore.List(store.ListPrefix("a")) 81 assert.Nil(err, "List should not error") 82 assert.Len(keys, 3, "List should return 3 keys") 83 for _, k := range keys { 84 err := cachedStore.Delete(k) 85 assert.Nil(err, "Delete should not error") 86 _, err = cachedStore.Read(k) 87 // N.B. - this may not pass on stores that are eventually consistent 88 assert.Equal(store.ErrNotFound, err, "record should be gone") 89 } 90 91 // Test Write 92 err = cachedStore.Write(r1) 93 assert.Nil(err, "Write shouldn't fail") 94 l2result, err := l2.Read(r1.Key) 95 assert.Nil(err) 96 assert.Len(l2result, 1) 97 assert.Equal(r1, l2result[0], "Write didn't make it all the way through to l2") 98 99 }