mirror of
https://github.com/rclone/rclone
synced 2024-12-24 15:43:45 +01:00
e43b5ce5e5
This is possible now that we no longer support go1.12 and brings rclone into line with standard practices in the Go world. This also removes errors.New and errors.Errorf from lib/errors and prefers the stdlib errors package over lib/errors.
148 lines
3.4 KiB
Go
148 lines
3.4 KiB
Go
package rc
|
|
|
|
import (
|
|
"context"
|
|
"encoding/json"
|
|
"errors"
|
|
"fmt"
|
|
"testing"
|
|
|
|
"github.com/rclone/rclone/cmd/serve/httplib"
|
|
"github.com/rclone/rclone/fs"
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/require"
|
|
)
|
|
|
|
func clearOptionBlock() func() {
|
|
oldOptionBlock := optionBlock
|
|
optionBlock = map[string]interface{}{}
|
|
return func() {
|
|
optionBlock = oldOptionBlock
|
|
}
|
|
}
|
|
|
|
var testOptions = struct {
|
|
String string
|
|
Int int
|
|
}{
|
|
String: "hello",
|
|
Int: 42,
|
|
}
|
|
|
|
func TestAddOption(t *testing.T) {
|
|
defer clearOptionBlock()()
|
|
assert.Equal(t, len(optionBlock), 0)
|
|
AddOption("potato", &testOptions)
|
|
assert.Equal(t, len(optionBlock), 1)
|
|
assert.Equal(t, len(optionReload), 0)
|
|
assert.Equal(t, &testOptions, optionBlock["potato"])
|
|
}
|
|
|
|
func TestAddOptionReload(t *testing.T) {
|
|
defer clearOptionBlock()()
|
|
assert.Equal(t, len(optionBlock), 0)
|
|
reload := func(ctx context.Context) error { return nil }
|
|
AddOptionReload("potato", &testOptions, reload)
|
|
assert.Equal(t, len(optionBlock), 1)
|
|
assert.Equal(t, len(optionReload), 1)
|
|
assert.Equal(t, &testOptions, optionBlock["potato"])
|
|
assert.Equal(t, fmt.Sprintf("%p", reload), fmt.Sprintf("%p", optionReload["potato"]))
|
|
}
|
|
|
|
func TestOptionsBlocks(t *testing.T) {
|
|
defer clearOptionBlock()()
|
|
AddOption("potato", &testOptions)
|
|
call := Calls.Get("options/blocks")
|
|
require.NotNil(t, call)
|
|
in := Params{}
|
|
out, err := call.Fn(context.Background(), in)
|
|
require.NoError(t, err)
|
|
require.NotNil(t, out)
|
|
assert.Equal(t, Params{"options": []string{"potato"}}, out)
|
|
}
|
|
|
|
func TestOptionsGet(t *testing.T) {
|
|
defer clearOptionBlock()()
|
|
AddOption("potato", &testOptions)
|
|
call := Calls.Get("options/get")
|
|
require.NotNil(t, call)
|
|
in := Params{}
|
|
out, err := call.Fn(context.Background(), in)
|
|
require.NoError(t, err)
|
|
require.NotNil(t, out)
|
|
assert.Equal(t, Params{"potato": &testOptions}, out)
|
|
}
|
|
|
|
func TestOptionsGetMarshal(t *testing.T) {
|
|
defer clearOptionBlock()()
|
|
ctx := context.Background()
|
|
ci := fs.GetConfig(ctx)
|
|
|
|
// Add some real options
|
|
AddOption("http", &httplib.DefaultOpt)
|
|
AddOption("main", ci)
|
|
AddOption("rc", &DefaultOpt)
|
|
|
|
// get them
|
|
call := Calls.Get("options/get")
|
|
require.NotNil(t, call)
|
|
in := Params{}
|
|
out, err := call.Fn(context.Background(), in)
|
|
require.NoError(t, err)
|
|
require.NotNil(t, out)
|
|
|
|
// Check that they marshal
|
|
_, err = json.Marshal(out)
|
|
require.NoError(t, err)
|
|
}
|
|
|
|
func TestOptionsSet(t *testing.T) {
|
|
defer clearOptionBlock()()
|
|
var reloaded int
|
|
AddOptionReload("potato", &testOptions, func(ctx context.Context) error {
|
|
if reloaded > 0 {
|
|
return errors.New("error while reloading")
|
|
}
|
|
reloaded++
|
|
return nil
|
|
})
|
|
call := Calls.Get("options/set")
|
|
require.NotNil(t, call)
|
|
|
|
in := Params{
|
|
"potato": Params{
|
|
"Int": 50,
|
|
},
|
|
}
|
|
out, err := call.Fn(context.Background(), in)
|
|
require.NoError(t, err)
|
|
require.Nil(t, out)
|
|
assert.Equal(t, 50, testOptions.Int)
|
|
assert.Equal(t, "hello", testOptions.String)
|
|
assert.Equal(t, 1, reloaded)
|
|
|
|
// error from reload
|
|
_, err = call.Fn(context.Background(), in)
|
|
require.Error(t, err)
|
|
assert.Contains(t, err.Error(), "error while reloading")
|
|
|
|
// unknown option block
|
|
in = Params{
|
|
"sausage": Params{
|
|
"Int": 50,
|
|
},
|
|
}
|
|
_, err = call.Fn(context.Background(), in)
|
|
require.Error(t, err)
|
|
assert.Contains(t, err.Error(), "unknown option block")
|
|
|
|
// bad shape
|
|
in = Params{
|
|
"potato": []string{"a", "b"},
|
|
}
|
|
_, err = call.Fn(context.Background(), in)
|
|
require.Error(t, err)
|
|
assert.Contains(t, err.Error(), "failed to write options")
|
|
|
|
}
|