github.com/cloudreve/Cloudreve/v3@v3.0.0-20240224133659-3edb00a6484c/pkg/cache/memo_test.go (about)

     1  package cache
     2  
     3  import (
     4  	"github.com/stretchr/testify/assert"
     5  	"path/filepath"
     6  	"testing"
     7  	"time"
     8  )
     9  
    10  func TestNewMemoStore(t *testing.T) {
    11  	asserts := assert.New(t)
    12  
    13  	store := NewMemoStore()
    14  	asserts.NotNil(store)
    15  	asserts.NotNil(store.Store)
    16  }
    17  
    18  func TestMemoStore_Set(t *testing.T) {
    19  	asserts := assert.New(t)
    20  
    21  	store := NewMemoStore()
    22  	err := store.Set("KEY", "vAL", -1)
    23  	asserts.NoError(err)
    24  
    25  	val, ok := store.Store.Load("KEY")
    26  	asserts.True(ok)
    27  	asserts.Equal("vAL", val.(itemWithTTL).Value)
    28  }
    29  
    30  func TestMemoStore_Get(t *testing.T) {
    31  	asserts := assert.New(t)
    32  	store := NewMemoStore()
    33  
    34  	// 正常情况
    35  	{
    36  		_ = store.Set("string", "string_val", -1)
    37  		val, ok := store.Get("string")
    38  		asserts.Equal("string_val", val)
    39  		asserts.True(ok)
    40  	}
    41  
    42  	// Key不存在
    43  	{
    44  		val, ok := store.Get("something")
    45  		asserts.Equal(nil, val)
    46  		asserts.False(ok)
    47  	}
    48  
    49  	// 存储struct
    50  	{
    51  		type testStruct struct {
    52  			key int
    53  		}
    54  		test := testStruct{key: 233}
    55  		_ = store.Set("struct", test, -1)
    56  		val, ok := store.Get("struct")
    57  		asserts.True(ok)
    58  		res, ok := val.(testStruct)
    59  		asserts.True(ok)
    60  		asserts.Equal(test, res)
    61  	}
    62  
    63  	// 过期
    64  	{
    65  		_ = store.Set("string", "string_val", 1)
    66  		time.Sleep(time.Duration(2) * time.Second)
    67  		val, ok := store.Get("string")
    68  		asserts.Nil(val)
    69  		asserts.False(ok)
    70  	}
    71  
    72  }
    73  
    74  func TestMemoStore_Gets(t *testing.T) {
    75  	asserts := assert.New(t)
    76  	store := NewMemoStore()
    77  
    78  	err := store.Set("1", "1,val", -1)
    79  	err = store.Set("2", "2,val", -1)
    80  	err = store.Set("3", "3,val", -1)
    81  	err = store.Set("4", "4,val", -1)
    82  	asserts.NoError(err)
    83  
    84  	// 全部命中
    85  	{
    86  		values, miss := store.Gets([]string{"1", "2", "3", "4"}, "")
    87  		asserts.Len(values, 4)
    88  		asserts.Len(miss, 0)
    89  	}
    90  
    91  	// 命中一半
    92  	{
    93  		values, miss := store.Gets([]string{"1", "2", "9", "10"}, "")
    94  		asserts.Len(values, 2)
    95  		asserts.Equal([]string{"9", "10"}, miss)
    96  	}
    97  }
    98  
    99  func TestMemoStore_Sets(t *testing.T) {
   100  	asserts := assert.New(t)
   101  	store := NewMemoStore()
   102  
   103  	err := store.Sets(map[string]interface{}{
   104  		"1": "1.val",
   105  		"2": "2.val",
   106  		"3": "3.val",
   107  		"4": "4.val",
   108  	}, "test_")
   109  	asserts.NoError(err)
   110  
   111  	vals, miss := store.Gets([]string{"1", "2", "3", "4"}, "test_")
   112  	asserts.Len(miss, 0)
   113  	asserts.Equal(map[string]interface{}{
   114  		"1": "1.val",
   115  		"2": "2.val",
   116  		"3": "3.val",
   117  		"4": "4.val",
   118  	}, vals)
   119  }
   120  
   121  func TestMemoStore_Delete(t *testing.T) {
   122  	asserts := assert.New(t)
   123  	store := NewMemoStore()
   124  
   125  	err := store.Sets(map[string]interface{}{
   126  		"1": "1.val",
   127  		"2": "2.val",
   128  		"3": "3.val",
   129  		"4": "4.val",
   130  	}, "test_")
   131  	asserts.NoError(err)
   132  
   133  	err = store.Delete([]string{"1", "2"}, "test_")
   134  	asserts.NoError(err)
   135  	values, miss := store.Gets([]string{"1", "2", "3", "4"}, "test_")
   136  	asserts.Equal([]string{"1", "2"}, miss)
   137  	asserts.Equal(map[string]interface{}{"3": "3.val", "4": "4.val"}, values)
   138  }
   139  
   140  func TestMemoStore_GarbageCollect(t *testing.T) {
   141  	asserts := assert.New(t)
   142  	store := NewMemoStore()
   143  	store.Set("test", 1, 1)
   144  	time.Sleep(time.Duration(2000) * time.Millisecond)
   145  	store.GarbageCollect()
   146  	_, ok := store.Get("test")
   147  	asserts.False(ok)
   148  }
   149  
   150  func TestMemoStore_PersistFailed(t *testing.T) {
   151  	a := assert.New(t)
   152  	store := NewMemoStore()
   153  	type testStruct struct{ v string }
   154  	store.Set("test", 1, 0)
   155  	store.Set("test2", testStruct{v: "test"}, 0)
   156  	err := store.Persist(filepath.Join(t.TempDir(), "TestMemoStore_PersistFailed"))
   157  	a.Error(err)
   158  }
   159  
   160  func TestMemoStore_PersistAndRestore(t *testing.T) {
   161  	a := assert.New(t)
   162  	store := NewMemoStore()
   163  	store.Set("test", 1, 0)
   164  	// already expired
   165  	store.Store.Store("test2", itemWithTTL{Value: "test", Expires: 1})
   166  	// expired after persist
   167  	store.Set("test3", 1, 1)
   168  	temp := filepath.Join(t.TempDir(), "TestMemoStore_PersistFailed")
   169  
   170  	// Persist
   171  	err := store.Persist(temp)
   172  	a.NoError(err)
   173  	a.FileExists(temp)
   174  
   175  	time.Sleep(2 * time.Second)
   176  	// Restore
   177  	store2 := NewMemoStore()
   178  	err = store2.Restore(temp)
   179  	a.NoError(err)
   180  	test, testOk := store2.Get("test")
   181  	a.EqualValues(1, test)
   182  	a.True(testOk)
   183  	test2, test2Ok := store2.Get("test2")
   184  	a.Nil(test2)
   185  	a.False(test2Ok)
   186  	test3, test3Ok := store2.Get("test3")
   187  	a.Nil(test3)
   188  	a.False(test3Ok)
   189  
   190  	a.NoFileExists(temp)
   191  }