github.com/rclone/rclone@v1.66.1-0.20240517100346-7b89735ae726/fs/cache/cache_test.go (about) 1 package cache 2 3 import ( 4 "context" 5 "errors" 6 "testing" 7 8 "github.com/rclone/rclone/fs" 9 "github.com/rclone/rclone/fstest/mockfs" 10 "github.com/stretchr/testify/assert" 11 "github.com/stretchr/testify/require" 12 ) 13 14 var ( 15 called = 0 16 errSentinel = errors.New("an error") 17 ) 18 19 func mockNewFs(t *testing.T) func(ctx context.Context, path string) (fs.Fs, error) { 20 called = 0 21 create := func(ctx context.Context, path string) (f fs.Fs, err error) { 22 assert.Equal(t, 0, called) 23 called++ 24 switch path { 25 case "mock:/": 26 return mockfs.NewFs(ctx, "mock", "/", nil) 27 case "mock:/file.txt", "mock:file.txt": 28 fMock, err := mockfs.NewFs(ctx, "mock", "/", nil) 29 require.NoError(t, err) 30 return fMock, fs.ErrorIsFile 31 case "mock:/error": 32 return nil, errSentinel 33 } 34 t.Fatalf("Unknown path %q", path) 35 panic("unreachable") 36 } 37 t.Cleanup(Clear) 38 return create 39 } 40 41 func TestGet(t *testing.T) { 42 create := mockNewFs(t) 43 44 assert.Equal(t, 0, Entries()) 45 46 f, err := GetFn(context.Background(), "mock:/", create) 47 require.NoError(t, err) 48 49 assert.Equal(t, 1, Entries()) 50 51 f2, err := GetFn(context.Background(), "mock:/", create) 52 require.NoError(t, err) 53 54 assert.Equal(t, f, f2) 55 } 56 57 func TestGetFile(t *testing.T) { 58 create := mockNewFs(t) 59 60 assert.Equal(t, 0, Entries()) 61 62 f, err := GetFn(context.Background(), "mock:/file.txt", create) 63 require.Equal(t, fs.ErrorIsFile, err) 64 require.NotNil(t, f) 65 66 assert.Equal(t, 2, Entries()) 67 68 f2, err := GetFn(context.Background(), "mock:/file.txt", create) 69 require.Equal(t, fs.ErrorIsFile, err) 70 require.NotNil(t, f2) 71 72 assert.Equal(t, f, f2) 73 74 // check parent is there too 75 f2, err = GetFn(context.Background(), "mock:/", create) 76 require.Nil(t, err) 77 require.NotNil(t, f2) 78 79 assert.Equal(t, f, f2) 80 } 81 82 func TestGetFile2(t *testing.T) { 83 create := mockNewFs(t) 84 85 assert.Equal(t, 0, Entries()) 86 87 f, err := GetFn(context.Background(), "mock:file.txt", create) 88 require.Equal(t, fs.ErrorIsFile, err) 89 require.NotNil(t, f) 90 91 assert.Equal(t, 2, Entries()) 92 93 f2, err := GetFn(context.Background(), "mock:file.txt", create) 94 require.Equal(t, fs.ErrorIsFile, err) 95 require.NotNil(t, f2) 96 97 assert.Equal(t, f, f2) 98 99 // check parent is there too 100 f2, err = GetFn(context.Background(), "mock:/", create) 101 require.Nil(t, err) 102 require.NotNil(t, f2) 103 104 assert.Equal(t, f, f2) 105 } 106 107 func TestGetError(t *testing.T) { 108 create := mockNewFs(t) 109 110 assert.Equal(t, 0, Entries()) 111 112 f, err := GetFn(context.Background(), "mock:/error", create) 113 require.Equal(t, errSentinel, err) 114 require.Equal(t, nil, f) 115 116 assert.Equal(t, 0, Entries()) 117 } 118 119 func TestPutErr(t *testing.T) { 120 create := mockNewFs(t) 121 122 f, err := mockfs.NewFs(context.Background(), "mock", "", nil) 123 require.NoError(t, err) 124 125 assert.Equal(t, 0, Entries()) 126 127 PutErr("mock:file.txt", f, fs.ErrorIsFile) 128 129 assert.Equal(t, 1, Entries()) 130 131 fNew, err := GetFn(context.Background(), "mock:file.txt", create) 132 require.Equal(t, fs.ErrorIsFile, err) 133 require.Equal(t, f, fNew) 134 135 assert.Equal(t, 1, Entries()) 136 137 // Check canonicalisation 138 139 PutErr("mock:/file.txt", f, fs.ErrorIsFile) 140 141 fNew, err = GetFn(context.Background(), "mock:/file.txt", create) 142 require.Equal(t, fs.ErrorIsFile, err) 143 require.Equal(t, f, fNew) 144 145 assert.Equal(t, 1, Entries()) 146 } 147 148 func TestPut(t *testing.T) { 149 create := mockNewFs(t) 150 151 f, err := mockfs.NewFs(context.Background(), "mock", "/alien", nil) 152 require.NoError(t, err) 153 154 assert.Equal(t, 0, Entries()) 155 156 Put("mock:/alien", f) 157 158 assert.Equal(t, 1, Entries()) 159 160 fNew, err := GetFn(context.Background(), "mock:/alien", create) 161 require.NoError(t, err) 162 require.Equal(t, f, fNew) 163 164 assert.Equal(t, 1, Entries()) 165 166 // Check canonicalisation 167 168 Put("mock:/alien/", f) 169 170 fNew, err = GetFn(context.Background(), "mock:/alien/", create) 171 require.NoError(t, err) 172 require.Equal(t, f, fNew) 173 174 assert.Equal(t, 1, Entries()) 175 } 176 177 func TestPin(t *testing.T) { 178 create := mockNewFs(t) 179 180 // Test pinning and unpinning nonexistent 181 f, err := mockfs.NewFs(context.Background(), "mock", "/alien", nil) 182 require.NoError(t, err) 183 Pin(f) 184 Unpin(f) 185 186 // Now test pinning an existing 187 f2, err := GetFn(context.Background(), "mock:/", create) 188 require.NoError(t, err) 189 Pin(f2) 190 Unpin(f2) 191 } 192 193 func TestClearConfig(t *testing.T) { 194 create := mockNewFs(t) 195 196 assert.Equal(t, 0, Entries()) 197 198 _, err := GetFn(context.Background(), "mock:/file.txt", create) 199 require.Equal(t, fs.ErrorIsFile, err) 200 201 assert.Equal(t, 2, Entries()) // file + parent 202 203 assert.Equal(t, 2, ClearConfig("mock")) 204 205 assert.Equal(t, 0, Entries()) 206 } 207 208 func TestClear(t *testing.T) { 209 create := mockNewFs(t) 210 211 // Create something 212 _, err := GetFn(context.Background(), "mock:/", create) 213 require.NoError(t, err) 214 215 assert.Equal(t, 1, Entries()) 216 217 Clear() 218 219 assert.Equal(t, 0, Entries()) 220 } 221 222 func TestEntries(t *testing.T) { 223 create := mockNewFs(t) 224 225 assert.Equal(t, 0, Entries()) 226 227 // Create something 228 _, err := GetFn(context.Background(), "mock:/", create) 229 require.NoError(t, err) 230 231 assert.Equal(t, 1, Entries()) 232 }