2019-05-23 19:26:16 +08:00
|
|
|
package cache
|
|
|
|
|
|
|
|
import (
|
2020-11-05 23:18:51 +08:00
|
|
|
"context"
|
2019-05-23 19:26:16 +08:00
|
|
|
"errors"
|
|
|
|
"testing"
|
|
|
|
|
2019-07-29 01:47:38 +08:00
|
|
|
"github.com/rclone/rclone/fs"
|
|
|
|
"github.com/rclone/rclone/fstest/mockfs"
|
2019-05-23 19:26:16 +08:00
|
|
|
"github.com/stretchr/testify/assert"
|
|
|
|
"github.com/stretchr/testify/require"
|
|
|
|
)
|
|
|
|
|
|
|
|
var (
|
|
|
|
called = 0
|
|
|
|
errSentinel = errors.New("an error")
|
|
|
|
)
|
|
|
|
|
2022-12-08 20:43:53 +08:00
|
|
|
func mockNewFs(t *testing.T) func(ctx context.Context, path string) (fs.Fs, error) {
|
2019-05-23 19:26:16 +08:00
|
|
|
called = 0
|
2020-11-05 23:18:51 +08:00
|
|
|
create := func(ctx context.Context, path string) (f fs.Fs, err error) {
|
2019-05-23 19:26:16 +08:00
|
|
|
assert.Equal(t, 0, called)
|
|
|
|
called++
|
|
|
|
switch path {
|
2020-05-01 19:49:34 +08:00
|
|
|
case "mock:/":
|
2023-04-28 19:01:04 +08:00
|
|
|
return mockfs.NewFs(ctx, "mock", "/", nil)
|
2024-03-10 12:36:57 +08:00
|
|
|
case "mock:/file.txt", "mock:file.txt", "mock:/file2.txt", "mock:file2.txt":
|
2023-04-28 19:01:04 +08:00
|
|
|
fMock, err := mockfs.NewFs(ctx, "mock", "/", nil)
|
|
|
|
require.NoError(t, err)
|
|
|
|
return fMock, fs.ErrorIsFile
|
2020-05-01 19:49:34 +08:00
|
|
|
case "mock:/error":
|
2019-05-23 19:26:16 +08:00
|
|
|
return nil, errSentinel
|
|
|
|
}
|
2020-05-01 19:49:34 +08:00
|
|
|
t.Fatalf("Unknown path %q", path)
|
|
|
|
panic("unreachable")
|
2019-05-23 19:26:16 +08:00
|
|
|
}
|
2022-12-08 20:43:53 +08:00
|
|
|
t.Cleanup(Clear)
|
|
|
|
return create
|
2019-05-23 19:26:16 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
func TestGet(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f, err := GetFn(context.Background(), "mock:/", create)
|
2019-05-23 19:26:16 +08:00
|
|
|
require.NoError(t, err)
|
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f2, err := GetFn(context.Background(), "mock:/", create)
|
2019-05-23 19:26:16 +08:00
|
|
|
require.NoError(t, err)
|
|
|
|
|
|
|
|
assert.Equal(t, f, f2)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestGetFile(t *testing.T) {
|
2024-03-10 12:36:57 +08:00
|
|
|
defer ClearMappings()
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f, err := GetFn(context.Background(), "mock:/file.txt", create)
|
2019-05-23 19:26:16 +08:00
|
|
|
require.Equal(t, fs.ErrorIsFile, err)
|
2019-08-10 00:03:57 +08:00
|
|
|
require.NotNil(t, f)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f2, err := GetFn(context.Background(), "mock:/file.txt", create)
|
2019-05-23 19:26:16 +08:00
|
|
|
require.Equal(t, fs.ErrorIsFile, err)
|
2019-08-10 00:03:57 +08:00
|
|
|
require.NotNil(t, f2)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
|
|
|
assert.Equal(t, f, f2)
|
2020-07-02 17:15:47 +08:00
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
// check it is also found when referred to by parent name
|
2020-11-05 23:18:51 +08:00
|
|
|
f2, err = GetFn(context.Background(), "mock:/", create)
|
2020-07-02 17:15:47 +08:00
|
|
|
require.Nil(t, err)
|
|
|
|
require.NotNil(t, f2)
|
|
|
|
|
|
|
|
assert.Equal(t, f, f2)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestGetFile2(t *testing.T) {
|
2024-03-10 12:36:57 +08:00
|
|
|
defer ClearMappings()
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2020-07-02 17:15:47 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2020-07-02 17:15:47 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f, err := GetFn(context.Background(), "mock:file.txt", create)
|
2020-07-02 17:15:47 +08:00
|
|
|
require.Equal(t, fs.ErrorIsFile, err)
|
|
|
|
require.NotNil(t, f)
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2020-07-02 17:15:47 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f2, err := GetFn(context.Background(), "mock:file.txt", create)
|
2020-07-02 17:15:47 +08:00
|
|
|
require.Equal(t, fs.ErrorIsFile, err)
|
|
|
|
require.NotNil(t, f2)
|
|
|
|
|
|
|
|
assert.Equal(t, f, f2)
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
// check it is also found when referred to by parent name
|
2020-11-05 23:18:51 +08:00
|
|
|
f2, err = GetFn(context.Background(), "mock:/", create)
|
2020-07-02 17:15:47 +08:00
|
|
|
require.Nil(t, err)
|
|
|
|
require.NotNil(t, f2)
|
|
|
|
|
|
|
|
assert.Equal(t, f, f2)
|
2019-05-23 19:26:16 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
func TestGetError(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
f, err := GetFn(context.Background(), "mock:/error", create)
|
2019-05-23 19:26:16 +08:00
|
|
|
require.Equal(t, errSentinel, err)
|
|
|
|
require.Equal(t, nil, f)
|
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
}
|
|
|
|
|
2024-01-19 18:34:03 +08:00
|
|
|
func TestPutErr(t *testing.T) {
|
|
|
|
create := mockNewFs(t)
|
|
|
|
|
|
|
|
f, err := mockfs.NewFs(context.Background(), "mock", "", nil)
|
|
|
|
require.NoError(t, err)
|
|
|
|
|
|
|
|
assert.Equal(t, 0, Entries())
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
PutErr("mock:/", f, fs.ErrorNotFoundInConfigFile)
|
2024-01-19 18:34:03 +08:00
|
|
|
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
fNew, err := GetFn(context.Background(), "mock:/", create)
|
|
|
|
require.Equal(t, fs.ErrorNotFoundInConfigFile, err)
|
2024-01-19 18:34:03 +08:00
|
|
|
require.Equal(t, f, fNew)
|
|
|
|
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
|
|
|
|
// Check canonicalisation
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
PutErr("mock:/file.txt", f, fs.ErrorNotFoundInConfigFile)
|
2024-01-19 18:34:03 +08:00
|
|
|
|
|
|
|
fNew, err = GetFn(context.Background(), "mock:/file.txt", create)
|
2024-03-10 12:36:57 +08:00
|
|
|
require.Equal(t, fs.ErrorNotFoundInConfigFile, err)
|
2024-01-19 18:34:03 +08:00
|
|
|
require.Equal(t, f, fNew)
|
|
|
|
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
}
|
|
|
|
|
2019-05-23 19:26:16 +08:00
|
|
|
func TestPut(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2023-04-28 19:01:04 +08:00
|
|
|
f, err := mockfs.NewFs(context.Background(), "mock", "/alien", nil)
|
|
|
|
require.NoError(t, err)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-05-01 19:49:34 +08:00
|
|
|
Put("mock:/alien", f)
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
fNew, err := GetFn(context.Background(), "mock:/alien", create)
|
2019-05-23 19:26:16 +08:00
|
|
|
require.NoError(t, err)
|
|
|
|
require.Equal(t, f, fNew)
|
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2020-05-01 19:49:34 +08:00
|
|
|
|
|
|
|
// Check canonicalisation
|
|
|
|
|
|
|
|
Put("mock:/alien/", f)
|
|
|
|
|
2020-11-05 23:18:51 +08:00
|
|
|
fNew, err = GetFn(context.Background(), "mock:/alien/", create)
|
2020-05-01 19:49:34 +08:00
|
|
|
require.NoError(t, err)
|
|
|
|
require.Equal(t, f, fNew)
|
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2020-05-01 19:49:34 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
func TestPin(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2020-05-01 19:49:34 +08:00
|
|
|
|
2022-08-14 10:56:32 +08:00
|
|
|
// Test pinning and unpinning nonexistent
|
2023-04-28 19:01:04 +08:00
|
|
|
f, err := mockfs.NewFs(context.Background(), "mock", "/alien", nil)
|
|
|
|
require.NoError(t, err)
|
2020-05-01 19:49:34 +08:00
|
|
|
Pin(f)
|
|
|
|
Unpin(f)
|
|
|
|
|
|
|
|
// Now test pinning an existing
|
2020-11-05 23:18:51 +08:00
|
|
|
f2, err := GetFn(context.Background(), "mock:/", create)
|
2020-05-01 19:49:34 +08:00
|
|
|
require.NoError(t, err)
|
|
|
|
Pin(f2)
|
|
|
|
Unpin(f2)
|
|
|
|
}
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
func TestPinFile(t *testing.T) {
|
|
|
|
defer ClearMappings()
|
|
|
|
create := mockNewFs(t)
|
|
|
|
|
|
|
|
// Test pinning and unpinning nonexistent
|
|
|
|
f, err := mockfs.NewFs(context.Background(), "mock", "/file.txt", nil)
|
|
|
|
require.NoError(t, err)
|
|
|
|
Pin(f)
|
|
|
|
Unpin(f)
|
|
|
|
|
|
|
|
// Now test pinning an existing
|
|
|
|
f2, err := GetFn(context.Background(), "mock:/file.txt", create)
|
|
|
|
require.Equal(t, fs.ErrorIsFile, err)
|
|
|
|
assert.Equal(t, 1, len(childParentMap))
|
|
|
|
|
|
|
|
Pin(f2)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
pinned, unpinned := EntriesWithPinCount()
|
|
|
|
assert.Equal(t, 1, pinned)
|
|
|
|
assert.Equal(t, 0, unpinned)
|
|
|
|
|
|
|
|
Unpin(f2)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
pinned, unpinned = EntriesWithPinCount()
|
|
|
|
assert.Equal(t, 0, pinned)
|
|
|
|
assert.Equal(t, 1, unpinned)
|
|
|
|
|
|
|
|
// try a different child of the same parent, and parent
|
|
|
|
// should not add additional cache items
|
|
|
|
called = 0 // this one does create() because we haven't seen it before and don't yet know it's a file
|
|
|
|
f3, err := GetFn(context.Background(), "mock:/file2.txt", create)
|
|
|
|
assert.Equal(t, fs.ErrorIsFile, err)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
assert.Equal(t, 2, len(childParentMap))
|
|
|
|
|
|
|
|
parent, err := GetFn(context.Background(), "mock:/", create)
|
|
|
|
assert.NoError(t, err)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
assert.Equal(t, 2, len(childParentMap))
|
|
|
|
|
|
|
|
Pin(f3)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
pinned, unpinned = EntriesWithPinCount()
|
|
|
|
assert.Equal(t, 1, pinned)
|
|
|
|
assert.Equal(t, 0, unpinned)
|
|
|
|
|
|
|
|
Unpin(f3)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
pinned, unpinned = EntriesWithPinCount()
|
|
|
|
assert.Equal(t, 0, pinned)
|
|
|
|
assert.Equal(t, 1, unpinned)
|
|
|
|
|
|
|
|
Pin(parent)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
pinned, unpinned = EntriesWithPinCount()
|
|
|
|
assert.Equal(t, 1, pinned)
|
|
|
|
assert.Equal(t, 0, unpinned)
|
|
|
|
|
|
|
|
Unpin(parent)
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
pinned, unpinned = EntriesWithPinCount()
|
|
|
|
assert.Equal(t, 0, pinned)
|
|
|
|
assert.Equal(t, 1, unpinned)
|
|
|
|
|
|
|
|
// all 3 should have equal configstrings
|
|
|
|
assert.Equal(t, fs.ConfigString(f2), fs.ConfigString(f3))
|
|
|
|
assert.Equal(t, fs.ConfigString(f2), fs.ConfigString(parent))
|
|
|
|
}
|
|
|
|
|
2020-11-30 19:52:25 +08:00
|
|
|
func TestClearConfig(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2020-11-30 19:52:25 +08:00
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2020-11-30 19:52:25 +08:00
|
|
|
|
|
|
|
_, err := GetFn(context.Background(), "mock:/file.txt", create)
|
|
|
|
require.Equal(t, fs.ErrorIsFile, err)
|
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2020-11-30 19:52:25 +08:00
|
|
|
|
2024-03-10 12:36:57 +08:00
|
|
|
assert.Equal(t, 1, ClearConfig("mock"))
|
2020-11-30 19:52:25 +08:00
|
|
|
|
|
|
|
assert.Equal(t, 0, Entries())
|
|
|
|
}
|
|
|
|
|
2020-05-01 19:49:34 +08:00
|
|
|
func TestClear(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2020-05-01 19:49:34 +08:00
|
|
|
|
|
|
|
// Create something
|
2020-11-05 23:18:51 +08:00
|
|
|
_, err := GetFn(context.Background(), "mock:/", create)
|
2020-05-01 19:49:34 +08:00
|
|
|
require.NoError(t, err)
|
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 1, Entries())
|
2020-05-01 19:49:34 +08:00
|
|
|
|
|
|
|
Clear()
|
|
|
|
|
2021-03-30 00:18:49 +08:00
|
|
|
assert.Equal(t, 0, Entries())
|
2019-05-23 19:26:16 +08:00
|
|
|
}
|
2020-11-29 19:25:51 +08:00
|
|
|
|
|
|
|
func TestEntries(t *testing.T) {
|
2022-12-08 20:43:53 +08:00
|
|
|
create := mockNewFs(t)
|
2020-11-29 19:25:51 +08:00
|
|
|
|
|
|
|
assert.Equal(t, 0, Entries())
|
|
|
|
|
|
|
|
// Create something
|
|
|
|
_, err := GetFn(context.Background(), "mock:/", create)
|
|
|
|
require.NoError(t, err)
|
|
|
|
|
|
|
|
assert.Equal(t, 1, Entries())
|
|
|
|
}
|